如何在 C# Winform 中专门在 Wndproc 中获取 IME 布局?

Posted

技术标签:

【中文标题】如何在 C# Winform 中专门在 Wndproc 中获取 IME 布局?【英文标题】:How to get the IME layout in C# Winform specially in Wndproc? 【发布时间】:2017-06-25 20:03:32 【问题描述】:

我有一个 winform 应用程序,我想在 C# 中获取当前输入语言的信息。我有 Windows 10 机器,我选择了韩语。选择韩语后,任务栏中有一个切换按钮可将输入语言更改为英语或韩语。

以下代码总是给出韩语,但当我选择英语输入时,它应该给出英语。

    [DllImport("user32.dll")]
    static extern IntPtr GetForegroundWindow();
    [DllImport("user32.dll")]
    static extern uint GetWindowThreadProcessId(IntPtr hwnd, IntPtr proccess);
    [DllImport("user32.dll")]
    static extern IntPtr GetKeyboardLayout(uint thread);
    public Form1()
    
        InitializeComponent();
        IntPtr foregroundWindow = GetForegroundWindow();
        uint foregroundProcess = GetWindowThreadProcessId(foregroundWindow, IntPtr.Zero);
        int keyboardLayout = GetKeyboardLayout(foregroundProcess).ToInt32() & 0xFFFF;
        CultureInfo info = new CultureInfo(keyboardLayout);
        int keyboardLayoutId = info.KeyboardLayoutId;
        string name = info.Name;
    

有没有其他方法可以获取输入语言信息。

您可以找到相同的附加图像。我已将 A 突出显示为英文输入。

我想要WndProc 方法中的这些信息。

问题总结: 所以我想处理用户通过切换按钮切换语言以键入的情况,当用户通过切换按钮切换语言时,我想要任何 wndproc 消息或窗口侧事件来获取语言信息。

【问题讨论】:

InputLanguage.CurrentInputLanguage @RezaAghaei 如何使用 InputLanguage.CurrentInputLanguage? 阅读手册:msdn.microsoft.com/en-us/library/… 工具栏按钮会更改前台进程的选定键盘布局。考虑到您的代码在您启动程序后运行一微秒,您可能无法足够快地点击该工具栏按钮。所以这只是一个pebkac问题。考虑一下 InputLanguageChanged 事件吧。 WM_INPUTLANGUAGECHANGE 消息。已经包装在 Winforms 中,它会触发 InputLanguageChanged 事件。 【参考方案1】:

您的问题是 IME 模式和输入布局混淆的结果。在这两种情况下,您的输入布局都是韩语 - 改变的是您的 IME 模式。

您可以使用Control.ImeMode 找到输入控件的IME 模式(并使用Control.ImeModeChanged 检查更改)。这将告诉您您使用韩语 - Hangul 或韩语 - Alpha。 编辑:实际上,这仅允许您强制执行给定设置,而不读取用户指定的 IME 模式,显然不应该不能用。

更复杂的是,如果您启用了全局输入(自 Windows 8 起可用),输入配置不再按线程存储,而是全局存储。在这种情况下,ImeMode 不起作用,并被完全忽略。我认为您无法从应用程序方面对此做任何事情 - 该设置不再是您可以查看或更改的。根据 MSDN,正确的替换是 ImmGetConversionStatus 函数,但仅适用于桌面应用程序。

【讨论】:

它在任何情况下都提供 NoControl @viveknuna 是的,因为您启用了全局输入。正如我在第三段中指出的那样,这完全禁用了 ImeMode 功能。 所以这意味着无论输入韩文还是英文都无法获得这些信息 @viveknuna 我能找到的最好的是imm32.dll,但我不确定它在实践中是如何工作的,或者使用它是否是个好主意。 Windows 中的方法似乎是这不是您的业务,可以这么说 - 它是为用户服务的。鉴于 IME 的复杂程度,我不能说我不同意 :D 将在 2 天内开始为这个问题提供赏金:P

以上是关于如何在 C# Winform 中专门在 Wndproc 中获取 IME 布局?的主要内容,如果未能解决你的问题,请参考以下文章

如何在C# Winform中嵌套一个播放器,就好像PPS那种我想做一个播放视频的软件,请高手指点啊

C#中对web程序进行数据库连接配置的问题,有没有winform和webforom通用的办法?

C# winForm添加webservice接口

[Winform]CefSharp ——js调用c#方法

c# winform 如何把时间戳转换为时间?

winform如何实现将数据库数据加载到树上