00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
#include "precomp.h"
00013
#pragma hdrstop
00014
00015
#ifdef HIRO_DEBUG
00016
#define D(x) x
00017
#else
00018 #define D(x)
00019
#endif
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 DWORD WINAPI
ImmProcessKey(
00031 HWND hWnd,
00032 HKL hkl,
00033 UINT uVKey,
00034 LPARAM lParam,
00035 DWORD dwHotKeyID)
00036 {
00037 HIMC hIMC =
ImmGetContext(
hWnd);
00038
PIMEDPI pImeDpi =
ImmLockImeDpi(hkl);
00039
DWORD dwReturn = 0;
00040
#if DBG
00041
if (dwHotKeyID >= IME_KHOTKEY_FIRST && dwHotKeyID <= IME_KHOTKEY_LAST) {
00042 TAGMSG2(DBGTAG_IMM,
"ImmProcessKey: Kor IME Hotkeys should not come here: dwHotKeyID=%x, uVKey=%x", dwHotKeyID, uVKey);
00043 }
00044
#endif
00045
00046
ImmAssert(dwHotKeyID != IME_KHOTKEY_ENGLISH &&
00047 dwHotKeyID != IME_KHOTKEY_SHAPE_TOGGLE &&
00048 dwHotKeyID != IME_KHOTKEY_HANJACONVERT);
00049
00050
00051
00052
00053
if (pImeDpi !=
NULL) {
00054 PINPUTCONTEXT pInputContext =
ImmLockIMC(hIMC);
00055
00056
if (pInputContext !=
NULL) {
00057 BOOLEAN fTruncateWideVK =
FALSE;
00058 BOOLEAN fCallIme =
TRUE;
00059 BOOLEAN fSkipThisKey =
FALSE;
00060
00061
#ifdef LATER
00062
00063
00064
00065
00066
00067
00068
00069
if ((pImeDpi->fdwProperty & IME_PROP_NO_KEYS_ON_CLOSE) &&
00070 !pInputContext->fOpen &&
00071 uVKey != VK_SHIFT &&
00072 uVKey != VK_CONTROL &&
00073 uVKey != VK_CAPITAL &&
00074 uVKey != VK_KANA &&
00075 uVKey != VK_NUMLOCK &&
00076 uVKey != VK_SCROLL) {
00077
00078
if(!(pimc->fdwConvMode & IME_CMODE_HANJACONVERT)) {
00079 fCallIme =
FALSE;
00080 }
00081 }
00082
else
00083
#endif
00084
00085
00086
00087
if ((
BYTE)uVKey == VK_PACKET &&
00088 (pImeDpi->
ImeInfo.fdwProperty & IME_PROP_ACCEPT_WIDE_VKEY) == 0) {
00089
00090
if (pImeDpi->
ImeInfo.fdwProperty & IME_PROP_UNICODE) {
00091
00092
00093
00094
00095 fTruncateWideVK =
TRUE;
00096 }
00097
else {
00098
00099
00100
00101
00102
00103
00104 fCallIme =
FALSE;
00105
if (pInputContext->fOpen) {
00106 fSkipThisKey =
TRUE;
00107 }
00108 }
00109 }
00110
00111
if (fCallIme) {
00112
PBYTE pbKeyState = (
PBYTE)
ImmLocalAlloc(0, 256);
00113
00114
ImmAssert(fSkipThisKey ==
FALSE);
00115
00116
if (pbKeyState !=
NULL) {
00117
if (
GetKeyboardState(pbKeyState)) {
00118
UINT uVKeyIme = uVKey;
00119
if (fTruncateWideVK) {
00120 uVKeyIme &= 0xffff;
00121 }
00122
if ( (*pImeDpi->
pfn.
ImeProcessKey)(hIMC, uVKeyIme, lParam, pbKeyState) ) {
00123
00124
00125
00126
00127
00128 pInputContext->fChgMsg =
TRUE;
00129 pInputContext->uSavedVKey = uVKey;
00130 dwReturn |=
IPHK_PROCESSBYIME;
00131 }
00132 }
00133
ImmLocalFree(pbKeyState);
00134 }
00135 }
00136
else if (fSkipThisKey) {
00137 dwReturn |= IPHK_SKIPTHISKEY;
00138
ImmAssert((dwReturn & (
IPHK_PROCESSBYIME |
IPHK_HOTKEY)) == 0);
00139 }
00140
ImmUnlockIMC(hIMC);
00141 }
00142
ImmUnlockImeDpi(pImeDpi);
00143 }
00144
00145
00146
00147
00148
if (dwHotKeyID != IME_INVALID_HOTKEY &&
HotKeyIDDispatcher(
hWnd, hIMC, hkl, dwHotKeyID)) {
00149
00150
00151
if ((uVKey != VK_KANJI) ||
00152 (dwHotKeyID != IME_JHOTKEY_CLOSE_OPEN)) {
00153 dwReturn |=
IPHK_HOTKEY;
00154 }
00155 }
00156
00157
00158
00159
00160
00161
if (dwReturn &
IPHK_PROCESSBYIME) {
00162
00163
DWORD dwImeCompat =
ImmGetAppCompatFlags(hIMC);
00164
00165
if (dwImeCompat & IMECOMPAT_NOVKPROCESSKEY) {
00166
00167
00168
00169
00170
if ( PRIMARYLANGID(LANGIDFROMLCID(GetSystemDefaultLCID())) == LANG_KOREAN &&
00171 ( (uVKey == VK_PROCESSKEY) || (dwReturn &
IPHK_HOTKEY) ) ) {
00172
ImmReleaseContext(
hWnd, hIMC);
00173
return dwReturn;
00174 }
00175
00176
ImmTranslateMessage(
hWnd, WM_KEYDOWN, VK_PROCESSKEY, lParam);
00177 dwReturn &= ~
IPHK_PROCESSBYIME;
00178 dwReturn |= IPHK_SKIPTHISKEY;
00179 }
00180 }
00181
ImmReleaseContext(
hWnd, hIMC);
00182
00183
return dwReturn;
00184 }
00185
00186 #define TRANSMSGCOUNT 256
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196 BOOL ImmTranslateMessage(
00197 HWND hwnd,
00198 UINT message,
00199 WPARAM wParam,
00200 LPARAM lParam)
00201 {
00202 HIMC hImc;
00203 PINPUTCONTEXT pInputContext;
00204
BOOL fReturn =
FALSE;
00205 HKL hkl;
00206
PIMEDPI pImeDpi =
NULL;
00207
PBYTE pbKeyState;
00208 PTRANSMSG pTransMsg;
00209 PTRANSMSGLIST pTransMsgList;
00210
DWORD dwSize;
00211
UINT uVKey;
00212
INT iNum;
00213
00214 UNREFERENCED_PARAMETER(wParam);
00215
00216
00217
00218
00219
switch (message) {
00220
case WM_KEYDOWN:
00221
case WM_KEYUP:
00222
case WM_SYSKEYDOWN:
00223
case WM_SYSKEYUP:
00224
break;
00225
default:
00226
return FALSE;
00227 }
00228
00229
00230
00231
00232 hImc =
ImmGetContext(hwnd);
00233 pInputContext =
ImmLockIMC(hImc);
00234
if (pInputContext ==
NULL) {
00235
ImmReleaseContext(hwnd, hImc);
00236
return FALSE;
00237 }
00238
00239
00240
00241
00242
if (!pInputContext->fChgMsg) {
00243
00244
if ((iNum=pInputContext->dwNumMsgBuf) != 0) {
00245
00246 pTransMsg = (PTRANSMSG)
ImmLockIMCC(pInputContext->hMsgBuf);
00247
if (pTransMsg !=
NULL) {
00248
ImmPostMessages(hwnd, hImc, iNum, pTransMsg);
00249
ImmUnlockIMCC(pInputContext->hMsgBuf);
00250 fReturn =
TRUE;
00251 }
00252
00253 pInputContext->dwNumMsgBuf = 0;
00254 }
00255
goto ExitITM;
00256 }
00257
00258 pInputContext->fChgMsg =
FALSE;
00259
00260
00261
00262
00263 hkl =
GetKeyboardLayout(
GetWindowThreadProcessId(hwnd,
NULL) );
00264 pImeDpi =
ImmLockImeDpi(hkl);
00265
if (pImeDpi ==
NULL) {
00266 RIPMSG1(RIP_WARNING,
"ImmTranslateMessage pImeDpi is NULL(hkl=%x)", hkl);
00267
goto ExitITM;
00268 }
00269
00270 pbKeyState =
ImmLocalAlloc(0, 256);
00271
if ( pbKeyState ==
NULL ) {
00272 RIPMSG0(RIP_WARNING,
"ImmTranslateMessage out of memory" );
00273
goto ExitITM;
00274 }
00275
00276
if (!
GetKeyboardState(pbKeyState)) {
00277 RIPMSG0(RIP_WARNING,
"ImmTranslateMessage GetKeyboardState() failed" );
00278
ImmLocalFree( pbKeyState );
00279
goto ExitITM;
00280 }
00281
00282
00283
00284
00285 uVKey = pInputContext->uSavedVKey;
00286
00287
if (pImeDpi->
ImeInfo.fdwProperty & IME_PROP_KBD_CHAR_FIRST) {
00288
00289
if (pImeDpi->
ImeInfo.fdwProperty & IME_PROP_UNICODE) {
00290 WCHAR wcTemp;
00291
00292 iNum =
ToUnicode(pInputContext->uSavedVKey,
00293 HIWORD(lParam),
00294 pbKeyState,
00295 &wcTemp,
00296 1,
00297 0);
00298
if (iNum == 1) {
00299
00300
00301
00302
00303
00304 uVKey = (uVKey & 0x00ff) | ((
UINT)wcTemp << 16);
00305 }
00306
00307 }
else {
00308 WORD wTemp = 0;
00309
00310 iNum =
ToAsciiEx(pInputContext->uSavedVKey,
00311 HIWORD(lParam),
00312 pbKeyState,
00313 &wTemp,
00314 0,
00315 hkl);
00316
ImmAssert(iNum <= 2);
00317
if (iNum > 0) {
00318
00319
00320
00321
00322
00323 uVKey = (uVKey & 0x00FF) | ((
UINT)wTemp << 8);
00324
00325
if ((
BYTE)uVKey == VK_PACKET) {
00326
00327
00328
00329
00330
00331
00332
00333
00334
00335
ImmAssert(pImeDpi->
ImeInfo.fdwProperty & IME_PROP_ACCEPT_WIDE_VKEY);
00336 }
00337
else {
00338 uVKey &= 0xffff;
00339 }
00340 }
00341 }
00342 }
00343
00344 dwSize = FIELD_OFFSET(TRANSMSGLIST, TransMsg)
00345 +
TRANSMSGCOUNT *
sizeof(TRANSMSG);
00346
00347 pTransMsgList = (PTRANSMSGLIST)
ImmLocalAlloc(0, dwSize);
00348
00349
if (pTransMsgList ==
NULL) {
00350 RIPMSG0(RIP_WARNING,
"ImmTranslateMessage out of memory" );
00351
ImmLocalFree(pbKeyState);
00352
goto ExitITM;
00353 }
00354
00355 pTransMsgList->uMsgCount =
TRANSMSGCOUNT;
00356 iNum = (*pImeDpi->
pfn.
ImeToAsciiEx)(uVKey,
00357 HIWORD(lParam),
00358 pbKeyState,
00359 pTransMsgList,
00360 0,
00361 hImc);
00362
00363
if (iNum >
TRANSMSGCOUNT) {
00364
00365
00366
00367
00368
00369
00370 pTransMsg = (PTRANSMSG)
ImmLockIMCC(pInputContext->hMsgBuf);
00371
if (pTransMsg !=
NULL) {
00372
ImmPostMessages(hwnd, hImc, iNum, pTransMsg);
00373
ImmUnlockIMCC(pInputContext->hMsgBuf);
00374 }
00375
00376
#ifdef LATER
00377
00378 fReturn =
TRUE;
00379
#endif
00380
00381 }
else if (iNum > 0) {
00382
ImmPostMessages(hwnd, hImc, iNum, &pTransMsgList->TransMsg[0]);
00383 fReturn =
TRUE;
00384 }
00385
00386
ImmLocalFree(pbKeyState);
00387
ImmLocalFree(pTransMsgList);
00388
00389 ExitITM:
00390
ImmUnlockImeDpi(pImeDpi);
00391
ImmUnlockIMC(hImc);
00392
ImmReleaseContext(hwnd, hImc);
00393
00394
return fReturn;
00395 }
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405
00406
00407
VOID
00408 ImmPostMessages(
00409 HWND hWnd,
00410 HIMC hImc,
00411 INT iNum,
00412 PTRANSMSG pTransMsg)
00413 {
00414
INT i;
00415
BOOL fAnsiIME;
00416
PCLIENTIMC pClientImc;
00417 PTRANSMSG pTransMsgTemp, pTransMsgBuf =
NULL;
00418
00419
00420
00421
00422
00423
00424 pClientImc =
ImmLockClientImc(hImc);
00425
if (pClientImc ==
NULL) {
00426 RIPMSG1(RIP_WARNING,
00427
"ImmPostMessages: Invalid hImc %lx.", hImc);
00428
return;
00429 }
00430
00431 fAnsiIME = !
TestICF(pClientImc,
IMCF_UNICODE);
00432
ImmUnlockClientImc(pClientImc);
00433
00434
00435
00436
00437 pTransMsgTemp = pTransMsg;
00438
if (
GetClientInfo()->dwExpWinVer <
VER40) {
00439
DWORD dwLangId = PRIMARYLANGID(
00440 LANGIDFROMLCID(
00441 GetSystemDefaultLCID()));
00442
if ( (dwLangId == LANG_KOREAN &&
TransGetLevel(
hWnd) == 3) ||
00443 dwLangId == LANG_JAPANESE ) {
00444
00445 pTransMsgBuf =
ImmLocalAlloc(0, iNum *
sizeof(TRANSMSG));
00446
if (pTransMsgBuf !=
NULL) {
00447 RtlCopyMemory(pTransMsgBuf, pTransMsg, iNum *
sizeof(TRANSMSG));
00448 iNum =
WINNLSTranslateMessage(iNum,
00449 pTransMsgBuf,
00450 hImc,
00451 fAnsiIME,
00452 dwLangId );
00453 pTransMsgTemp = pTransMsgBuf;
00454 }
00455 }
00456 }
00457
00458
for (i = 0; i < iNum; i++) {
00459
if (fAnsiIME) {
00460 PostMessageA(
hWnd,
00461 pTransMsgTemp->message,
00462 pTransMsgTemp->wParam,
00463 pTransMsgTemp->lParam);
00464 }
else {
00465 PostMessageW(
hWnd,
00466 pTransMsgTemp->message,
00467 pTransMsgTemp->wParam,
00468 pTransMsgTemp->lParam);
00469 }
00470 pTransMsgTemp++;
00471 }
00472
00473
if (pTransMsgBuf !=
NULL) {
00474
ImmLocalFree(pTransMsgBuf);
00475 }
00476 }
00477
00478 UINT WINNLSTranslateMessage(
00479 INT iNum,
00480 PTRANSMSG pTransMsg,
00481 HIMC hImc,
00482 BOOL fAnsi,
00483 DWORD dwLangId )
00484 {
00485 LPINPUTCONTEXT pInputContext;
00486 LPCOMPOSITIONSTRING pCompStr;
00487
UINT uiRet = 0;
00488
00489 pInputContext =
ImmLockIMC(hImc);
00490
if (pInputContext ==
NULL) {
00491
return uiRet;
00492 }
00493
00494 pCompStr = (LPCOMPOSITIONSTRING)
ImmLockIMCC( pInputContext->hCompStr );
00495
00496
if (dwLangId == LANG_KOREAN) {
00497 uiRet =
WINNLSTranslateMessageK((
UINT)iNum,
00498 pTransMsg,
00499 pInputContext,
00500 pCompStr,
00501 fAnsi );
00502 }
else if ( dwLangId == LANG_JAPANESE ) {
00503 uiRet =
WINNLSTranslateMessageJ((
UINT)iNum,
00504 pTransMsg,
00505 pInputContext,
00506 pCompStr,
00507 fAnsi );
00508 }
00509
00510
if (pCompStr !=
NULL) {
00511
ImmUnlockIMCC(pInputContext->hCompStr);
00512 }
00513
ImmUnlockIMC(hImc);
00514
00515
return uiRet;
00516 }
00517