--- old/src/windows/native/sun/windows/awt_Component.h 2012-09-27 16:57:58.330883300 +0400 +++ new/src/windows/native/sun/windows/awt_Component.h 2012-09-27 16:57:57.590789300 +0400 @@ -441,7 +441,7 @@ static jint GetJavaModifiers(); static jint GetButton(int mouseButton); static UINT GetButtonMK(int mouseButton); - static UINT WindowsKeyToJavaKey(UINT windowsKey, UINT modifiers); + static UINT WindowsKeyToJavaKey(UINT windowsKey, UINT modifiers, UINT character, BOOL isDeadKey); static void JavaKeyToWindowsKey(UINT javaKey, UINT *windowsKey, UINT *modifiers, UINT originalWindowsKey); static void UpdateDynPrimaryKeymap(UINT wkey, UINT jkeyLegacy, jint keyLocation, UINT modifiers); @@ -453,7 +453,7 @@ enum TransOps {NONE, LOAD, SAVE}; - UINT WindowsKeyToJavaChar(UINT wkey, UINT modifiers, TransOps ops); + UINT WindowsKeyToJavaChar(UINT wkey, UINT modifiers, TransOps ops, BOOL &isDeadKey); /* routines used for input method support */ void SetInputMethod(jobject im, BOOL useNativeCompWindow); --- old/src/windows/native/sun/windows/awt_Component.cpp 2012-09-27 16:58:03.190000300 +0400 +++ new/src/windows/native/sun/windows/awt_Component.cpp 2012-09-27 16:58:02.222377400 +0400 @@ -3144,7 +3144,8 @@ return; } -UINT AwtComponent::WindowsKeyToJavaKey(UINT windowsKey, UINT modifiers) +UINT AwtComponent::WindowsKeyToJavaKey(UINT windowsKey, UINT modifiers, UINT character, BOOL isDeadKey) + { // Handle the few cases where we need to take the modifier into // consideration for the Java VK code or where we have to take the keyboard @@ -3171,6 +3172,15 @@ break; }; + // check dead key + if (isDeadKey) { + for (int i = 0; charToDeadVKTable[i].c != 0; i++) { + if (charToDeadVKTable[i].c == character) { + return charToDeadVKTable[i].javaKey; + } + } + } + // for the general case, use a bi-directional table for (int i = 0; keyMapTable[i].windowsKey != 0; i++) { if (keyMapTable[i].windowsKey == windowsKey) { @@ -3384,14 +3394,18 @@ } } -UINT AwtComponent::WindowsKeyToJavaChar(UINT wkey, UINT modifiers, TransOps ops) +UINT AwtComponent::WindowsKeyToJavaChar(UINT wkey, UINT modifiers, TransOps ops, BOOL &isDeadKey) { static Hashtable transTable("VKEY translations"); + static Hashtable deadKeyFlagTable("Dead Key Flags"); + isDeadKey = FALSE; // Try to translate using last saved translation if (ops == LOAD) { + void* deadKeyFlag = deadKeyFlagTable.remove(reinterpret_cast(static_cast(wkey))); void* value = transTable.remove(reinterpret_cast(static_cast(wkey))); if (value != NULL) { + isDeadKey = static_cast(reinterpret_cast(deadKeyFlag)); return static_cast(reinterpret_cast(value)); } } @@ -3484,12 +3498,13 @@ // instead of creating our own conversion tables, I'll let Win32 // convert the character for me. - WORD mbChar; + WORD wChar[2]; UINT scancode = ::MapVirtualKey(wkey, 0); - int converted = ::ToAsciiEx(wkey, scancode, keyboardState, - &mbChar, 0, GetKeyboardLayout()); + int converted = ::ToUnicodeEx(wkey, scancode, keyboardState, + wChar, 2, 0, GetKeyboardLayout()); UINT translation; + BOOL deadKeyFlag = (converted == 2); // Dead Key if (converted < 0) { @@ -3508,16 +3523,16 @@ } else // the caller expects a Unicode character. if (converted > 0) { - WCHAR unicodeChar[2]; - VERIFY(::MultiByteToWideChar(GetCodePage(), MB_PRECOMPOSED, - (LPCSTR)&mbChar, 1, unicodeChar, 1)); - - translation = unicodeChar[0]; + translation = wChar[0]; } if (ops == SAVE) { transTable.put(reinterpret_cast(static_cast(wkey)), reinterpret_cast(static_cast(translation))); + deadKeyFlagTable.put(reinterpret_cast(static_cast(wkey)), + reinterpret_cast(static_cast(deadKeyFlag))); } + + isDeadKey = deadKeyFlag; return translation; } @@ -3537,8 +3552,9 @@ UINT modifiers = GetJavaModifiers(); jint keyLocation = GetKeyLocation(wkey, flags); - UINT jkey = WindowsKeyToJavaKey(wkey, modifiers); - UINT character = WindowsKeyToJavaChar(wkey, modifiers, SAVE); + BOOL isDeadKey = FALSE; + UINT character = WindowsKeyToJavaChar(wkey, modifiers, SAVE, isDeadKey); + UINT jkey = WindowsKeyToJavaKey(wkey, modifiers, character, isDeadKey); UpdateDynPrimaryKeymap(wkey, jkey, keyLocation, modifiers); @@ -3579,8 +3595,9 @@ UINT modifiers = GetJavaModifiers(); jint keyLocation = GetKeyLocation(wkey, flags); - UINT jkey = WindowsKeyToJavaKey(wkey, modifiers); - UINT character = WindowsKeyToJavaChar(wkey, modifiers, LOAD); + BOOL isDeadKey = FALSE; + UINT character = WindowsKeyToJavaChar(wkey, modifiers, LOAD, isDeadKey); + UINT jkey = WindowsKeyToJavaKey(wkey, modifiers, character, isDeadKey); UpdateDynPrimaryKeymap(wkey, jkey, keyLocation, modifiers); SendKeyEventToFocusOwner(java_awt_event_KeyEvent_KEY_RELEASED, @@ -5628,7 +5645,8 @@ } } - modifiedChar = p->WindowsKeyToJavaChar(winKey, modifiers, AwtComponent::NONE); + BOOL isDeadKey = FALSE; + modifiedChar = p->WindowsKeyToJavaChar(winKey, modifiers, AwtComponent::NONE, isDeadKey); bCharChanged = (keyChar != modifiedChar); } break; @@ -7166,4 +7184,4 @@ removedDCs = removedDCs->next; delete tmpDCList; } -} +} \ No newline at end of file