From a1fdd1bebc7c59ce77939cf16908a6ac08110b85 Mon Sep 17 00:00:00 2001 From: nightwing Date: Thu, 2 May 2013 18:11:04 +0400 Subject: [PATCH] allow canceling commands in multi_select mode --- lib/ace/ext/emmet.js | 3 ++- lib/ace/lib/event_emitter.js | 35 ++++++++++++++++++++++++++++++----- lib/ace/multi_select.js | 24 ++++++++++++++---------- lib/ace/snippets.js | 3 +-- 4 files changed, 47 insertions(+), 18 deletions(-) diff --git a/lib/ace/ext/emmet.js b/lib/ace/ext/emmet.js index 552350e4..d5296060 100644 --- a/lib/ace/ext/emmet.js +++ b/lib/ace/ext/emmet.js @@ -339,7 +339,8 @@ for (var command in keymap) { name: "emmet:" + command, action: command, bindKey: keymap[command], - exec: runEmmetCommand + exec: runEmmetCommand, + multiSelectAction: "forEach" }); } diff --git a/lib/ace/lib/event_emitter.js b/lib/ace/lib/event_emitter.js index 39d76f9a..482ae0d4 100644 --- a/lib/ace/lib/event_emitter.js +++ b/lib/ace/lib/event_emitter.js @@ -85,12 +85,37 @@ EventEmitter.once = function(eventName, callback) { EventEmitter.setDefaultHandler = function(eventName, callback) { - this._defaultHandlers = this._defaultHandlers || {}; + var handlers = this._defaultHandlers + if (!handlers) + handlers = this._defaultHandlers = {_disabled_: {}}; - if (this._defaultHandlers[eventName]) - throw new Error("The default handler for '" + eventName + "' is already set"); - - this._defaultHandlers[eventName] = callback; + if (handlers[eventName]) { + var old = handlers[eventName]; + var disabled = handlers._disabled_[eventName]; + if (!disabled) + handlers._disabled_[eventName] = disabled = []; + disabled.push(old); + var i = disabled.indexOf(callback); + if (i != -1) + disabled.splice(i, 1); + } + handlers[eventName] = callback; +}; +EventEmitter.removeDefaultHandler = function(eventName, callback) { + var handlers = this._defaultHandlers + if (!handlers) + return; + var disabled = handlers._disabled_[eventName]; + + if (handlers[eventName] == callback) { + var old = handlers[eventName]; + if (disabled) + this.setDefaultHandler(eventName, disabled.pop()); + } else if (disabled) { + var i = disabled.indexOf(callback); + if (i != -1) + disabled.splice(i, 1); + } }; EventEmitter.on = diff --git a/lib/ace/multi_select.js b/lib/ace/multi_select.js index c54224f6..9d063837 100644 --- a/lib/ace/multi_select.js +++ b/lib/ace/multi_select.js @@ -420,7 +420,7 @@ var Editor = require("./editor").Editor; this.setStyle("ace_multiselect"); this.keyBinding.addKeyboardHandler(commands.keyboardHandler); - this.commands.on("exec", this.$onMultiSelectExec); + this.commands.setDefaultHandler("exec", this.$onMultiSelectExec); this.renderer.updateCursor(); this.renderer.updateBackMarkers(); @@ -434,7 +434,7 @@ var Editor = require("./editor").Editor; this.unsetStyle("ace_multiselect"); this.keyBinding.removeKeyboardHandler(commands.keyboardHandler); - this.commands.removeEventListener("exec", this.$onMultiSelectExec); + this.commands.removeDefaultHandler("exec", this.$onMultiSelectExec); this.renderer.updateCursor(); this.renderer.updateBackMarkers(); }; @@ -445,20 +445,20 @@ var Editor = require("./editor").Editor; if (!editor.multiSelect) return; if (!command.multiSelectAction) { - command.exec(editor, e.args || {}); + var result = command.exec(editor, e.args || {}); editor.multiSelect.addRange(editor.multiSelect.toOrientedRange()); editor.multiSelect.mergeOverlappingRanges(); } else if (command.multiSelectAction == "forEach") { - editor.forEachSelection(command, e.args); + result = editor.forEachSelection(command, e.args); } else if (command.multiSelectAction == "forEachLine") { - editor.forEachSelection(command, e.args, true); + result = editor.forEachSelection(command, e.args, true); } else if (command.multiSelectAction == "single") { editor.exitMultiSelectMode(); - command.exec(editor, e.args || {}); + result = command.exec(editor, e.args || {}); } else { - command.multiSelectAction(editor, e.args || {}); + result = command.multiSelectAction(editor, e.args || {}); } - e.preventDefault(); + return result; }; /** @@ -474,7 +474,8 @@ var Editor = require("./editor").Editor; var session = this.session; var selection = this.selection; var rangeList = selection.rangeList; - + var result; + var reg = selection._eventRegistry; selection._eventRegistry = {}; @@ -487,7 +488,9 @@ var Editor = require("./editor").Editor; } tmpSel.fromOrientedRange(rangeList.ranges[i]); this.selection = session.selection = tmpSel; - cmd.exec(this, args || {}); + var cmdResult = cmd.exec(this, args || {}); + if (!result == undefined) + result = cmdResult; tmpSel.toOrientedRange(rangeList.ranges[i]); } tmpSel.detach(); @@ -499,6 +502,7 @@ var Editor = require("./editor").Editor; this.onCursorChange(); this.onSelectionChange(); + return result; }; /** diff --git a/lib/ace/snippets.js b/lib/ace/snippets.js index eb2a9153..da9533b1 100644 --- a/lib/ace/snippets.js +++ b/lib/ace/snippets.js @@ -760,8 +760,7 @@ var TabstopManager = function(editor) { "Esc": function(ed) { ed.tabstopManager.detach(); }, - // todo multiselectExec doesn't handle command return values - "!Return": function(ed) { + "Return": function(ed) { //ed.tabstopManager.tabNext(1); return false; }