1 /*
2 * Copyright (c) 1996, 2015, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
240 m_PendingLeadByte = 0;
241 m_bitsCandType = 0;
242
243 windowMoveLockPosX = 0;
244 windowMoveLockPosY = 0;
245 windowMoveLockPosCX = 0;
246 windowMoveLockPosCY = 0;
247
248 m_hCursorCache = NULL;
249
250 m_bSubclassed = FALSE;
251 m_bPauseDestroy = FALSE;
252
253 m_MessagesProcessing = 0;
254 m_wheelRotationAmount = 0;
255 if (!sm_PrimaryDynamicTableBuilt) {
256 // do it once.
257 AwtComponent::BuildPrimaryDynamicTable();
258 sm_PrimaryDynamicTableBuilt = TRUE;
259 }
260 }
261
262 AwtComponent::~AwtComponent()
263 {
264 DASSERT(AwtToolkit::IsMainThread());
265
266 /* Disconnect all links. */
267 UnlinkObjects();
268
269 /*
270 * All the messages for this component are processed, native
271 * resources are freed, and Java object is not connected to
272 * the native one anymore. So we can safely destroy component's
273 * handle.
274 */
275 DestroyHWnd();
276
277 if (sm_getComponentCache == this) {
278 sm_getComponentCache = NULL;
279 }
2935 {L'`', java_awt_event_KeyEvent_VK_DEAD_GRAVE},
2936 {L'\'', java_awt_event_KeyEvent_VK_DEAD_ACUTE},
2937 {0x00B4, java_awt_event_KeyEvent_VK_DEAD_ACUTE},
2938 {L'^', java_awt_event_KeyEvent_VK_DEAD_CIRCUMFLEX},
2939 {L'~', java_awt_event_KeyEvent_VK_DEAD_TILDE},
2940 {0x02DC, java_awt_event_KeyEvent_VK_DEAD_TILDE},
2941 {0x00AF, java_awt_event_KeyEvent_VK_DEAD_MACRON},
2942 {0x02D8, java_awt_event_KeyEvent_VK_DEAD_BREVE},
2943 {0x02D9, java_awt_event_KeyEvent_VK_DEAD_ABOVEDOT},
2944 {L'"', java_awt_event_KeyEvent_VK_DEAD_DIAERESIS},
2945 {0x00A8, java_awt_event_KeyEvent_VK_DEAD_DIAERESIS},
2946 {0x02DA, java_awt_event_KeyEvent_VK_DEAD_ABOVERING},
2947 {0x02DD, java_awt_event_KeyEvent_VK_DEAD_DOUBLEACUTE},
2948 {0x02C7, java_awt_event_KeyEvent_VK_DEAD_CARON}, // aka hacek
2949 {L',', java_awt_event_KeyEvent_VK_DEAD_CEDILLA},
2950 {0x00B8, java_awt_event_KeyEvent_VK_DEAD_CEDILLA},
2951 {0x02DB, java_awt_event_KeyEvent_VK_DEAD_OGONEK},
2952 {0x037A, java_awt_event_KeyEvent_VK_DEAD_IOTA}, // ASCII ???
2953 {0x309B, java_awt_event_KeyEvent_VK_DEAD_VOICED_SOUND},
2954 {0x309C, java_awt_event_KeyEvent_VK_DEAD_SEMIVOICED_SOUND},
2955 {0,0}
2956 };
2957
2958 // The full map of the current keyboard state including
2959 // windows virtual key, scancode, java virtual key, and unicode
2960 // for this key sans modifiers.
2961 // All but first element may be 0.
2962 // XXX in the update releases this is an addition to the unchanged existing code
2963 struct DynPrimaryKeymapEntry {
2964 UINT wkey;
2965 UINT scancode;
2966 UINT jkey;
2967 WCHAR unicode;
2968 };
2969
2970 static DynPrimaryKeymapEntry dynPrimaryKeymap[256];
2971
2972 void
2973 AwtComponent::InitDynamicKeyMapTable()
2974 {
3427 void* value = transTable.remove(reinterpret_cast<void*>(static_cast<INT_PTR>(wkey)));
3428 if (value != NULL) {
3429 isDeadKey = static_cast<BOOL>(reinterpret_cast<INT_PTR>(deadKeyFlag));
3430 return static_cast<UINT>(reinterpret_cast<INT_PTR>(value));
3431 }
3432 }
3433
3434 // If the windows key is a return, wkey will equal 13 ('\r')
3435 // In this case, we want to return 10 ('\n')
3436 // Since ToAscii would convert VK_RETURN to '\r', we need
3437 // to have a special case here.
3438 if (wkey == VK_RETURN)
3439 return '\n';
3440
3441 // high order bit in keyboardState indicates whether the key is down
3442 static const BYTE KEY_STATE_DOWN = 0x80;
3443 BYTE keyboardState[AwtToolkit::KB_STATE_SIZE];
3444 AwtToolkit::GetKeyboardState(keyboardState);
3445
3446 // apply modifiers to keyboard state if necessary
3447 if (modifiers) {
3448 BOOL shiftIsDown = modifiers & java_awt_event_InputEvent_SHIFT_DOWN_MASK;
3449 BOOL altIsDown = modifiers & java_awt_event_InputEvent_ALT_DOWN_MASK;
3450 BOOL ctrlIsDown = modifiers & java_awt_event_InputEvent_CTRL_DOWN_MASK;
3451
3452 // Windows treats AltGr as Ctrl+Alt
3453 if (modifiers & java_awt_event_InputEvent_ALT_GRAPH_DOWN_MASK) {
3454 altIsDown = TRUE;
3455 ctrlIsDown = TRUE;
3456 }
3457
3458 if (shiftIsDown) {
3459 keyboardState[VK_SHIFT] |= KEY_STATE_DOWN;
3460 }
3461
3462 // fix for 4623376,4737679,4501485,4740906,4708221 (4173679/4122715)
3463 // Here we try to resolve a conflict with ::ToAsciiEx's translating
3464 // ALT+number key combinations. kdm@sarc.spb.su
3465 // yan: Do it for navigation keys only, otherwise some AltGr deadkeys fail.
3466 if( IsNavigationKey(wkey) ) {
3467 keyboardState[VK_MENU] &= ~KEY_STATE_DOWN;
3468 }
3500 TCHAR ch;
3501 short vk;
3502 for (ch = _T('\033'); ch < _T('\040'); ch++) {
3503 vk = ::VkKeyScan(ch);
3504 if (wkey == LOBYTE(vk)) {
3505 UINT shiftState = HIBYTE(vk);
3506 if ((shiftState & _VKS_CTRL_MASK) ||
3507 (!(shiftState & _VKS_SHIFT_MASK)
3508 == !shiftIsDown))
3509 {
3510 keyboardState[VK_CONTROL] |= KEY_STATE_DOWN;
3511 }
3512 break;
3513 }
3514 }
3515 }
3516 } // ctrlIsDown && altIsDown
3517 } // ctrlIsDown
3518 } // modifiers
3519
3520 // instead of creating our own conversion tables, I'll let Win32
3521 // convert the character for me.
3522 WORD wChar[2];
3523 UINT scancode = ::MapVirtualKey(wkey, 0);
3524 int converted = ::ToUnicodeEx(wkey, scancode, keyboardState,
3525 wChar, 2, 0, GetKeyboardLayout());
3526
3527 UINT translation;
3528 BOOL deadKeyFlag = (converted == 2);
3529
3530 // Dead Key
3531 if (converted < 0) {
3532 translation = java_awt_event_KeyEvent_CHAR_UNDEFINED;
3533 } else
3534 // No translation available -- try known conversions or else punt.
3535 if (converted == 0) {
3536 if (wkey == VK_DELETE) {
3537 translation = '\177';
3538 } else
3539 if (wkey >= VK_NUMPAD0 && wkey <= VK_NUMPAD9) {
3540 translation = '0' + wkey - VK_NUMPAD0;
3541 } else {
3542 translation = java_awt_event_KeyEvent_CHAR_UNDEFINED;
3543 }
3544 } else
3545 // the caller expects a Unicode character.
3546 if (converted > 0) {
3547 translation = wChar[0];
3548 }
3549 if (ops == SAVE) {
3550 transTable.put(reinterpret_cast<void*>(static_cast<INT_PTR>(wkey)),
3551 reinterpret_cast<void*>(static_cast<INT_PTR>(translation)));
3665 {
3666 // We will simply create Java events here.
3667 WCHAR unicodeChar = character;
3668 MSG msg;
3669 InitMessage(&msg, WM_IME_CHAR, character,
3670 MAKELPARAM(repCnt, flags));
3671
3672 jint modifiers = GetJavaModifiers();
3673 SendKeyEventToFocusOwner(java_awt_event_KeyEvent_KEY_TYPED,
3674 ::JVM_CurrentTimeMillis(NULL, 0),
3675 java_awt_event_KeyEvent_VK_UNDEFINED,
3676 unicodeChar, modifiers,
3677 java_awt_event_KeyEvent_KEY_LOCATION_UNKNOWN, (jlong)0,
3678 &msg);
3679 return mrConsume;
3680 }
3681
3682 MsgRouting AwtComponent::WmChar(UINT character, UINT repCnt, UINT flags,
3683 BOOL system)
3684 {
3685 // Will only get WmChar messages with DBCS if we create them for
3686 // an Edit class in the WmForwardChar method. These synthesized
3687 // DBCS chars are ok to pass on directly to the default window
3688 // procedure. They've already been filtered through the Java key
3689 // event queue. We will never get the trail byte since the edit
3690 // class will PeekMessage(&msg, hwnd, WM_CHAR, WM_CHAR,
3691 // PM_REMOVE). I would like to be able to pass this character off
3692 // via WM_AWT_FORWARD_BYTE, but the Edit classes don't seem to
3693 // like that.
3694
3695 // We will simply create Java events here.
3696 UINT message = system ? WM_SYSCHAR : WM_CHAR;
3697
3698 // The Alt modifier is reported in the 29th bit of the lParam,
3699 // i.e., it is the 13th bit of `flags' (which is HIWORD(lParam)).
3700 bool alt_is_down = (flags & (1<<13)) != 0;
3701
3702 // Fix for bug 4141621, corrected by fix for bug 6223726: Alt+space doesn't invoke system menu
3703 // We should not pass this particular combination to Java.
3704
|
1 /*
2 * Copyright (c) 1996, 2016, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
240 m_PendingLeadByte = 0;
241 m_bitsCandType = 0;
242
243 windowMoveLockPosX = 0;
244 windowMoveLockPosY = 0;
245 windowMoveLockPosCX = 0;
246 windowMoveLockPosCY = 0;
247
248 m_hCursorCache = NULL;
249
250 m_bSubclassed = FALSE;
251 m_bPauseDestroy = FALSE;
252
253 m_MessagesProcessing = 0;
254 m_wheelRotationAmount = 0;
255 if (!sm_PrimaryDynamicTableBuilt) {
256 // do it once.
257 AwtComponent::BuildPrimaryDynamicTable();
258 sm_PrimaryDynamicTableBuilt = TRUE;
259 }
260
261 deadKeyActive = FALSE;
262 }
263
264 AwtComponent::~AwtComponent()
265 {
266 DASSERT(AwtToolkit::IsMainThread());
267
268 /* Disconnect all links. */
269 UnlinkObjects();
270
271 /*
272 * All the messages for this component are processed, native
273 * resources are freed, and Java object is not connected to
274 * the native one anymore. So we can safely destroy component's
275 * handle.
276 */
277 DestroyHWnd();
278
279 if (sm_getComponentCache == this) {
280 sm_getComponentCache = NULL;
281 }
2937 {L'`', java_awt_event_KeyEvent_VK_DEAD_GRAVE},
2938 {L'\'', java_awt_event_KeyEvent_VK_DEAD_ACUTE},
2939 {0x00B4, java_awt_event_KeyEvent_VK_DEAD_ACUTE},
2940 {L'^', java_awt_event_KeyEvent_VK_DEAD_CIRCUMFLEX},
2941 {L'~', java_awt_event_KeyEvent_VK_DEAD_TILDE},
2942 {0x02DC, java_awt_event_KeyEvent_VK_DEAD_TILDE},
2943 {0x00AF, java_awt_event_KeyEvent_VK_DEAD_MACRON},
2944 {0x02D8, java_awt_event_KeyEvent_VK_DEAD_BREVE},
2945 {0x02D9, java_awt_event_KeyEvent_VK_DEAD_ABOVEDOT},
2946 {L'"', java_awt_event_KeyEvent_VK_DEAD_DIAERESIS},
2947 {0x00A8, java_awt_event_KeyEvent_VK_DEAD_DIAERESIS},
2948 {0x02DA, java_awt_event_KeyEvent_VK_DEAD_ABOVERING},
2949 {0x02DD, java_awt_event_KeyEvent_VK_DEAD_DOUBLEACUTE},
2950 {0x02C7, java_awt_event_KeyEvent_VK_DEAD_CARON}, // aka hacek
2951 {L',', java_awt_event_KeyEvent_VK_DEAD_CEDILLA},
2952 {0x00B8, java_awt_event_KeyEvent_VK_DEAD_CEDILLA},
2953 {0x02DB, java_awt_event_KeyEvent_VK_DEAD_OGONEK},
2954 {0x037A, java_awt_event_KeyEvent_VK_DEAD_IOTA}, // ASCII ???
2955 {0x309B, java_awt_event_KeyEvent_VK_DEAD_VOICED_SOUND},
2956 {0x309C, java_awt_event_KeyEvent_VK_DEAD_SEMIVOICED_SOUND},
2957 {0x0004, java_awt_event_KeyEvent_VK_COMPOSE},
2958 {0,0}
2959 };
2960
2961 // The full map of the current keyboard state including
2962 // windows virtual key, scancode, java virtual key, and unicode
2963 // for this key sans modifiers.
2964 // All but first element may be 0.
2965 // XXX in the update releases this is an addition to the unchanged existing code
2966 struct DynPrimaryKeymapEntry {
2967 UINT wkey;
2968 UINT scancode;
2969 UINT jkey;
2970 WCHAR unicode;
2971 };
2972
2973 static DynPrimaryKeymapEntry dynPrimaryKeymap[256];
2974
2975 void
2976 AwtComponent::InitDynamicKeyMapTable()
2977 {
3430 void* value = transTable.remove(reinterpret_cast<void*>(static_cast<INT_PTR>(wkey)));
3431 if (value != NULL) {
3432 isDeadKey = static_cast<BOOL>(reinterpret_cast<INT_PTR>(deadKeyFlag));
3433 return static_cast<UINT>(reinterpret_cast<INT_PTR>(value));
3434 }
3435 }
3436
3437 // If the windows key is a return, wkey will equal 13 ('\r')
3438 // In this case, we want to return 10 ('\n')
3439 // Since ToAscii would convert VK_RETURN to '\r', we need
3440 // to have a special case here.
3441 if (wkey == VK_RETURN)
3442 return '\n';
3443
3444 // high order bit in keyboardState indicates whether the key is down
3445 static const BYTE KEY_STATE_DOWN = 0x80;
3446 BYTE keyboardState[AwtToolkit::KB_STATE_SIZE];
3447 AwtToolkit::GetKeyboardState(keyboardState);
3448
3449 // apply modifiers to keyboard state if necessary
3450 BOOL shiftIsDown = FALSE;
3451 if (modifiers) {
3452 shiftIsDown = modifiers & java_awt_event_InputEvent_SHIFT_DOWN_MASK;
3453 BOOL altIsDown = modifiers & java_awt_event_InputEvent_ALT_DOWN_MASK;
3454 BOOL ctrlIsDown = modifiers & java_awt_event_InputEvent_CTRL_DOWN_MASK;
3455
3456 // Windows treats AltGr as Ctrl+Alt
3457 if (modifiers & java_awt_event_InputEvent_ALT_GRAPH_DOWN_MASK) {
3458 altIsDown = TRUE;
3459 ctrlIsDown = TRUE;
3460 }
3461
3462 if (shiftIsDown) {
3463 keyboardState[VK_SHIFT] |= KEY_STATE_DOWN;
3464 }
3465
3466 // fix for 4623376,4737679,4501485,4740906,4708221 (4173679/4122715)
3467 // Here we try to resolve a conflict with ::ToAsciiEx's translating
3468 // ALT+number key combinations. kdm@sarc.spb.su
3469 // yan: Do it for navigation keys only, otherwise some AltGr deadkeys fail.
3470 if( IsNavigationKey(wkey) ) {
3471 keyboardState[VK_MENU] &= ~KEY_STATE_DOWN;
3472 }
3504 TCHAR ch;
3505 short vk;
3506 for (ch = _T('\033'); ch < _T('\040'); ch++) {
3507 vk = ::VkKeyScan(ch);
3508 if (wkey == LOBYTE(vk)) {
3509 UINT shiftState = HIBYTE(vk);
3510 if ((shiftState & _VKS_CTRL_MASK) ||
3511 (!(shiftState & _VKS_SHIFT_MASK)
3512 == !shiftIsDown))
3513 {
3514 keyboardState[VK_CONTROL] |= KEY_STATE_DOWN;
3515 }
3516 break;
3517 }
3518 }
3519 }
3520 } // ctrlIsDown && altIsDown
3521 } // ctrlIsDown
3522 } // modifiers
3523
3524 WORD wChar[2];
3525 int converted = 1;
3526 UINT ch = ::MapVirtualKey(wkey, 2);
3527 if (ch & 0x80000000) {
3528 // Dead key which is handled as a normal key
3529 isDeadKey = deadKeyActive = TRUE;
3530 } else if (deadKeyActive) {
3531 // We cannot use ::ToUnicodeEx if dead key is active because this will
3532 // break dead key function
3533 wChar[0] = shiftIsDown ? ch : tolower(ch);
3534 } else {
3535 UINT scancode = ::MapVirtualKey(wkey, 0);
3536 converted = ::ToUnicodeEx(wkey, scancode, keyboardState,
3537 wChar, 2, 0, GetKeyboardLayout());
3538 }
3539
3540 UINT translation;
3541 BOOL deadKeyFlag = (converted == 2);
3542
3543 // Dead Key
3544 if (converted < 0 || wChar[0] == 0 || isDeadKey) {
3545 translation = java_awt_event_KeyEvent_CHAR_UNDEFINED;
3546 } else
3547 // No translation available -- try known conversions or else punt.
3548 if (converted == 0) {
3549 if (wkey == VK_DELETE) {
3550 translation = '\177';
3551 } else
3552 if (wkey >= VK_NUMPAD0 && wkey <= VK_NUMPAD9) {
3553 translation = '0' + wkey - VK_NUMPAD0;
3554 } else {
3555 translation = java_awt_event_KeyEvent_CHAR_UNDEFINED;
3556 }
3557 } else
3558 // the caller expects a Unicode character.
3559 if (converted > 0) {
3560 translation = wChar[0];
3561 }
3562 if (ops == SAVE) {
3563 transTable.put(reinterpret_cast<void*>(static_cast<INT_PTR>(wkey)),
3564 reinterpret_cast<void*>(static_cast<INT_PTR>(translation)));
3678 {
3679 // We will simply create Java events here.
3680 WCHAR unicodeChar = character;
3681 MSG msg;
3682 InitMessage(&msg, WM_IME_CHAR, character,
3683 MAKELPARAM(repCnt, flags));
3684
3685 jint modifiers = GetJavaModifiers();
3686 SendKeyEventToFocusOwner(java_awt_event_KeyEvent_KEY_TYPED,
3687 ::JVM_CurrentTimeMillis(NULL, 0),
3688 java_awt_event_KeyEvent_VK_UNDEFINED,
3689 unicodeChar, modifiers,
3690 java_awt_event_KeyEvent_KEY_LOCATION_UNKNOWN, (jlong)0,
3691 &msg);
3692 return mrConsume;
3693 }
3694
3695 MsgRouting AwtComponent::WmChar(UINT character, UINT repCnt, UINT flags,
3696 BOOL system)
3697 {
3698 deadKeyActive = FALSE;
3699
3700 // Will only get WmChar messages with DBCS if we create them for
3701 // an Edit class in the WmForwardChar method. These synthesized
3702 // DBCS chars are ok to pass on directly to the default window
3703 // procedure. They've already been filtered through the Java key
3704 // event queue. We will never get the trail byte since the edit
3705 // class will PeekMessage(&msg, hwnd, WM_CHAR, WM_CHAR,
3706 // PM_REMOVE). I would like to be able to pass this character off
3707 // via WM_AWT_FORWARD_BYTE, but the Edit classes don't seem to
3708 // like that.
3709
3710 // We will simply create Java events here.
3711 UINT message = system ? WM_SYSCHAR : WM_CHAR;
3712
3713 // The Alt modifier is reported in the 29th bit of the lParam,
3714 // i.e., it is the 13th bit of `flags' (which is HIWORD(lParam)).
3715 bool alt_is_down = (flags & (1<<13)) != 0;
3716
3717 // Fix for bug 4141621, corrected by fix for bug 6223726: Alt+space doesn't invoke system menu
3718 // We should not pass this particular combination to Java.
3719
|