Unverified Commit 1b9cab71 authored by Greg Spencer's avatar Greg Spencer Committed by GitHub

Clean up synonyms, key code generation. (#138192)

## Description

This cleans up how synonyms are calculated, and adds a reverse mapping from pseudo keys to the real keys they are synonyms of.

Updates the `layout_goals.json` to include the "Space" key, since that was added in the engine without updating the generation configuration.
parent 5980342e
...@@ -225,35 +225,40 @@ class LogicalKeyboardKey extends KeyboardKey { ...@@ -225,35 +225,40 @@ class LogicalKeyboardKey extends KeyboardKey {
/// Returns a set of pseudo-key synonyms for the given `key`. /// Returns a set of pseudo-key synonyms for the given `key`.
/// ///
/// This allows finding the pseudo-keys that also represents a concrete /// This allows finding the pseudo-keys that also represent a concrete `key`
/// `key` so that a class with a key map can match pseudo-keys as well as the /// so that a class with a key map can match pseudo-keys as well as the actual
/// actual generated keys. /// generated keys.
/// ///
/// The pseudo-keys returned in the set are typically used to represent keys /// Pseudo-keys returned in the set are typically used to represent keys which
/// which appear in multiple places on the keyboard, such as the [shift], /// appear in multiple places on the keyboard, such as the [shift], [alt],
/// [alt], [control], and [meta] keys. The keys in the returned set won't ever /// [control], and [meta] keys. Pseudo-keys in the returned set won't ever be
/// be generated directly, but if a more specific key event is received, then /// generated directly, but if a more specific key event is received, then
/// this set can be used to find the more general pseudo-key. For example, if /// this set can be used to find the more general pseudo-key. For example, if
/// this is a [shiftLeft] key, this accessor will return the set /// this is a [shiftLeft] key, this accessor will return the set
/// `<LogicalKeyboardKey>{ shift }`. /// `<LogicalKeyboardKey>{ shift }`.
Set<LogicalKeyboardKey> get synonyms { Set<LogicalKeyboardKey> get synonyms => _synonyms[this] ?? <LogicalKeyboardKey>{};
final LogicalKeyboardKey? result = _synonyms[this];
return result == null ? <LogicalKeyboardKey>{} : <LogicalKeyboardKey>{result};
}
/// Takes a set of keys, and returns the same set, but with any keys that have /// Takes a set of keys, and returns the same set, but with any keys that have
/// synonyms replaced. /// synonyms replaced.
/// ///
/// It is used, for example, to make sets of keys with members like /// It is used, for example, to take sets of keys with members like
/// [controlRight] and [controlLeft] and convert that set to contain just /// [controlRight] and [controlLeft] and convert that set to contain just
/// [control], so that the question "is any control key down?" can be asked. /// [control], so that the question "is any control key down?" can be asked.
static Set<LogicalKeyboardKey> collapseSynonyms(Set<LogicalKeyboardKey> input) { static Set<LogicalKeyboardKey> collapseSynonyms(Set<LogicalKeyboardKey> input) {
final Set<LogicalKeyboardKey> result = <LogicalKeyboardKey>{}; return input.expand((LogicalKeyboardKey element) {
for (final LogicalKeyboardKey key in input) { return _synonyms[element] ?? <LogicalKeyboardKey>{element};
final LogicalKeyboardKey? synonym = _synonyms[key]; }).toSet();
result.add(synonym ?? key); }
}
return result; /// Returns the given set with any pseudo-keys expanded into their synonyms.
///
/// It is used, for example, to take sets of keys with members like [control]
/// and [shift] and convert that set to contain [controlLeft], [controlRight],
/// [shiftLeft], and [shiftRight].
static Set<LogicalKeyboardKey> expandSynonyms(Set<LogicalKeyboardKey> input) {
return input.expand((LogicalKeyboardKey element) {
return _reverseSynonyms[element] ?? <LogicalKeyboardKey>{element};
}).toSet();
} }
@override @override
...@@ -277,10 +282,14 @@ class LogicalKeyboardKey extends KeyboardKey { ...@@ -277,10 +282,14 @@ class LogicalKeyboardKey extends KeyboardKey {
@@@LOGICAL_KEY_MAP@@@ @@@LOGICAL_KEY_MAP@@@
}; };
// A map of keys to the pseudo-key synonym for that key. Used by getSynonyms. // A map of keys to the pseudo-key synonym for that key.
static final Map<LogicalKeyboardKey, LogicalKeyboardKey> _synonyms = <LogicalKeyboardKey, LogicalKeyboardKey>{ static final Map<LogicalKeyboardKey, Set<LogicalKeyboardKey>> _synonyms = <LogicalKeyboardKey, Set<LogicalKeyboardKey>>{
@@@LOGICAL_KEY_SYNONYMS@@@ }; @@@LOGICAL_KEY_SYNONYMS@@@ };
// A map of pseudo-key to the set of keys that are synonyms for that pseudo-key.
static final Map<LogicalKeyboardKey, Set<LogicalKeyboardKey>> _reverseSynonyms = <LogicalKeyboardKey, Set<LogicalKeyboardKey>>{
@@@LOGICAL_KEY_REVERSE_SYNONYMS@@@ };
static const Map<int, String> _keyLabels = <int, String>{ static const Map<int, String> _keyLabels = <int, String>{
@@@LOGICAL_KEY_KEY_LABELS@@@ @@@LOGICAL_KEY_KEY_LABELS@@@
}; };
......
{ {
"Backquote": false,
"Backslash": false,
"BracketLeft": false,
"BracketRight": false,
"Comma": false,
"Digit0": true,
"Digit1": true,
"Digit2": true,
"Digit3": true,
"Digit4": true,
"Digit5": true,
"Digit6": true,
"Digit7": true,
"Digit8": true,
"Digit9": true,
"Equal": false,
"IntlBackslash": false,
"KeyA": true, "KeyA": true,
"KeyB": true, "KeyB": true,
"KeyC": true, "KeyC": true,
...@@ -25,26 +42,10 @@ ...@@ -25,26 +42,10 @@
"KeyX": true, "KeyX": true,
"KeyY": true, "KeyY": true,
"KeyZ": true, "KeyZ": true,
"Digit1": true,
"Digit2": true,
"Digit3": true,
"Digit4": true,
"Digit5": true,
"Digit6": true,
"Digit7": true,
"Digit8": true,
"Digit9": true,
"Digit0": true,
"Quote": false,
"Comma": false,
"Minus": false, "Minus": false,
"Period": false, "Period": false,
"Slash": false, "Quote": false,
"Semicolon": false, "Semicolon": false,
"Equal": false, "Slash": false,
"BracketLeft": false, "Space": false
"Backslash": false,
"BracketRight": false,
"Backquote": false,
"IntlBackslash": false
} }
...@@ -39,7 +39,7 @@ const NSDictionary* modifierFlagToKeyCode = @{ ...@@ -39,7 +39,7 @@ const NSDictionary* modifierFlagToKeyCode = @{
@@@SPECIAL_KEY_CONSTANTS@@@ @@@SPECIAL_KEY_CONSTANTS@@@
const std::vector<LayoutGoal> layoutGoals = { const std::vector<LayoutGoal> kLayoutGoals = {
@@@LAYOUT_GOALS@@@ @@@LAYOUT_GOALS@@@
}; };
......
...@@ -115,12 +115,22 @@ $otherComments static const LogicalKeyboardKey $constantName = LogicalKeyboardK ...@@ -115,12 +115,22 @@ $otherComments static const LogicalKeyboardKey $constantName = LogicalKeyboardK
for (final SynonymKeyInfo synonymInfo in synonyms.values) { for (final SynonymKeyInfo synonymInfo in synonyms.values) {
for (final LogicalKeyEntry key in synonymInfo.keys) { for (final LogicalKeyEntry key in synonymInfo.keys) {
final LogicalKeyEntry synonym = logicalData.entryByName(synonymInfo.name); final LogicalKeyEntry synonym = logicalData.entryByName(synonymInfo.name);
result.writeln(' ${key.constantName}: ${synonym.constantName},'); result.writeln(' ${key.constantName}: <LogicalKeyboardKey>{${synonym.constantName}},');
} }
} }
return result.toString(); return result.toString();
} }
String get _logicalReverseSynonyms {
final StringBuffer result = StringBuffer();
for (final SynonymKeyInfo synonymInfo in synonyms.values) {
final LogicalKeyEntry synonym = logicalData.entryByName(synonymInfo.name);
final List<String> entries = synonymInfo.keys.map<String>((LogicalKeyEntry entry) => entry.constantName).toList();
result.writeln(' ${synonym.constantName}: <LogicalKeyboardKey>{${entries.join(', ')}},');
}
return result.toString();
}
String get _logicalKeyLabels { String get _logicalKeyLabels {
final OutputLines<int> lines = OutputLines<int>('Logical key labels', behavior: DeduplicateBehavior.kSkip); final OutputLines<int> lines = OutputLines<int>('Logical key labels', behavior: DeduplicateBehavior.kSkip);
for (final LogicalKeyEntry entry in logicalData.entries) { for (final LogicalKeyEntry entry in logicalData.entries) {
...@@ -169,6 +179,7 @@ ${_wrapString(constant.description)} /// ...@@ -169,6 +179,7 @@ ${_wrapString(constant.description)} ///
'LOGICAL_KEY_MAP': _predefinedKeyCodeMap, 'LOGICAL_KEY_MAP': _predefinedKeyCodeMap,
'LOGICAL_KEY_DEFINITIONS': _logicalDefinitions, 'LOGICAL_KEY_DEFINITIONS': _logicalDefinitions,
'LOGICAL_KEY_SYNONYMS': _logicalSynonyms, 'LOGICAL_KEY_SYNONYMS': _logicalSynonyms,
'LOGICAL_KEY_REVERSE_SYNONYMS': _logicalReverseSynonyms,
'LOGICAL_KEY_KEY_LABELS': _logicalKeyLabels, 'LOGICAL_KEY_KEY_LABELS': _logicalKeyLabels,
'PHYSICAL_KEY_MAP': _predefinedHidCodeMap, 'PHYSICAL_KEY_MAP': _predefinedHidCodeMap,
'PHYSICAL_KEY_DEFINITIONS': _physicalDefinitions, 'PHYSICAL_KEY_DEFINITIONS': _physicalDefinitions,
......
...@@ -108,7 +108,7 @@ class MacOSCodeGenerator extends PlatformCodeGenerator { ...@@ -108,7 +108,7 @@ class MacOSCodeGenerator extends PlatformCodeGenerator {
'${mandatory ? 'true' : 'false'}' '${mandatory ? 'true' : 'false'}'
'},'; '},';
lines.add(logicalEntry.value, lines.add(logicalEntry.value,
' ${line.padRight(39)}' ' ${line.padRight(32)}'
'// ${logicalEntry.name}'); '// ${logicalEntry.name}');
}); });
return lines.sortedJoin().trimRight(); return lines.sortedJoin().trimRight();
......
...@@ -79,6 +79,7 @@ void main() { ...@@ -79,6 +79,7 @@ void main() {
expect(output, contains('modifierFlagToKeyCode')); expect(output, contains('modifierFlagToKeyCode'));
expect(output, contains('kCapsLockPhysicalKey')); expect(output, contains('kCapsLockPhysicalKey'));
expect(output, contains('kCapsLockLogicalKey')); expect(output, contains('kCapsLockLogicalKey'));
expect(output, contains('kLayoutGoals'));
checkCommonOutput(output); checkCommonOutput(output);
}); });
test('Generate Keycodes for iOS', () { test('Generate Keycodes for iOS', () {
......
...@@ -225,35 +225,40 @@ class LogicalKeyboardKey extends KeyboardKey { ...@@ -225,35 +225,40 @@ class LogicalKeyboardKey extends KeyboardKey {
/// Returns a set of pseudo-key synonyms for the given `key`. /// Returns a set of pseudo-key synonyms for the given `key`.
/// ///
/// This allows finding the pseudo-keys that also represents a concrete /// This allows finding the pseudo-keys that also represent a concrete `key`
/// `key` so that a class with a key map can match pseudo-keys as well as the /// so that a class with a key map can match pseudo-keys as well as the actual
/// actual generated keys. /// generated keys.
/// ///
/// The pseudo-keys returned in the set are typically used to represent keys /// Pseudo-keys returned in the set are typically used to represent keys which
/// which appear in multiple places on the keyboard, such as the [shift], /// appear in multiple places on the keyboard, such as the [shift], [alt],
/// [alt], [control], and [meta] keys. The keys in the returned set won't ever /// [control], and [meta] keys. Pseudo-keys in the returned set won't ever be
/// be generated directly, but if a more specific key event is received, then /// generated directly, but if a more specific key event is received, then
/// this set can be used to find the more general pseudo-key. For example, if /// this set can be used to find the more general pseudo-key. For example, if
/// this is a [shiftLeft] key, this accessor will return the set /// this is a [shiftLeft] key, this accessor will return the set
/// `<LogicalKeyboardKey>{ shift }`. /// `<LogicalKeyboardKey>{ shift }`.
Set<LogicalKeyboardKey> get synonyms { Set<LogicalKeyboardKey> get synonyms => _synonyms[this] ?? <LogicalKeyboardKey>{};
final LogicalKeyboardKey? result = _synonyms[this];
return result == null ? <LogicalKeyboardKey>{} : <LogicalKeyboardKey>{result};
}
/// Takes a set of keys, and returns the same set, but with any keys that have /// Takes a set of keys, and returns the same set, but with any keys that have
/// synonyms replaced. /// synonyms replaced.
/// ///
/// It is used, for example, to make sets of keys with members like /// It is used, for example, to take sets of keys with members like
/// [controlRight] and [controlLeft] and convert that set to contain just /// [controlRight] and [controlLeft] and convert that set to contain just
/// [control], so that the question "is any control key down?" can be asked. /// [control], so that the question "is any control key down?" can be asked.
static Set<LogicalKeyboardKey> collapseSynonyms(Set<LogicalKeyboardKey> input) { static Set<LogicalKeyboardKey> collapseSynonyms(Set<LogicalKeyboardKey> input) {
final Set<LogicalKeyboardKey> result = <LogicalKeyboardKey>{}; return input.expand((LogicalKeyboardKey element) {
for (final LogicalKeyboardKey key in input) { return _synonyms[element] ?? <LogicalKeyboardKey>{element};
final LogicalKeyboardKey? synonym = _synonyms[key]; }).toSet();
result.add(synonym ?? key); }
}
return result; /// Returns the given set with any pseudo-keys expanded into their synonyms.
///
/// It is used, for example, to take sets of keys with members like [control]
/// and [shift] and convert that set to contain [controlLeft], [controlRight],
/// [shiftLeft], and [shiftRight].
static Set<LogicalKeyboardKey> expandSynonyms(Set<LogicalKeyboardKey> input) {
return input.expand((LogicalKeyboardKey element) {
return _reverseSynonyms[element] ?? <LogicalKeyboardKey>{element};
}).toSet();
} }
@override @override
...@@ -3017,16 +3022,24 @@ class LogicalKeyboardKey extends KeyboardKey { ...@@ -3017,16 +3022,24 @@ class LogicalKeyboardKey extends KeyboardKey {
0x0020000031f: gameButtonZ, 0x0020000031f: gameButtonZ,
}; };
// A map of keys to the pseudo-key synonym for that key. Used by getSynonyms. // A map of keys to the pseudo-key synonym for that key.
static final Map<LogicalKeyboardKey, LogicalKeyboardKey> _synonyms = <LogicalKeyboardKey, LogicalKeyboardKey>{ static final Map<LogicalKeyboardKey, Set<LogicalKeyboardKey>> _synonyms = <LogicalKeyboardKey, Set<LogicalKeyboardKey>>{
shiftLeft: shift, shiftLeft: <LogicalKeyboardKey>{shift},
shiftRight: shift, shiftRight: <LogicalKeyboardKey>{shift},
metaLeft: meta, metaLeft: <LogicalKeyboardKey>{meta},
metaRight: meta, metaRight: <LogicalKeyboardKey>{meta},
altLeft: alt, altLeft: <LogicalKeyboardKey>{alt},
altRight: alt, altRight: <LogicalKeyboardKey>{alt},
controlLeft: control, controlLeft: <LogicalKeyboardKey>{control},
controlRight: control, controlRight: <LogicalKeyboardKey>{control},
};
// A map of pseudo-key to the set of keys that are synonyms for that pseudo-key.
static final Map<LogicalKeyboardKey, Set<LogicalKeyboardKey>> _reverseSynonyms = <LogicalKeyboardKey, Set<LogicalKeyboardKey>>{
shift: <LogicalKeyboardKey>{shiftLeft, shiftRight},
meta: <LogicalKeyboardKey>{metaLeft, metaRight},
alt: <LogicalKeyboardKey>{altLeft, altRight},
control: <LogicalKeyboardKey>{controlLeft, controlRight},
}; };
static const Map<int, String> _keyLabels = <int, String>{ static const Map<int, String> _keyLabels = <int, String>{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment