pcjbird:>
疑惑列表:
1.SmartPhone输入法是基于IME-IMM的吗?(我想应该是的,因为我调用ImmSetOpenStatus可以打开输入法的)
2.IME是否有标准与非标准之分,是不是一些非标准的输入法有可能不会生成IMM消息?(我在调用天码输入法的时候在组词过程中会收到WM_IME_COMPOSITION消息,但好像A4连这个消息也不会生成)
3.基于SmartPhone操作系统的手机键盘输入法是怎样实现的呢?(我看了SDK下的例子Phoneime,似乎没有什么异常的地方啊)
4.为什么在SmartPhone系统输入法中在组词开始和结束都不会生成WM_IME_STARTCOMPOSITION和WM_IME_ENDCOMPOSITION消息,且在组词过程中使用ImmGetCompositionString也无法获得输入法组词结果,同样ImmGetCandidateList、ImmGetConversionList之类的函数也似乎没有任何结果?
5.那SmartPhone系统中的标准输入框控件是怎样接受输入法的输入的呢?
6.我的目标是自定义一个控件像标准输入框那样(当然是基本功能)能够接受手机键盘输入法的输入,有什么好的建议呢?
期待高手的帮助!!!
pknife>
1)是的;
2)应该没有标准与非标准之分,有的输入法用了钩子也不一定;
3)SDK下的例子Phoneime已经充分展示了如何输入英文和数字,只不过没有调用拼音输入的代码;
4)WM_IME_STARTCOMPOSITION和WM_IME_ENDCOMPOSITION应该是开发者自已发送给系统的;
5)接受输入法,要发送GCS_RESULTSTR消息给系统,当然,要对COMPOSITIONSTRING这个结构的一些参数进行设置;
6)创建一个Edit吧,可以的。
pcjbird>
To pknife:
感谢你的回复!
首先我的目标不是设计一款输入法,而是自定义一个控件像标准输入框那样(当然是基本功能)能够接受手机键盘输入法的输入。
1.WM_IME_STARTCOMPOSITION和WM_IME_ENDCOMPOSITION应该是输入法通过输入法管理器发送给系统,最终通知给应用程序的吧?!问题是,我现在在应用程序中无法接受到这两个输入法消息。
2.正如你所说的,“接受输入法,要发送GCS_RESULTSTR消息给系统,当然,要对COMPOSITIONSTRING这个结构的一些参数进行设置;”。
public string getImeString(IntPtr hwnd)
{
IntPtr hIMC = ImmGetContext(hwnd);
StringBuilder buf;
try
{
int strLen = ImmGetCompositionString(hIMC, 0x800, null, 0);
buf = new StringBuilder(strLen);
int getSize = ImmGetCompositionString(hIMC, 0x800, buf, (uint)strLen);
byte[] by = System.Text.Encoding.Default.GetBytes(buf.ToString());
return System.Text.Encoding.Default.GetString(by, 0, strLen);
}
finally
{
ImmReleaseContext(hwnd, hIMC);
}
}
关于设置我想应该没什么问题,是根据SDK上的方法写的,且在PPC(Pocket PC)下测试过,程序没有问题,只不过到了SmartPhone操作系统下,程序无法接受到WM_IME_STARTCOMPOSITION和WM_IME_ENDCOMPOSITION消息,而且使用ImmGetCompositionString、ImmGetCandidateList、ImmGetConversionList之类的函数都无法的到预期的结果。
期待更多的帮助,谢谢!
pknife>
微软给出一个例子,不过是C++的,不知道有没有帮助,你可以参考一下:
BOOL GetCompositionString( HWND hWnd, LPTSTR *pszCompStr, UINT *cchCompStr )
{
ASSERT(hWnd);
DWORD dwBufLen = NULL;
HIMC hImc = ImmGetContext(hWnd);
if (!hImc)
{
DEBUGMSG(1, (_T("Failed to get handle to current input context./r/n")));
return FALSE;
}
// Determine how much space is required to store the composition string.
if ( (dwBufLen = ImmGetCompositionString( hImc, GCS_COMPSTR, NULL, 0l)) < 0 )
{
DEBUGMSG(1, (_T("No composition string./r/n")));
return FALSE;
}
if ( *cchCompStr < (dwBufLen/sizeof(TCHAR)) + 1 )
{
DEBUGMSG(1, (_T("pszCompStr needs to be at least %i characters large./r/n"),
(dwBufLen/sizeof(TCHAR)) + 1));
*cchCompStr = (dwBufLen/sizeof(TCHAR)) + 1;
return FALSE;
}
ImmGetCompositionString( hImc, GCS_COMPSTR, *pszCompStr, dwBufLen );
(*pszCompStr)[dwBufLen] = NULL;
return TRUE;
}
pcjbird>
通过GCS_COMPSTR似乎只能获得当前按下的键值,却不能得到经过IME转换的结果。
pknife>
GCS_RESULTSTR呢
pcjbird>
GCS_RESULTSTR在SmartPhone下得到的空,在Pocket PC(SIP)下就很正常。。。
我上面的代码就是GCS_RESULTSTR的。
我用Windows CE Remote Spy可以看到WM_IME_STARTCOMPOSITION和WM_IME_ENDCOMPOSITION消息,为什么在应用程序里用GetMessage(out Msg, IntPtr.Zero, 0, 0)获取不到这些消息呢?是被处理掉了吗?最奇怪的是GetMessage(out Msg, IntPtr.Zero, 0, 0)却取到了WM_IME_COMPOSITION消息???
这到底是为啥啊?望高手指教。。。
另外还有个问题,在公司的时候用Windows CE Remote Spy监视窗口消息看不到任何消息,在家里的机子上就可以,一切正常,我看了ce remote spy版本是一样的啊,难道是仿真器的问题,可仿真器也是装的一个版本的!!!真是有点晕了。。。[测试环境:smartphone QVGA WM5.0仿真器]