mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-13 05:15:45 +00:00
Bug 432389 CapsLock and NumLock state should be preferred at KeyTranslate code: r=josh+karl, sr=roc, a=dsicore tests: r+sr=roc
This commit is contained in:
parent
7717a4851b
commit
990c48434e
@ -4147,6 +4147,19 @@ GetScriptFromKeyboardLayout(SInt32 aLayoutID)
|
||||
return smRoman;
|
||||
}
|
||||
|
||||
static PRUint32
|
||||
GetUSLayoutCharFromKeyTranslate(UInt32 aKeyCode, UInt32 aModifiers)
|
||||
{
|
||||
KeyTranslateData kt;
|
||||
Handle handle = ::GetResource('uchr', kKLUSKeyboard); // US keyboard layout
|
||||
if (!handle || !(*handle)) {
|
||||
NS_ERROR("US keyboard layout doesn't have uchr resource");
|
||||
return 0;
|
||||
}
|
||||
UInt32 kbType = 40; // ANSI, don't use actual layout
|
||||
return UCKeyTranslateToUnicode((UCKeyboardLayout*)(*handle), aKeyCode,
|
||||
aModifiers, kbType);
|
||||
}
|
||||
|
||||
- (void) convertCocoaKeyEvent:(NSEvent*)aKeyEvent toGeckoEvent:(nsKeyEvent*)outGeckoEvent
|
||||
{
|
||||
@ -4223,33 +4236,40 @@ GetScriptFromKeyboardLayout(SInt32 aLayoutID)
|
||||
kt.mKchr.mHandle = nsnull;
|
||||
}
|
||||
}
|
||||
PRUint32 unshiftedChar = 0;
|
||||
PRUint32 shiftedChar = 0;
|
||||
PRUint32 unshiftedCmdChar = 0;
|
||||
PRUint32 shiftedCmdChar = 0;
|
||||
|
||||
UInt32 key = [aKeyEvent keyCode];
|
||||
UInt32 mod;
|
||||
|
||||
// normal chars
|
||||
mod = 0;
|
||||
unshiftedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
mod |= shiftKey;
|
||||
shiftedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
UInt32 baseMod = 0;
|
||||
if ([aKeyEvent modifierFlags] & NSAlphaShiftKeyMask)
|
||||
baseMod |= alphaLock;
|
||||
if ([aKeyEvent modifierFlags] & NSNumericPadKeyMask)
|
||||
baseMod |= kEventKeyModifierNumLockMask;
|
||||
|
||||
// with cmd chars
|
||||
mod = cmdKey;
|
||||
unshiftedCmdChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
// normal chars
|
||||
mod = baseMod;
|
||||
PRUint32 unshiftedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
mod |= shiftKey;
|
||||
shiftedCmdChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
PRUint32 shiftedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
|
||||
// with Cmd key
|
||||
// XXX we should remove CapsLock state, that changes from Latin to
|
||||
// Cyrillic characters with Russian layout of 10.4 only when Cmd key
|
||||
// is pressed.
|
||||
mod = (baseMod & ~alphaLock);
|
||||
PRUint32 uncmdedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
PRUint32 uncmdedUSChar = GetUSLayoutCharFromKeyTranslate(key, mod);
|
||||
mod |= cmdKey;
|
||||
PRUint32 cmdedChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
mod |= shiftKey;
|
||||
PRUint32 cmdedShiftChar = GetUniCharFromKeyTranslate(kt, key, mod);
|
||||
|
||||
// Is the keyboard layout changed by Cmd key?
|
||||
// E.g., Arabic, Russian, Hebrew, Greek and Dvorak-QWERTY.
|
||||
PRBool isCmdSwitchLayout = unshiftedChar != unshiftedCmdChar;
|
||||
PRBool isCmdSwitchLayout = uncmdedChar != cmdedChar;
|
||||
// Is the keyboard layout for Latin, but Cmd key switches the layout?
|
||||
// I.e., Dvorak-QWERTY
|
||||
PRBool isDvorakQWERTY = isCmdSwitchLayout &&
|
||||
unshiftedChar && unshiftedChar < 0x7F;
|
||||
PRBool isDvorakQWERTY = isCmdSwitchLayout && kt.mScript == smRoman;
|
||||
|
||||
// If the current keyboard is not Dvorak-QWERTY or Cmd is not pressed,
|
||||
// we should append unshiftedChar and shiftedChar for handling the
|
||||
@ -4259,12 +4279,54 @@ GetScriptFromKeyboardLayout(SInt32 aLayoutID)
|
||||
nsAlternativeCharCode altCharCodes(unshiftedChar, shiftedChar);
|
||||
outGeckoEvent->alternativeCharCodes.AppendElement(altCharCodes);
|
||||
}
|
||||
|
||||
// Cleaning up cmdedShiftChar with CapsLocked characters.
|
||||
if (!isCmdSwitchLayout) {
|
||||
// Don't replace if cmdedChar and cmdedShiftChar are not same.
|
||||
// E.g., Cmd+Shift+SS(eszett) is '/'. But Shift+SS is '?'. Then,
|
||||
// we should send '/' directly and '?' should be sent as alternative.
|
||||
if (shiftedChar && cmdedChar == cmdedShiftChar)
|
||||
cmdedShiftChar = shiftedChar;
|
||||
if (unshiftedChar)
|
||||
cmdedChar = unshiftedChar;
|
||||
} else if (uncmdedUSChar == cmdedChar) {
|
||||
mod = baseMod | shiftKey;
|
||||
PRUint32 ch = GetUSLayoutCharFromKeyTranslate(key, mod);
|
||||
if (ch && cmdedChar == cmdedShiftChar)
|
||||
cmdedShiftChar = ch;
|
||||
ch = GetUSLayoutCharFromKeyTranslate(key, mod & ~shiftKey);
|
||||
if (ch)
|
||||
cmdedChar = ch;
|
||||
}
|
||||
|
||||
// XXX We should do something similar when Control is down (bug 429510).
|
||||
if (outGeckoEvent->isMeta &&
|
||||
!(outGeckoEvent->isControl || outGeckoEvent->isAlt)) {
|
||||
|
||||
// The character to use for charCode.
|
||||
PRUint32 preferredCharCode = 0;
|
||||
preferredCharCode = outGeckoEvent->isShift ? cmdedShiftChar : cmdedChar;
|
||||
|
||||
if (preferredCharCode) {
|
||||
#ifdef DEBUG_KB
|
||||
if (outGeckoEvent->charCode != preferredCharCode) {
|
||||
NSLog(@" charCode replaced: %X(%C) to %X(%C)",
|
||||
outGeckoEvent->charCode,
|
||||
outGeckoEvent->charCode > ' ' ? outGeckoEvent->charCode : ' ',
|
||||
preferredCharCode,
|
||||
preferredCharCode > ' ' ? preferredCharCode : ' ');
|
||||
}
|
||||
#endif
|
||||
outGeckoEvent->charCode = preferredCharCode;
|
||||
}
|
||||
}
|
||||
|
||||
// If the current keyboard layout is switched by the Cmd key,
|
||||
// we should append unshiftedCmdChar and shiftedCmdChar that are
|
||||
// we should append cmdedChar and shiftedCmdChar that are
|
||||
// Latin char for the key. But don't append at Dvorak-QWERTY.
|
||||
if ((unshiftedCmdChar || shiftedCmdChar) &&
|
||||
if ((cmdedChar || cmdedShiftChar) &&
|
||||
isCmdSwitchLayout && !isDvorakQWERTY) {
|
||||
nsAlternativeCharCode altCharCodes(unshiftedCmdChar, shiftedCmdChar);
|
||||
nsAlternativeCharCode altCharCodes(cmdedChar, cmdedShiftChar);
|
||||
outGeckoEvent->alternativeCharCodes.AppendElement(altCharCodes);
|
||||
}
|
||||
}
|
||||
|
@ -192,13 +192,13 @@ function runPressTests()
|
||||
// Command keys
|
||||
testKey({layout:"US", keyCode:0, command:1, chars:"a", unmodifiedChars:"a"},
|
||||
"a");
|
||||
// Shift-cmd gives us the unshifted character
|
||||
// Shift-cmd gives us the shifted character
|
||||
testKey({layout:"US", keyCode:0, command:1, shift:1, chars:"a", unmodifiedChars:"A"},
|
||||
"a");
|
||||
"A");
|
||||
// Ctrl-cmd gives us the unshifted character
|
||||
testKey({layout:"US", keyCode:0, command:1, ctrl:1, chars:"\u0001", unmodifiedChars:"a"},
|
||||
"a");
|
||||
// Alt-cmd gives us the *shifted* character
|
||||
// Alt-cmd gives us the shifted character
|
||||
testKey({layout:"US", keyCode:0, command:1, alt:1, chars:"\u00e5", unmodifiedChars:"a"},
|
||||
"\u00e5");
|
||||
testKey({layout:"US", keyCode:0, command:1, alt:1, shift:1, chars:"\u00c5", unmodifiedChars:"a"},
|
||||
@ -213,13 +213,13 @@ function runPressTests()
|
||||
// Greek command keys
|
||||
testKey({layout:"Greek", keyCode:0, command:1, chars:"a", unmodifiedChars:"\u03b1"},
|
||||
"a");
|
||||
// Shift-cmd gives us the unshifted character
|
||||
// Shift-cmd gives us the shifted character
|
||||
testKey({layout:"Greek", keyCode:0, command:1, shift:1, chars:"a", unmodifiedChars:"\u391"},
|
||||
"a");
|
||||
"A");
|
||||
// Ctrl-cmd gives us the unshifted character
|
||||
testKey({layout:"Greek", keyCode:0, command:1, ctrl:1, chars:"\u0001", unmodifiedChars:"\u03b1"},
|
||||
"a");
|
||||
// Alt-cmd gives us the *shifted* character
|
||||
// Alt-cmd gives us the shifted character
|
||||
testKey({layout:"Greek", keyCode:0, command:1, alt:1, chars:"\u00a8", unmodifiedChars:"\u03b1"},
|
||||
"\u00a8");
|
||||
testKey({layout:"Greek", keyCode:0, command:1, alt:1, shift:1, chars:"\u00b9", unmodifiedChars:"\u0391"},
|
||||
|
Loading…
Reference in New Issue
Block a user