mirror of
https://github.com/atom/atom.git
synced 2026-02-09 22:24:59 -05:00
WIP: Begin introducing multi-keystroke bindings to Keymap
This commit is contained in:
@@ -8,30 +8,39 @@ PEG = require 'pegjs'
|
||||
module.exports =
|
||||
class BindingSet
|
||||
selector: null
|
||||
keystrokeMap: null
|
||||
commandsByKeystrokes: null
|
||||
commandForEvent: null
|
||||
parser: null
|
||||
|
||||
constructor: (@selector, mapOrFunction) ->
|
||||
@parser = PEG.buildParser(fs.read(require.resolve 'keystroke-pattern.pegjs'))
|
||||
@specificity = Specificity(@selector)
|
||||
@keystrokeMap = {}
|
||||
@commandsByKeystrokes = {}
|
||||
|
||||
if _.isFunction(mapOrFunction)
|
||||
@commandForEvent = mapOrFunction
|
||||
else
|
||||
@keystrokeMap = @normalizeKeystrokeMap(mapOrFunction)
|
||||
@commandsByKeystrokes = @normalizeCommandsByKeystrokes(mapOrFunction)
|
||||
@commandForEvent = (event) =>
|
||||
for keystroke, command of @keystrokeMap
|
||||
return command if event.keystroke == keystroke
|
||||
for keystrokes, command of @commandsByKeystrokes
|
||||
return command if event.keystrokes == keystrokes
|
||||
null
|
||||
|
||||
normalizeKeystrokeMap: (keystrokeMap) ->
|
||||
normalizeKeystrokeMap = {}
|
||||
for keystroke, command of keystrokeMap
|
||||
normalizeKeystrokeMap[@normalizeKeystroke(keystroke)] = command
|
||||
matchesKeystrokePrefix: (event) ->
|
||||
for keystrokes, command of @commandsByKeystrokes
|
||||
return true if keystrokes.indexOf(event.keystrokes) == 0
|
||||
false
|
||||
|
||||
normalizeKeystrokeMap
|
||||
normalizeCommandsByKeystrokes: (commandsByKeystrokes) ->
|
||||
normalizedCommandsByKeystrokes = {}
|
||||
for keystrokes, command of commandsByKeystrokes
|
||||
normalizedCommandsByKeystrokes[@normalizeKeystrokes(keystrokes)] = command
|
||||
normalizedCommandsByKeystrokes
|
||||
|
||||
normalizeKeystrokes: (keystrokes) ->
|
||||
normalizedKeystrokes = keystrokes.split(/\s+/).map (keystroke) =>
|
||||
@normalizeKeystroke(keystroke)
|
||||
normalizedKeystrokes.join(' ')
|
||||
|
||||
normalizeKeystroke: (keystroke) ->
|
||||
keys = @parser.parse(keystroke)
|
||||
|
||||
@@ -8,6 +8,7 @@ Specificity = require 'specificity'
|
||||
module.exports =
|
||||
class Keymap
|
||||
bindingSets: null
|
||||
queuedKeystrokes: null
|
||||
|
||||
constructor: ->
|
||||
@bindingSets = []
|
||||
@@ -40,7 +41,8 @@ class Keymap
|
||||
keystrokeMap
|
||||
|
||||
handleKeyEvent: (event) ->
|
||||
event.keystroke = @keystrokeStringForEvent(event)
|
||||
event.keystrokes = @multiKeystrokeStringForEvent(event)
|
||||
@queuedKeystrokes = null
|
||||
currentNode = $(event.target)
|
||||
while currentNode.length
|
||||
candidateBindingSets = @bindingSets.filter (set) -> currentNode.is(set.selector)
|
||||
@@ -52,6 +54,10 @@ class Keymap
|
||||
return false
|
||||
else if command == false
|
||||
return false
|
||||
|
||||
if bindingSet.matchesKeystrokePrefix(event)
|
||||
@queuedKeystrokes = event.keystrokes
|
||||
return false
|
||||
currentNode = currentNode.parent()
|
||||
true
|
||||
|
||||
@@ -60,6 +66,13 @@ class Keymap
|
||||
commandEvent.keyEvent = keyEvent
|
||||
$(keyEvent.target).trigger(commandEvent)
|
||||
|
||||
multiKeystrokeStringForEvent: (event) ->
|
||||
currentKeystroke = @keystrokeStringForEvent(event)
|
||||
if @queuedKeystrokes
|
||||
@queuedKeystrokes + ' ' + currentKeystroke
|
||||
else
|
||||
currentKeystroke
|
||||
|
||||
keystrokeStringForEvent: (event) ->
|
||||
if /^U\+/i.test event.originalEvent.keyIdentifier
|
||||
hexCharCode = event.originalEvent.keyIdentifier.replace(/^U\+/i, '')
|
||||
|
||||
Reference in New Issue
Block a user