为什么文本框在使用韩语键盘输入值时改变了事件触发三次

本文关键字:事件 三次 改变 文本 韩语 输入 键盘 为什么 | 更新日期: 2023-09-27 18:15:10

我的电脑使用韩语。如果我在TexBox控件中输入值,则触发三次TextBoxChanged事件。第一次我得到了输入的值,第二次我得到了空值,最后我得到了输入的值

如果有人知道这是为什么。

提前感谢。

为什么文本框在使用韩语键盘输入值时改变了事件触发三次

原因是韩文IME会跟踪按键并显示中间的性格。当我们让richtextbox输出它的文本时事件,它将破坏IME的工作

这确实是由于RichTextBox中的缺陷,导致每次字符完成时IME进入模式退出,由于发送WM_IME_COMPOSITION窗口消息给IME,导致它认为IME已完成。这是在检索RichTextBox的Text属性时触发的。这里是一个解决方案,它覆盖了RichTextBox窗口过程来拦截和避免韩国IME条目的错误代码路径,并使用Text的内部值来避免调用底层控件的属性,如果IME是中间合成,但仍然在每个字符输入后更新。请注意,该类公开了一个名为KoreanWorkaroundEnabled的bool属性,默认情况下该属性为true。您可以将其设置为false以将行为恢复为默认值,如果您的文本输入语言是中文或日语,则必须这样做。在这些情况下,这种解决方法将打破正常的行为。您可以使用主机表单上的InputLanguageChanged事件,根据当前输入语言设置属性:

    public Form1()
    {
        InitializeComponent();
        this.InputLanguageChanged += Form1_InputLanguageChanged;
    }
    void Form1_InputLanguageChanged(object sender, InputLanguageChangedEventArgs e)
    {
        if (!e.InputLanguage.Culture.TwoLetterISOLanguageName.Equals("ko"))
            richTextBoxKorean1.KoreanWorkaroundEnabled = false;
        else
            richTextBoxKorean1.KoreanWorkaroundEnabled = true;
    }

下面是重写的RichTextBox类,它实现了解决方法:

public class RichTextBoxKorean : RichTextBox 
{
    [DllImport("imm32.dll", CharSet = CharSet.Unicode)]
    private static extern int ImmGetCompositionString(IntPtr hIMC, uint dwIndex, byte[] lpBuf, int dwBufLen);
    [DllImport("imm32.dll", CharSet = CharSet.Unicode)]
    private static extern IntPtr ImmGetContext(IntPtr hWnd);
    [DllImport("imm32.dll", CharSet = CharSet.Unicode)]
    public static extern IntPtr ImmReleaseContext(IntPtr hWnd, IntPtr context);

    public enum WM_IME
    {
        GCS_RESULTSTR = 0x800,
        EM_STREAMOUT = 0x044A,
        WM_IME_COMPOSITION  =0x10F,
        WM_IME_ENDCOMPOSITION   =0x10E,     
        WM_IME_STARTCOMPOSITION     =0x10D
    }
    private bool skipImeComposition = false;
    private bool imeComposing = false;
    public bool KoreanWorkaroundEnabled = true;
    string _mText = "";
    protected override void WndProc(ref Message m)
    {
        if (KoreanWorkaroundEnabled)
        {
            switch (m.Msg)
            {
                case (int)WM_IME.EM_STREAMOUT:
                    if (imeComposing)
                    {
                        skipImeComposition = true;
                    }
                    base.WndProc(ref m);
                    break;
                case (int)WM_IME.WM_IME_COMPOSITION:
                    if (m.LParam.ToInt32() == (int)WM_IME.GCS_RESULTSTR)
                    {
                        IntPtr hImm = ImmGetContext(this.Handle);
                        int dwSize = ImmGetCompositionString(hImm, (int)WM_IME.GCS_RESULTSTR, null, 0);
                        byte[] outstr = new byte[dwSize];
                        ImmGetCompositionString(hImm, (int)WM_IME.GCS_RESULTSTR, outstr, dwSize);
                        _mText += Encoding.Unicode.GetString(outstr).ToString();
                        ImmReleaseContext(this.Handle, hImm);
                    }
                    if (skipImeComposition)
                    {
                        skipImeComposition = false;
                        break;
                    }
                    base.WndProc(ref m);
                    break;
                case (int)WM_IME.WM_IME_STARTCOMPOSITION:
                    imeComposing = true;
                    base.WndProc(ref m);
                    break;
                case (int)WM_IME.WM_IME_ENDCOMPOSITION:
                    imeComposing = false;
                    base.WndProc(ref m);
                    break;
                default:
                    base.WndProc(ref m);
                    break;
            }
        }
        else
            base.WndProc(ref m);
    }
    public override string Text
    {
        get
        {
            if (!imeComposing)
            {
                _mText = base.Text;
                return base.Text;
            }
            else
            {
                return _mText;
            }
        }
        set
        {
            base.Text = value;
            _mText = value;
        }
    }
}

https://social.msdn.microsoft.com/forums/windows/en us/cefa5376 - 7912 - 47 - f6 b86a - 197 a211c2b70/get -文本——从richtextbox -控制-没有令人不安的输入法输入-东-亚洲- -当language?forum=winforms