2

我的非 Unicode 应用程序需要能够处理 Unicode 键盘输入(WM_CHAR/等),因此接收 8 位字符代码,然后在内部将其转换为 Unicode。需要 9x 兼容性,因此不能选择使用大多数 Unicode API。

目前它查看 PRIMARYLANGID(GetKeyboardLayout(0)) 返回的语言,并在硬编码表中查找相关代码页。我找不到获取特定语言或键盘布局使用的代码页的函数。然后可以使用 MultiByteToWideChar 转换字符/字符串。

有没有办法获取当前键盘布局的代码页?GetACP 返回不受当前键盘布局影响的默认系统代码页。

4

3 回答 3

3

这是另一种方法:

WORD languageID = LOWORD(GetKeyboardLayout(0));
char szLCData[6+1];
GetLocaleInfoA(MAKELCID(languageID, SORT_DEFAULT), LOCALE_IDEFAULTANSICODEPAGE,
               szLCData, _countof(szLCData));
int codepage = atoi(szLCData);
于 2009-08-23T04:08:56.110 回答
3

虽然这是一个旧线程,但我今天早上的大部分时间都在寻找一种方法来识别给定特定字符集ID 的 Windows代码页(当当前键盘布局/区域设置未设置为该字符集时)。我认为示例代码可能对寻找类似信息的其他人有用。

就我而言,我想将 161(希腊语)等字符集值映射到等效的 Windows 代码页 1253。经过大量挖掘后,我得出以下结论:

/*
 * Convert a font charset value (e.g. 161 - Greek) into a Windows codepage (1253 for Greek)
 */

UINT CodepageFromCharset(UINT nCharset)
{
    UINT nCodepage = CP_ACP;
    CHARSETINFO csi = {0};

    // Note, the symbol charset (2, CS_SYMBOL) translates to the symbol codepage (42, CP_SYMBOL).
    // However, this codepage does NOT produce valid character translations so the ANSI charset
    // (ANSI_CHARSET) is used instead. This appears to be a known problem.
    // See this discussion: "More than you ever wanted to know about CP_SYMBOL"
    // (http://www.siao2.com/2005/11/08/490495.aspx)

    if (nCharset == SYMBOL_CHARSET) nCharset = 0;
    DWORD* lpdw = (DWORD*)nCharset;

    // Non-zero return value indicates success...
    if (TranslateCharsetInfo(lpdw, &csi, TCI_SRCCHARSET) == 0)
    {
        // This should *not* happen but just in case make sure we use a valid default codepage.
    #ifdef _UNICODE
        csi.ciACP = 1200;
    #else
        csi.ciACP = CP_ACP;
    #endif
    }

    return csi.ciACP;
}

希望这对其他人有用!

约翰

于 2011-01-24T13:06:50.130 回答
1

我在需要在 Windows 9X 上运行的应用程序上遇到了类似的问题。我最终想出的解决方案是监听 WM_INPUTLANGCHANGE 通知消息,当用户更改输入语言时,这些消息会发送到顶级窗口。在我的消息过程中,我有这样的事情:

case WM_INPUTLANGCHANGE:
  {
    CHARSETINFO cs;
    if (TranslateCharsetInfo((DWORD*)wParam,&cs,TCI_SRCCHARSET))
      m_codePage = cs.ciACP;
    return DefWindowProc(WM_INPUTLANGCHANGE,wParam,lParam);
  }
  break;

其中 m_codePage 是一个初始化为 UNIT

  m_codePage = CP_ACP;

然后我在对 MultiByteToWideChar() 的调用中使用 m___codePage 来处理来自 WM_CHAR 等的键。

于 2009-08-18T11:58:12.587 回答