Commit 2e59be50 authored by Arnaud Fontaine's avatar Arnaud Fontaine

ZODB Components: Add Ace Editor settings menu (Alt+p) to set up keybinding styles for example.

parent 72a35a09
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts76362800.02</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ext-settings_menu.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/* ***** BEGIN LICENSE BLOCK *****\n
* Distributed under the BSD license:\n
*\n
* Copyright (c) 2013 Matthew Christopher Kastor-Inare III, Atropa Inc. Intl\n
* All rights reserved.\n
*\n
* Contributed to Ajax.org under the BSD license.\n
*\n
* Redistribution and use in source and binary forms, with or without\n
* modification, are permitted provided that the following conditions are met:\n
* * Redistributions of source code must retain the above copyright\n
* notice, this list of conditions and the following disclaimer.\n
* * Redistributions in binary form must reproduce the above copyright\n
* notice, this list of conditions and the following disclaimer in the\n
* documentation and/or other materials provided with the distribution.\n
* * Neither the name of Ajax.org B.V. nor the\n
* names of its contributors may be used to endorse or promote products\n
* derived from this software without specific prior written permission.\n
*\n
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND\n
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n
* DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY\n
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n
*\n
* ***** END LICENSE BLOCK ***** */\n
\n
define(\'ace/ext/settings_menu\', [\'require\', \'exports\', \'module\' , \'ace/ext/menu_tools/generate_settings_menu\', \'ace/ext/menu_tools/overlay_page\', \'ace/editor\'], function(require, exports, module) {\n
\n
var generateSettingsMenu = require(\'./menu_tools/generate_settings_menu\').generateSettingsMenu;\n
var overlayPage = require(\'./menu_tools/overlay_page\').overlayPage;\n
function showSettingsMenu(editor) {\n
var sm = document.getElementById(\'ace_settingsmenu\');\n
if (!sm) \n
overlayPage(editor, generateSettingsMenu(editor), \'0\', \'0\', \'0\');\n
}\n
module.exports.init = function(editor) {\n
var Editor = require("ace/editor").Editor;\n
Editor.prototype.showSettingsMenu = function() {\n
showSettingsMenu(this);\n
};\n
};\n
});\n
\n
define(\'ace/ext/menu_tools/generate_settings_menu\', [\'require\', \'exports\', \'module\' , \'ace/ext/menu_tools/element_generator\', \'ace/ext/menu_tools/add_editor_menu_options\', \'ace/ext/menu_tools/get_set_functions\'], function(require, exports, module) {\n
\n
var egen = require(\'./element_generator\');\n
var addEditorMenuOptions = require(\'./add_editor_menu_options\').addEditorMenuOptions;\n
var getSetFunctions = require(\'./get_set_functions\').getSetFunctions;\n
module.exports.generateSettingsMenu = function generateSettingsMenu (editor) {\n
var elements = [];\n
function cleanupElementsList() {\n
elements.sort(function(a, b) {\n
var x = a.getAttribute(\'contains\');\n
var y = b.getAttribute(\'contains\');\n
return x.localeCompare(y);\n
});\n
}\n
function wrapElements() {\n
var topmenu = document.createElement(\'div\');\n
topmenu.setAttribute(\'id\', \'ace_settingsmenu\');\n
elements.forEach(function(element) {\n
topmenu.appendChild(element);\n
});\n
return topmenu;\n
}\n
function createNewEntry(obj, clss, item, val) {\n
var el;\n
var div = document.createElement(\'div\');\n
div.setAttribute(\'contains\', item);\n
div.setAttribute(\'class\', \'ace_optionsMenuEntry\');\n
div.setAttribute(\'style\', \'clear: both;\');\n
\n
div.appendChild(egen.createLabel(\n
item.replace(/^set/, \'\').replace(/([A-Z])/g, \' $1\').trim(),\n
item\n
));\n
\n
if (Array.isArray(val)) {\n
el = egen.createSelection(item, val, clss);\n
el.addEventListener(\'change\', function(e) {\n
try{\n
editor.menuOptions[e.target.id].forEach(function(x) {\n
if(x.textContent !== e.target.textContent) {\n
delete x.selected;\n
}\n
});\n
obj[e.target.id](e.target.value);\n
} catch (err) {\n
throw new Error(err);\n
}\n
});\n
} else if(typeof val === \'boolean\') {\n
el = egen.createCheckbox(item, val, clss);\n
el.addEventListener(\'change\', function(e) {\n
try{\n
obj[e.target.id](!!e.target.checked);\n
} catch (err) {\n
throw new Error(err);\n
}\n
});\n
} else {\n
el = egen.createInput(item, val, clss);\n
el.addEventListener(\'change\', function(e) {\n
try{\n
if(e.target.value === \'true\') {\n
obj[e.target.id](true);\n
} else if(e.target.value === \'false\') {\n
obj[e.target.id](false);\n
} else {\n
obj[e.target.id](e.target.value);\n
}\n
} catch (err) {\n
throw new Error(err);\n
}\n
});\n
}\n
el.style.cssText = \'float:right;\';\n
div.appendChild(el);\n
return div;\n
}\n
function makeDropdown(item, esr, clss, fn) {\n
var val = editor.menuOptions[item];\n
var currentVal = esr[fn]();\n
if (typeof currentVal == \'object\')\n
currentVal = currentVal.$id;\n
val.forEach(function(valuex) {\n
if (valuex.value === currentVal)\n
valuex.selected = \'selected\';\n
});\n
return createNewEntry(esr, clss, item, val);\n
}\n
function handleSet(setObj) {\n
var item = setObj.functionName;\n
var esr = setObj.parentObj;\n
var clss = setObj.parentName;\n
var val;\n
var fn = item.replace(/^set/, \'get\');\n
if(editor.menuOptions[item] !== undefined) {\n
elements.push(makeDropdown(item, esr, clss, fn));\n
} else if(typeof esr[fn] === \'function\') {\n
try {\n
val = esr[fn]();\n
if(typeof val === \'object\') {\n
val = val.$id;\n
}\n
elements.push(\n
createNewEntry(esr, clss, item, val)\n
);\n
} catch (e) {\n
}\n
}\n
}\n
addEditorMenuOptions(editor);\n
getSetFunctions(editor).forEach(function(setObj) {\n
handleSet(setObj);\n
});\n
cleanupElementsList();\n
return wrapElements();\n
};\n
\n
});\n
\n
define(\'ace/ext/menu_tools/element_generator\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
module.exports.createOption = function createOption (obj) {\n
var attribute;\n
var el = document.createElement(\'option\');\n
for(attribute in obj) {\n
if(obj.hasOwnProperty(attribute)) {\n
if(attribute === \'selected\') {\n
el.setAttribute(attribute, obj[attribute]);\n
} else {\n
el[attribute] = obj[attribute];\n
}\n
}\n
}\n
return el;\n
};\n
module.exports.createCheckbox = function createCheckbox (id, checked, clss) {\n
var el = document.createElement(\'input\');\n
el.setAttribute(\'type\', \'checkbox\');\n
el.setAttribute(\'id\', id);\n
el.setAttribute(\'name\', id);\n
el.setAttribute(\'value\', checked);\n
el.setAttribute(\'class\', clss);\n
if(checked) {\n
el.setAttribute(\'checked\', \'checked\');\n
}\n
return el;\n
};\n
module.exports.createInput = function createInput (id, value, clss) {\n
var el = document.createElement(\'input\');\n
el.setAttribute(\'type\', \'text\');\n
el.setAttribute(\'id\', id);\n
el.setAttribute(\'name\', id);\n
el.setAttribute(\'value\', value);\n
el.setAttribute(\'class\', clss);\n
return el;\n
};\n
module.exports.createLabel = function createLabel (text, labelFor) {\n
var el = document.createElement(\'label\');\n
el.setAttribute(\'for\', labelFor);\n
el.textContent = text;\n
return el;\n
};\n
module.exports.createSelection = function createSelection (id, values, clss) {\n
var el = document.createElement(\'select\');\n
el.setAttribute(\'id\', id);\n
el.setAttribute(\'name\', id);\n
el.setAttribute(\'class\', clss);\n
values.forEach(function(item) {\n
el.appendChild(module.exports.createOption(item));\n
});\n
return el;\n
};\n
\n
});\n
\n
define(\'ace/ext/menu_tools/add_editor_menu_options\', [\'require\', \'exports\', \'module\' , \'ace/ext/modelist\', \'ace/ext/themelist\'], function(require, exports, module) {\n
module.exports.addEditorMenuOptions = function addEditorMenuOptions (editor) {\n
var modelist = require(\'../modelist\');\n
var themelist = require(\'../themelist\');\n
editor.menuOptions = {\n
"setNewLineMode" : [{\n
"textContent" : "unix",\n
"value" : "unix"\n
}, {\n
"textContent" : "windows",\n
"value" : "windows"\n
}, {\n
"textContent" : "auto",\n
"value" : "auto"\n
}],\n
"setTheme" : [],\n
"setMode" : [],\n
"setKeyboardHandler": [{\n
"textContent" : "ace",\n
"value" : ""\n
}, {\n
"textContent" : "vim",\n
"value" : "ace/keyboard/vim"\n
}, {\n
"textContent" : "emacs",\n
"value" : "ace/keyboard/emacs"\n
}]\n
};\n
\n
editor.menuOptions.setTheme = themelist.themes.map(function(theme) {\n
return {\n
\'textContent\' : theme.desc,\n
\'value\' : theme.theme\n
};\n
});\n
\n
editor.menuOptions.setMode = modelist.modes.map(function(mode) {\n
return {\n
\'textContent\' : mode.name,\n
\'value\' : mode.mode\n
};\n
});\n
};\n
\n
\n
});define(\'ace/ext/modelist\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
\n
\n
var modes = [];\n
function getModeForPath(path) {\n
var mode = modesByName.text;\n
var fileName = path.split(/[\\/\\\\]/).pop();\n
for (var i = 0; i < modes.length; i++) {\n
if (modes[i].supportsFile(fileName)) {\n
mode = modes[i];\n
break;\n
}\n
}\n
return mode;\n
}\n
\n
var Mode = function(name, caption, extensions) {\n
this.name = name;\n
this.caption = caption;\n
this.mode = "ace/mode/" + name;\n
this.extensions = extensions;\n
if (/\\^/.test(extensions)) {\n
var re = extensions.replace(/\\|(\\^)?/g, function(a, b){\n
return "$|" + (b ? "^" : "^.*\\\\.");\n
}) + "$";\n
} else {\n
var re = "^.*\\\\.(" + extensions + ")$";\n
}\n
\n
this.extRe = new RegExp(re, "gi");\n
};\n
\n
Mode.prototype.supportsFile = function(filename) {\n
return filename.match(this.extRe);\n
};\n
var supportedModes = {\n
ABAP: ["abap"],\n
ADA: ["ada|adb"],\n
ActionScript:["as"],\n
AsciiDoc: ["asciidoc"],\n
Assembly_x86:["asm"],\n
AutoHotKey: ["ahk"],\n
BatchFile: ["bat|cmd"],\n
C9Search: ["c9search_results"],\n
C_Cpp: ["c|cc|cpp|cxx|h|hh|hpp"],\n
Clojure: ["clj"],\n
Cobol: ["^CBL|COB"],\n
coffee: ["^Cakefile|coffee|cf|cson"],\n
ColdFusion: ["cfm"],\n
CSharp: ["cs"],\n
CSS: ["css"],\n
Curly: ["curly"],\n
D: ["d|di"],\n
Dart: ["dart"],\n
Diff: ["diff|patch"],\n
Dot: ["dot"],\n
Erlang: ["erl|hrl"],\n
EJS: ["ejs"],\n
Forth: ["frt|fs|ldr"],\n
FreeMarker: ["ftl"],\n
Glsl: ["glsl|frag|vert"],\n
golang: ["go"],\n
Groovy: ["groovy"],\n
HAML: ["haml"],\n
Haskell: ["hs"],\n
haXe: ["hx"],\n
HTML: ["htm|html|xhtml"],\n
HTML_Ruby: ["erb|rhtml|html.erb"],\n
Ini: ["Ini|conf"],\n
Jade: ["jade"],\n
Java: ["java"],\n
JavaScript: ["js"],\n
JSON: ["json"],\n
JSONiq: ["jq"],\n
JSP: ["jsp"],\n
JSX: ["jsx"],\n
Julia: ["jl"],\n
LaTeX: ["latex|tex|ltx|bib"],\n
LESS: ["less"],\n
Liquid: ["liquid"],\n
Lisp: ["lisp"],\n
LiveScript: ["ls"],\n
LogiQL: ["logic|lql"],\n
LSL: ["lsl"],\n
Lua: ["lua"],\n
LuaPage: ["lp"],\n
Lucene: ["lucene"],\n
Makefile: ["^GNUmakefile|^makefile|^Makefile|^OCamlMakefile|make"],\n
MATLAB: ["matlab"],\n
Markdown: ["md|markdown"],\n
MySQL: ["mysql"],\n
MUSHCode: ["mc|mush"],\n
ObjectiveC: ["m|mm"],\n
OCaml: ["ml|mli"],\n
Pascal: ["pas|p"],\n
Perl: ["pl|pm"],\n
pgSQL: ["pgsql"],\n
PHP: ["php|phtml"],\n
Powershell: ["ps1"],\n
Prolog: ["plg|prolog"],\n
Properties: ["properties"],\n
Python: ["py"],\n
R: ["r"],\n
RDoc: ["Rd"],\n
RHTML: ["Rhtml"],\n
Ruby: ["ru|gemspec|rake|rb"],\n
Rust: ["rs"],\n
SASS: ["sass"],\n
SCAD: ["scad"],\n
Scala: ["scala"],\n
Scheme: ["scm|rkt"],\n
SCSS: ["scss"],\n
SH: ["sh|bash"],\n
snippets: ["snippets"],\n
SQL: ["sql"],\n
Stylus: ["styl|stylus"],\n
SVG: ["svg"],\n
Tcl: ["tcl"],\n
Tex: ["tex"],\n
Text: ["txt"],\n
Textile: ["textile"],\n
Toml: ["toml"],\n
Twig: ["twig"],\n
Typescript: ["typescript|ts|str"],\n
VBScript: ["vbs"],\n
Velocity: ["vm"],\n
XML: ["xml|rdf|rss|wsdl|xslt|atom|mathml|mml|xul|xbl"],\n
XQuery: ["xq"],\n
YAML: ["yaml"]\n
};\n
\n
var nameOverrides = {\n
ObjectiveC: "Objective-C",\n
CSharp: "C#",\n
golang: "Go",\n
C_Cpp: "C/C++",\n
coffee: "CoffeeScript",\n
HTML_Ruby: "HTML (Ruby)"\n
};\n
var modesByName = {};\n
for (var name in supportedModes) {\n
var data = supportedModes[name];\n
var displayName = nameOverrides[name] || name;\n
var filename = name.toLowerCase();\n
var mode = new Mode(filename, displayName, data[0]);\n
modesByName[filename] = mode;\n
modes.push(mode);\n
}\n
\n
module.exports = {\n
getModeForPath: getModeForPath,\n
modes: modes,\n
modesByName: modesByName\n
};\n
\n
});\n
\n
define(\'ace/ext/themelist\', [\'require\', \'exports\', \'module\' , \'ace/ext/themelist_utils/themes\'], function(require, exports, module) {\n
module.exports.themes = require(\'ace/ext/themelist_utils/themes\').themes;\n
module.exports.ThemeDescription = function(name) {\n
this.name = name;\n
this.desc = name.split(\'_\'\n
).map(\n
function(namePart) {\n
return namePart[0].toUpperCase() + namePart.slice(1);\n
}\n
).join(\' \');\n
this.theme = "ace/theme/" + name;\n
};\n
\n
module.exports.themesByName = {};\n
\n
module.exports.themes = module.exports.themes.map(function(name) {\n
module.exports.themesByName[name] = new module.exports.ThemeDescription(name);\n
return module.exports.themesByName[name];\n
});\n
\n
});\n
\n
define(\'ace/ext/themelist_utils/themes\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
\n
module.exports.themes = [\n
"ambiance",\n
"chaos",\n
"chrome",\n
"clouds",\n
"clouds_midnight",\n
"cobalt",\n
"crimson_editor",\n
"dawn",\n
"dreamweaver",\n
"eclipse",\n
"github",\n
"idle_fingers",\n
"kr_theme",\n
"merbivore",\n
"merbivore_soft",\n
"monokai",\n
"mono_industrial",\n
"pastel_on_dark",\n
"solarized_dark",\n
"solarized_light",\n
"terminal",\n
"textmate",\n
"tomorrow",\n
"tomorrow_night",\n
"tomorrow_night_blue",\n
"tomorrow_night_bright",\n
"tomorrow_night_eighties",\n
"twilight",\n
"vibrant_ink",\n
"xcode"\n
];\n
\n
});\n
\n
define(\'ace/ext/menu_tools/get_set_functions\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
module.exports.getSetFunctions = function getSetFunctions (editor) {\n
var out = [];\n
var my = {\n
\'editor\' : editor,\n
\'session\' : editor.session,\n
\'renderer\' : editor.renderer\n
};\n
var opts = [];\n
var skip = [\n
\'setOption\',\n
\'setUndoManager\',\n
\'setDocument\',\n
\'setValue\',\n
\'setBreakpoints\',\n
\'setScrollTop\',\n
\'setScrollLeft\',\n
\'setSelectionStyle\',\n
\'setWrapLimitRange\'\n
];\n
[\'renderer\', \'session\', \'editor\'].forEach(function(esra) {\n
var esr = my[esra];\n
var clss = esra;\n
for(var fn in esr) {\n
if(skip.indexOf(fn) === -1) {\n
if(/^set/.test(fn) && opts.indexOf(fn) === -1) {\n
opts.push(fn);\n
out.push({\n
\'functionName\' : fn,\n
\'parentObj\' : esr,\n
\'parentName\' : clss\n
});\n
}\n
}\n
}\n
});\n
return out;\n
};\n
\n
});\n
\n
define(\'ace/ext/menu_tools/overlay_page\', [\'require\', \'exports\', \'module\' , \'ace/lib/dom\'], function(require, exports, module) {\n
\n
var dom = require("../../lib/dom");\n
var cssText = "#ace_settingsmenu, #kbshortcutmenu {\\\n
background-color: #F7F7F7;\\\n
color: black;\\\n
box-shadow: -5px 4px 5px rgba(126, 126, 126, 0.55);\\\n
padding: 1em 0.5em 2em 1em;\\\n
overflow: auto;\\\n
position: absolute;\\\n
margin: 0;\\\n
bottom: 0;\\\n
right: 0;\\\n
top: 0;\\\n
z-index: 9991;\\\n
cursor: default;\\\n
}\\\n
.ace_dark #ace_settingsmenu, .ace_dark #kbshortcutmenu {\\\n
box-shadow: -20px 10px 25px rgba(126, 126, 126, 0.25);\\\n
background-color: rgba(255, 255, 255, 0.6);\\\n
color: black;\\\n
}\\\n
.ace_optionsMenuEntry:hover {\\\n
background-color: rgba(100, 100, 100, 0.1);\\\n
-webkit-transition: all 0.5s;\\\n
transition: all 0.3s\\\n
}\\\n
.ace_closeButton {\\\n
background: rgba(245, 146, 146, 0.5);\\\n
border: 1px solid #F48A8A;\\\n
border-radius: 50%;\\\n
padding: 7px;\\\n
position: absolute;\\\n
right: -8px;\\\n
top: -8px;\\\n
z-index: 1000;\\\n
}\\\n
.ace_closeButton{\\\n
background: rgba(245, 146, 146, 0.9);\\\n
}\\\n
.ace_optionsMenuKey {\\\n
color: darkslateblue;\\\n
font-weight: bold;\\\n
}\\\n
.ace_optionsMenuCommand {\\\n
color: darkcyan;\\\n
font-weight: normal;\\\n
}";\n
dom.importCssString(cssText);\n
module.exports.overlayPage = function overlayPage(editor, contentElement, top, right, bottom, left) {\n
top = top ? \'top: \' + top + \';\' : \'\';\n
bottom = bottom ? \'bottom: \' + bottom + \';\' : \'\';\n
right = right ? \'right: \' + right + \';\' : \'\';\n
left = left ? \'left: \' + left + \';\' : \'\';\n
\n
var closer = document.createElement(\'div\');\n
var contentContainer = document.createElement(\'div\');\n
\n
function documentEscListener(e) {\n
if (e.keyCode === 27) {\n
closer.click();\n
}\n
}\n
\n
closer.style.cssText = \'margin: 0; padding: 0; \' +\n
\'position: fixed; top:0; bottom:0; left:0; right:0;\' +\n
\'z-index: 9990; \' +\n
\'background-color: rgba(0, 0, 0, 0.3);\';\n
closer.addEventListener(\'click\', function() {\n
document.removeEventListener(\'keydown\', documentEscListener);\n
closer.parentNode.removeChild(closer);\n
editor.focus();\n
closer = null;\n
});\n
document.addEventListener(\'keydown\', documentEscListener);\n
\n
contentContainer.style.cssText = top + right + bottom + left;\n
contentContainer.addEventListener(\'click\', function(e) {\n
e.stopPropagation();\n
});\n
\n
var wrapper = dom.createElement("div");\n
wrapper.style.position = "relative";\n
\n
var closeButton = dom.createElement("div");\n
closeButton.className = "ace_closeButton";\n
closeButton.addEventListener(\'click\', function() {\n
closer.click();\n
});\n
\n
wrapper.appendChild(closeButton);\n
contentContainer.appendChild(wrapper);\n
\n
contentContainer.appendChild(contentElement);\n
closer.appendChild(contentContainer);\n
document.body.appendChild(closer);\n
editor.blur();\n
};\n
\n
});
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>19778</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts76363578.4</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>keybinding-emacs.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/* ***** BEGIN LICENSE BLOCK *****\n
* Distributed under the BSD license:\n
*\n
* Copyright (c) 2010, Ajax.org B.V.\n
* All rights reserved.\n
*\n
* Redistribution and use in source and binary forms, with or without\n
* modification, are permitted provided that the following conditions are met:\n
* * Redistributions of source code must retain the above copyright\n
* notice, this list of conditions and the following disclaimer.\n
* * Redistributions in binary form must reproduce the above copyright\n
* notice, this list of conditions and the following disclaimer in the\n
* documentation and/or other materials provided with the distribution.\n
* * Neither the name of Ajax.org B.V. nor the\n
* names of its contributors may be used to endorse or promote products\n
* derived from this software without specific prior written permission.\n
*\n
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND\n
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n
* DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY\n
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n
*\n
* ***** END LICENSE BLOCK ***** */\n
\n
define(\'ace/keyboard/emacs\', [\'require\', \'exports\', \'module\' , \'ace/lib/dom\', \'ace/incremental_search\', \'ace/commands/incremental_search_commands\', \'ace/keyboard/hash_handler\', \'ace/lib/keys\'], function(require, exports, module) {\n
\n
\n
var dom = require("../lib/dom");\n
require("../incremental_search");\n
var iSearchCommandModule = require("../commands/incremental_search_commands");\n
\n
\n
var screenToTextBlockCoordinates = function(x, y) {\n
var canvasPos = this.scroller.getBoundingClientRect();\n
\n
var col = Math.floor(\n
(x + this.scrollLeft - canvasPos.left - this.$padding) / this.characterWidth\n
);\n
var row = Math.floor(\n
(y + this.scrollTop - canvasPos.top) / this.lineHeight\n
);\n
\n
return this.session.screenToDocumentPosition(row, col);\n
};\n
\n
var HashHandler = require("./hash_handler").HashHandler;\n
exports.handler = new HashHandler();\n
\n
exports.handler.isEmacs = true;\n
exports.handler.$id = "ace/keyboard/emacs";\n
\n
var initialized = false;\n
var $formerLongWords;\n
var $formerLineStart;\n
\n
exports.handler.attach = function(editor) {\n
if (!initialized) {\n
initialized = true;\n
dom.importCssString(\'\\\n
.emacs-mode .ace_cursor{\\\n
border: 2px rgba(50,250,50,0.8) solid!important;\\\n
-moz-box-sizing: border-box!important;\\\n
-webkit-box-sizing: border-box!important;\\\n
box-sizing: border-box!important;\\\n
background-color: rgba(0,250,0,0.9);\\\n
opacity: 0.5;\\\n
}\\\n
.emacs-mode .ace_cursor.ace_hidden{\\\n
opacity: 1;\\\n
background-color: transparent;\\\n
}\\\n
.emacs-mode .ace_overwrite-cursors .ace_cursor {\\\n
opacity: 1;\\\n
background-color: transparent;\\\n
border-width: 0 0 2px 2px !important;\\\n
}\\\n
.emacs-mode .ace_text-layer {\\\n
z-index: 4\\\n
}\\\n
.emacs-mode .ace_cursor-layer {\\\n
z-index: 2\\\n
}\', \'emacsMode\'\n
);\n
}\n
$formerLongWords = editor.session.$selectLongWords;\n
editor.session.$selectLongWords = true;\n
$formerLineStart = editor.session.$useEmacsStyleLineStart;\n
editor.session.$useEmacsStyleLineStart = true;\n
\n
editor.session.$emacsMark = null; // the active mark\n
editor.session.$emacsMarkRing = editor.session.$emacsMarkRing || [];\n
\n
editor.emacsMark = function() {\n
return this.session.$emacsMark;\n
}\n
\n
editor.setEmacsMark = function(p) {\n
this.session.$emacsMark = p;\n
}\n
\n
editor.pushEmacsMark = function(p, activate) {\n
var prevMark = this.session.$emacsMark;\n
if (prevMark)\n
this.session.$emacsMarkRing.push(prevMark);\n
if (!p || activate) this.setEmacsMark(p)\n
else this.session.$emacsMarkRing.push(p);\n
}\n
\n
editor.popEmacsMark = function() {\n
var mark = this.emacsMark();\n
if (mark) { this.setEmacsMark(null); return mark; }\n
return this.session.$emacsMarkRing.pop();\n
}\n
\n
editor.getLastEmacsMark = function(p) {\n
return this.session.$emacsMark || this.session.$emacsMarkRing.slice(-1)[0];\n
}\n
\n
editor.on("click", $resetMarkMode);\n
editor.on("changeSession", $kbSessionChange);\n
editor.renderer.screenToTextCoordinates = screenToTextBlockCoordinates;\n
editor.setStyle("emacs-mode");\n
editor.commands.addCommands(commands);\n
exports.handler.platform = editor.commands.platform;\n
editor.$emacsModeHandler = this;\n
editor.addEventListener(\'copy\', this.onCopy);\n
editor.addEventListener(\'paste\', this.onPaste);\n
};\n
\n
exports.handler.detach = function(editor) {\n
delete editor.renderer.screenToTextCoordinates;\n
editor.session.$selectLongWords = $formerLongWords;\n
editor.session.$useEmacsStyleLineStart = $formerLineStart;\n
editor.removeEventListener("click", $resetMarkMode);\n
editor.removeEventListener("changeSession", $kbSessionChange);\n
editor.unsetStyle("emacs-mode");\n
editor.commands.removeCommands(commands);\n
editor.removeEventListener(\'copy\', this.onCopy);\n
editor.removeEventListener(\'paste\', this.onPaste);\n
};\n
\n
var $kbSessionChange = function(e) {\n
if (e.oldSession) {\n
e.oldSession.$selectLongWords = $formerLongWords;\n
e.oldSession.$useEmacsStyleLineStart = $formerLineStart;\n
}\n
\n
$formerLongWords = e.session.$selectLongWords;\n
e.session.$selectLongWords = true;\n
$formerLineStart = e.session.$useEmacsStyleLineStart;\n
e.session.$useEmacsStyleLineStart = true;\n
\n
if (!e.session.hasOwnProperty(\'$emacsMark\'))\n
e.session.$emacsMark = null;\n
if (!e.session.hasOwnProperty(\'$emacsMarkRing\'))\n
e.session.$emacsMarkRing = [];\n
}\n
\n
var $resetMarkMode = function(e) {\n
e.editor.session.$emacsMark = null;\n
}\n
\n
var keys = require("../lib/keys").KEY_MODS,\n
eMods = {C: "ctrl", S: "shift", M: "alt", CMD: "command"},\n
combinations = ["C-S-M-CMD",\n
"S-M-CMD", "C-M-CMD", "C-S-CMD", "C-S-M",\n
"M-CMD", "S-CMD", "S-M", "C-CMD", "C-M", "C-S",\n
"CMD", "M", "S", "C"];\n
combinations.forEach(function(c) {\n
var hashId = 0;\n
c.split("-").forEach(function(c) {\n
hashId = hashId | keys[eMods[c]];\n
});\n
eMods[hashId] = c.toLowerCase() + "-";\n
});\n
\n
exports.handler.onCopy = function(e, editor) {\n
if (editor.$handlesEmacsOnCopy) return;\n
editor.$handlesEmacsOnCopy = true;\n
exports.handler.commands.killRingSave.exec(editor);\n
delete editor.$handlesEmacsOnCopy;\n
}\n
\n
exports.handler.onPaste = function(e, editor) {\n
editor.pushEmacsMark(editor.getCursorPosition());\n
}\n
\n
exports.handler.bindKey = function(key, command) {\n
if (!key)\n
return;\n
\n
var ckb = this.commmandKeyBinding;\n
key.split("|").forEach(function(keyPart) {\n
keyPart = keyPart.toLowerCase();\n
ckb[keyPart] = command;\n
var keyParts = keyPart.split(" ").slice(0,-1);\n
keyParts.reduce(function(keyMapKeys, keyPart, i) {\n
var prefix = keyMapKeys[i-1] ? keyMapKeys[i-1] + \' \' : \'\';\n
return keyMapKeys.concat([prefix + keyPart]);\n
}, []).forEach(function(keyPart) {\n
if (!ckb[keyPart]) ckb[keyPart] = "null";\n
});\n
}, this);\n
}\n
\n
exports.handler.handleKeyboard = function(data, hashId, key, keyCode) {\n
var editor = data.editor;\n
if (hashId == -1) {\n
editor.pushEmacsMark();\n
if (data.count) {\n
var str = Array(data.count + 1).join(key);\n
data.count = null;\n
return {command: "insertstring", args: str};\n
}\n
}\n
\n
if (key == "\\x00") return undefined;\n
\n
var modifier = eMods[hashId];\n
if (modifier == "c-" || data.universalArgument) {\n
var prevCount = String(data.count || 0);\n
var count = parseInt(key[key.length - 1]);\n
if (typeof count === \'number\' && !isNaN(count)) {\n
data.count = parseInt(prevCount + count);\n
return {command: "null"};\n
} else if (data.universalArgument) {\n
data.count = 4;\n
}\n
}\n
data.universalArgument = false;\n
if (modifier) key = modifier + key;\n
if (data.keyChain) key = data.keyChain += " " + key;\n
var command = this.commmandKeyBinding[key];\n
data.keyChain = command == "null" ? key : "";\n
if (!command) return undefined;\n
if (command === "null") return {command: "null"};\n
\n
if (command === "universalArgument") {\n
data.universalArgument = true;\n
return {command: "null"};\n
}\n
var args;\n
if (typeof command !== "string") {\n
args = command.args;\n
if (command.command) command = command.command;\n
if (command === "goorselect") {\n
command = editor.emacsMark() ? args[1] : args[0];\n
args = null;\n
}\n
}\n
\n
if (typeof command === "string") {\n
if (command === "insertstring" ||\n
command === "splitline" ||\n
command === "togglecomment") {\n
editor.pushEmacsMark();\n
}\n
command = this.commands[command] || editor.commands.commands[command];\n
if (!command) return undefined;\n
}\n
\n
if (!command.readonly && !command.isYank)\n
data.lastCommand = null;\n
\n
if (data.count) {\n
var count = data.count;\n
data.count = 0;\n
if (!command || !command.handlesCount) {\n
return {\n
args: args,\n
command: {\n
exec: function(editor, args) {\n
for (var i = 0; i < count; i++)\n
command.exec(editor, args);\n
}\n
}\n
};\n
} else {\n
if (!args) args = {}\n
if (typeof args === \'object\') args.count = count;\n
}\n
}\n
\n
return {command: command, args: args};\n
};\n
\n
exports.emacsKeys = {\n
"Up|C-p" : {command: "goorselect", args: ["golineup","selectup"]},\n
"Down|C-n" : {command: "goorselect", args: ["golinedown","selectdown"]},\n
"Left|C-b" : {command: "goorselect", args: ["gotoleft","selectleft"]},\n
"Right|C-f" : {command: "goorselect", args: ["gotoright","selectright"]},\n
"C-Left|M-b" : {command: "goorselect", args: ["gotowordleft","selectwordleft"]},\n
"C-Right|M-f" : {command: "goorselect", args: ["gotowordright","selectwordright"]},\n
"Home|C-a" : {command: "goorselect", args: ["gotolinestart","selecttolinestart"]},\n
"End|C-e" : {command: "goorselect", args: ["gotolineend","selecttolineend"]},\n
"C-Home|S-M-,": {command: "goorselect", args: ["gotostart","selecttostart"]},\n
"C-End|S-M-." : {command: "goorselect", args: ["gotoend","selecttoend"]},\n
"S-Up|S-C-p" : "selectup",\n
"S-Down|S-C-n" : "selectdown",\n
"S-Left|S-C-b" : "selectleft",\n
"S-Right|S-C-f" : "selectright",\n
"S-C-Left|S-M-b" : "selectwordleft",\n
"S-C-Right|S-M-f" : "selectwordright",\n
"S-Home|S-C-a" : "selecttolinestart",\n
"S-End|S-C-e" : "selecttolineend",\n
"S-C-Home" : "selecttostart",\n
"S-C-End" : "selecttoend",\n
\n
"C-l" : "recenterTopBottom",\n
"M-s" : "centerselection",\n
"M-g": "gotoline",\n
"C-x C-p": "selectall",\n
"C-Down": {command: "goorselect", args: ["gotopagedown","selectpagedown"]},\n
"C-Up": {command: "goorselect", args: ["gotopageup","selectpageup"]},\n
"PageDown|C-v": {command: "goorselect", args: ["gotopagedown","selectpagedown"]},\n
"PageUp|M-v": {command: "goorselect", args: ["gotopageup","selectpageup"]},\n
"S-C-Down": "selectpagedown",\n
"S-C-Up": "selectpageup",\n
\n
"C-s": "iSearch",\n
"C-r": "iSearchBackwards",\n
\n
"M-C-s": "findnext",\n
"M-C-r": "findprevious",\n
"S-M-5": "replace",\n
"Backspace": "backspace",\n
"Delete|C-d": "del",\n
"Return|C-m": {command: "insertstring", args: "\\n"}, // "newline"\n
"C-o": "splitline",\n
\n
"M-d|C-Delete": {command: "killWord", args: "right"},\n
"C-Backspace|M-Backspace|M-Delete": {command: "killWord", args: "left"},\n
"C-k": "killLine",\n
\n
"C-y|S-Delete": "yank",\n
"M-y": "yankRotate",\n
"C-g": "keyboardQuit",\n
\n
"C-w": "killRegion",\n
"M-w": "killRingSave",\n
"C-Space": "setMark",\n
"C-x C-x": "exchangePointAndMark",\n
\n
"C-t": "transposeletters",\n
"M-u": "touppercase", // Doesn\'t work\n
"M-l": "tolowercase",\n
"M-/": "autocomplete", // Doesn\'t work\n
"C-u": "universalArgument",\n
\n
"M-;": "togglecomment",\n
\n
"C-/|C-x u|S-C--|C-z": "undo",\n
"S-C-/|S-C-x u|C--|S-C-z": "redo", //infinite undo?\n
"C-x r": "selectRectangularRegion",\n
"M-x": {command: "focusCommandLine", args: "M-x "}\n
};\n
\n
\n
exports.handler.bindKeys(exports.emacsKeys);\n
\n
exports.handler.addCommands({\n
recenterTopBottom: function(editor) {\n
var renderer = editor.renderer;\n
var pos = renderer.$cursorLayer.getPixelPosition();\n
var h = renderer.$size.scrollerHeight - renderer.lineHeight;\n
var scrollTop = renderer.scrollTop;\n
if (Math.abs(pos.top - scrollTop) < 2) {\n
scrollTop = pos.top - h;\n
} else if (Math.abs(pos.top - scrollTop - h * 0.5) < 2) {\n
scrollTop = pos.top;\n
} else {\n
scrollTop = pos.top - h * 0.5;\n
}\n
editor.session.setScrollTop(scrollTop);\n
},\n
selectRectangularRegion: function(editor) {\n
editor.multiSelect.toggleBlockSelection();\n
},\n
setMark: {\n
exec: function(editor, args) {\n
if (args && args.count) {\n
var mark = editor.popEmacsMark();\n
mark && editor.selection.moveCursorToPosition(mark);\n
return;\n
}\n
\n
var mark = editor.emacsMark(),\n
transientMarkModeActive = true;\n
if (transientMarkModeActive && (mark || !editor.selection.isEmpty())) {\n
editor.pushEmacsMark();\n
editor.clearSelection();\n
return;\n
}\n
\n
if (mark) {\n
var cp = editor.getCursorPosition();\n
if (editor.selection.isEmpty() &&\n
mark.row == cp.row && mark.column == cp.column) {\n
editor.pushEmacsMark();\n
return;\n
}\n
}\n
mark = editor.getCursorPosition();\n
editor.setEmacsMark(mark);\n
editor.selection.setSelectionAnchor(mark.row, mark.column);\n
},\n
readonly: true,\n
handlesCount: true,\n
multiSelectAction: "forEach"\n
},\n
exchangePointAndMark: {\n
exec: function(editor, args) {\n
var sel = editor.selection;\n
if (args.count) {\n
var pos = editor.getCursorPosition();\n
sel.clearSelection();\n
sel.moveCursorToPosition(editor.popEmacsMark());\n
editor.pushEmacsMark(pos);\n
return;\n
}\n
var lastMark = editor.getLastEmacsMark();\n
var range = sel.getRange();\n
if (range.isEmpty()) {\n
sel.selectToPosition(lastMark);\n
return;\n
}\n
sel.setSelectionRange(range, !sel.isBackwards());\n
},\n
readonly: true,\n
handlesCount: true,\n
multiSelectAction: "forEach"\n
},\n
killWord: {\n
exec: function(editor, dir) {\n
editor.clearSelection();\n
if (dir == "left")\n
editor.selection.selectWordLeft();\n
else\n
editor.selection.selectWordRight();\n
\n
var range = editor.getSelectionRange();\n
var text = editor.session.getTextRange(range);\n
exports.killRing.add(text);\n
\n
editor.session.remove(range);\n
editor.clearSelection();\n
},\n
multiSelectAction: "forEach"\n
},\n
killLine: function(editor) {\n
editor.pushEmacsMark(null);\n
var pos = editor.getCursorPosition();\n
if (pos.column == 0 &&\n
editor.session.doc.getLine(pos.row).length == 0) {\n
editor.selection.selectLine();\n
} else {\n
editor.clearSelection();\n
editor.selection.selectLineEnd();\n
}\n
var range = editor.getSelectionRange();\n
var text = editor.session.getTextRange(range);\n
exports.killRing.add(text);\n
\n
editor.session.remove(range);\n
editor.clearSelection();\n
},\n
yank: function(editor) {\n
editor.onPaste(exports.killRing.get() || \'\');\n
editor.keyBinding.$data.lastCommand = "yank";\n
},\n
yankRotate: function(editor) {\n
if (editor.keyBinding.$data.lastCommand != "yank")\n
return;\n
editor.undo();\n
editor.onPaste(exports.killRing.rotate());\n
editor.keyBinding.$data.lastCommand = "yank";\n
},\n
killRegion: {\n
exec: function(editor) {\n
exports.killRing.add(editor.getCopyText());\n
editor.commands.byName.cut.exec(editor);\n
},\n
readonly: true,\n
multiSelectAction: "forEach"\n
},\n
killRingSave: {\n
exec: function(editor) {\n
exports.killRing.add(editor.getCopyText());\n
setTimeout(function() {\n
var sel = editor.selection,\n
range = sel.getRange();\n
editor.pushEmacsMark(sel.isBackwards() ? range.end : range.start);\n
sel.clearSelection();\n
}, 0);\n
},\n
readonly: true\n
},\n
keyboardQuit: function(editor) {\n
editor.selection.clearSelection();\n
editor.setEmacsMark(null);\n
},\n
focusCommandLine: function(editor, arg) {\n
if (editor.showCommandLine)\n
editor.showCommandLine(arg);\n
}\n
});\n
\n
exports.handler.addCommands(iSearchCommandModule.iSearchStartCommands);\n
\n
var commands = exports.handler.commands;\n
commands.yank.isYank = true;\n
commands.yankRotate.isYank = true;\n
\n
exports.killRing = {\n
$data: [],\n
add: function(str) {\n
str && this.$data.push(str);\n
if (this.$data.length > 30)\n
this.$data.shift();\n
},\n
get: function(n) {\n
n = n || 1;\n
return this.$data.slice(this.$data.length-n, this.$data.length).reverse().join(\'\\n\');\n
},\n
pop: function() {\n
if (this.$data.length > 1)\n
this.$data.pop();\n
return this.get();\n
},\n
rotate: function() {\n
this.$data.unshift(this.$data.pop());\n
return this.get();\n
}\n
};\n
\n
});\n
\n
define(\'ace/incremental_search\', [\'require\', \'exports\', \'module\' , \'ace/lib/oop\', \'ace/range\', \'ace/search\', \'ace/search_highlight\', \'ace/commands/incremental_search_commands\', \'ace/lib/dom\', \'ace/commands/command_manager\', \'ace/editor\', \'ace/config\'], function(require, exports, module) {\n
\n
\n
var oop = require("./lib/oop");\n
var Range = require("./range").Range;\n
var Search = require("./search").Search;\n
var SearchHighlight = require("./search_highlight").SearchHighlight;\n
var iSearchCommandModule = require("./commands/incremental_search_commands");\n
var ISearchKbd = iSearchCommandModule.IncrementalSearchKeyboardHandler;\n
function IncrementalSearch() {\n
this.$options = {wrap: false, skipCurrent: false};\n
this.$keyboardHandler = new ISearchKbd(this);\n
}\n
\n
oop.inherits(IncrementalSearch, Search);\n
\n
;(function() {\n
\n
this.activate = function(ed, backwards) {\n
this.$editor = ed;\n
this.$startPos = this.$currentPos = ed.getCursorPosition();\n
this.$options.needle = \'\';\n
this.$options.backwards = backwards;\n
ed.keyBinding.addKeyboardHandler(this.$keyboardHandler);\n
this.$mousedownHandler = ed.addEventListener(\'mousedown\', this.onMouseDown.bind(this));\n
this.selectionFix(ed);\n
this.statusMessage(true);\n
}\n
\n
this.deactivate = function(reset) {\n
this.cancelSearch(reset);\n
this.$editor.keyBinding.removeKeyboardHandler(this.$keyboardHandler);\n
if (this.$mousedownHandler) {\n
this.$editor.removeEventListener(\'mousedown\', this.$mousedownHandler);\n
delete this.$mousedownHandler;\n
}\n
this.message(\'\');\n
}\n
\n
this.selectionFix = function(editor) {\n
if (editor.selection.isEmpty() && !editor.session.$emacsMark) {\n
editor.clearSelection();\n
}\n
}\n
\n
this.highlight = function(regexp) {\n
var sess = this.$editor.session,\n
hl = sess.$isearchHighlight = sess.$isearchHighlight || sess.addDynamicMarker(\n
new SearchHighlight(null, "ace_isearch-result", "text"));\n
hl.setRegexp(regexp);\n
sess._emit("changeBackMarker"); // force highlight layer redraw\n
}\n
\n
this.cancelSearch = function(reset) {\n
var e = this.$editor;\n
this.$prevNeedle = this.$options.needle;\n
this.$options.needle = \'\';\n
if (reset) {\n
e.moveCursorToPosition(this.$startPos);\n
this.$currentPos = this.$startPos;\n
} else {\n
e.pushEmacsMark && e.pushEmacsMark(this.$startPos, false);\n
}\n
this.highlight(null);\n
return Range.fromPoints(this.$currentPos, this.$currentPos);\n
}\n
\n
this.highlightAndFindWithNeedle = function(moveToNext, needleUpdateFunc) {\n
if (!this.$editor) return null;\n
var options = this.$options;\n
if (needleUpdateFunc) {\n
options.needle = needleUpdateFunc.call(this, options.needle || \'\') || \'\';\n
}\n
if (options.needle.length === 0) {\n
this.statusMessage(true);\n
return this.cancelSearch(true);\n
};\n
options.start = this.$currentPos;\n
var session = this.$editor.session,\n
found = this.find(session);\n
if (found) {\n
if (options.backwards) found = Range.fromPoints(found.end, found.start);\n
this.$editor.moveCursorToPosition(found.end);\n
if (moveToNext) this.$currentPos = found.end;\n
this.highlight(options.re)\n
}\n
\n
this.statusMessage(found);\n
\n
return found;\n
}\n
\n
this.addChar = function(c) {\n
return this.highlightAndFindWithNeedle(false, function(needle) {\n
return needle + c;\n
});\n
}\n
\n
this.removeChar = function(c) {\n
return this.highlightAndFindWithNeedle(false, function(needle) {\n
return needle.length > 0 ? needle.substring(0, needle.length-1) : needle;\n
});\n
}\n
\n
this.next = function(options) {\n
options = options || {};\n
this.$options.backwards = !!options.backwards;\n
this.$currentPos = this.$editor.getCursorPosition();\n
return this.highlightAndFindWithNeedle(true, function(needle) {\n
return options.useCurrentOrPrevSearch && needle.length === 0 ?\n
this.$prevNeedle || \'\' : needle;\n
});\n
}\n
\n
this.onMouseDown = function(evt) {\n
this.deactivate();\n
return true;\n
}\n
\n
this.statusMessage = function(found) {\n
var options = this.$options, msg = \'\';\n
msg += options.backwards ? \'reverse-\' : \'\';\n
msg += \'isearch: \' + options.needle;\n
msg += found ? \'\' : \' (not found)\';\n
this.message(msg);\n
}\n
\n
this.message = function(msg) {\n
if (this.$editor.showCommandLine) {\n
this.$editor.showCommandLine(msg);\n
this.$editor.focus();\n
} else {\n
console.log(msg);\n
}\n
}\n
\n
}).call(IncrementalSearch.prototype);\n
\n
\n
exports.IncrementalSearch = IncrementalSearch;\n
\n
var dom = require(\'./lib/dom\');\n
dom.importCssString && dom.importCssString("\\\n
.ace_marker-layer .ace_isearch-result {\\\n
position: absolute;\\\n
z-index: 6;\\\n
-moz-box-sizing: border-box;\\\n
-webkit-box-sizing: border-box;\\\n
box-sizing: border-box;\\\n
}\\\n
div.ace_isearch-result {\\\n
border-radius: 4px;\\\n
background-color: rgba(255, 200, 0, 0.5);\\\n
box-shadow: 0 0 4px rgb(255, 200, 0);\\\n
}\\\n
.ace_dark div.ace_isearch-result {\\\n
background-color: rgb(100, 110, 160);\\\n
box-shadow: 0 0 4px rgb(80, 90, 140);\\\n
}", "incremental-search-highlighting");\n
var commands = require("./commands/command_manager");\n
(function() {\n
this.setupIncrementalSearch = function(editor, val) {\n
if (this.usesIncrementalSearch == val) return;\n
this.usesIncrementalSearch = val;\n
var iSearchCommands = iSearchCommandModule.iSearchStartCommands;\n
var method = val ? \'addCommands\' : \'removeCommands\';\n
this[method](iSearchCommands);\n
};\n
}).call(commands.CommandManager.prototype);\n
var Editor = require("./editor").Editor;\n
require("./config").defineOptions(Editor.prototype, "editor", {\n
useIncrementalSearch: {\n
set: function(val) {\n
this.keyBinding.$handlers.forEach(function(handler) {\n
if (handler.setupIncrementalSearch) {\n
handler.setupIncrementalSearch(this, val);\n
}\n
});\n
this._emit(\'incrementalSearchSettingChanged\', {isEnabled: val});\n
}\n
}\n
});\n
\n
});\n
\n
define(\'ace/commands/incremental_search_commands\', [\'require\', \'exports\', \'module\' , \'ace/config\', \'ace/lib/oop\', \'ace/keyboard/hash_handler\', \'ace/commands/occur_commands\'], function(require, exports, module) {\n
\n
var config = require("../config");\n
var oop = require("../lib/oop");\n
var HashHandler = require("../keyboard/hash_handler").HashHandler;\n
var occurStartCommand = require("./occur_commands").occurStartCommand;\n
exports.iSearchStartCommands = [{\n
name: "iSearch",\n
bindKey: {win: "Ctrl-F", mac: "Command-F"},\n
exec: function(editor, options) {\n
config.loadModule(["core", "ace/incremental_search"], function(e) {\n
var iSearch = e.iSearch = e.iSearch || new e.IncrementalSearch();\n
iSearch.activate(editor, options.backwards);\n
if (options.jumpToFirstMatch) iSearch.next(options);\n
});\n
},\n
readOnly: true\n
}, {\n
name: "iSearchBackwards",\n
exec: function(editor, jumpToNext) { editor.execCommand(\'iSearch\', {backwards: true}); },\n
readOnly: true\n
}, {\n
name: "iSearchAndGo",\n
bindKey: {win: "Ctrl-K", mac: "Command-G"},\n
exec: function(editor, jumpToNext) { editor.execCommand(\'iSearch\', {jumpToFirstMatch: true, useCurrentOrPrevSearch: true}); },\n
readOnly: true\n
}, {\n
name: "iSearchBackwardsAndGo",\n
bindKey: {win: "Ctrl-Shift-K", mac: "Command-Shift-G"},\n
exec: function(editor) { editor.execCommand(\'iSearch\', {jumpToFirstMatch: true, backwards: true, useCurrentOrPrevSearch: true}); },\n
readOnly: true\n
}];\n
exports.iSearchCommands = [{\n
name: "restartSearch",\n
bindKey: {win: "Ctrl-F", mac: "Command-F"},\n
exec: function(iSearch) {\n
iSearch.cancelSearch(true);\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: "searchForward",\n
bindKey: {win: "Ctrl-S|Ctrl-K", mac: "Ctrl-S|Command-G"},\n
exec: function(iSearch, options) {\n
options.useCurrentOrPrevSearch = true;\n
iSearch.next(options);\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: "searchBackward",\n
bindKey: {win: "Ctrl-R|Ctrl-Shift-K", mac: "Ctrl-R|Command-Shift-G"},\n
exec: function(iSearch, options) {\n
options.useCurrentOrPrevSearch = true;\n
options.backwards = true;\n
iSearch.next(options);\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: "extendSearchTerm",\n
exec: function(iSearch, string) {\n
iSearch.addChar(string);\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: "extendSearchTermSpace",\n
bindKey: "space",\n
exec: function(iSearch) { iSearch.addChar(\' \'); },\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: "shrinkSearchTerm",\n
bindKey: "backspace",\n
exec: function(iSearch) {\n
iSearch.removeChar();\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: \'confirmSearch\',\n
bindKey: \'return\',\n
exec: function(iSearch) { iSearch.deactivate(); },\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: \'cancelSearch\',\n
bindKey: \'esc|Ctrl-G\',\n
exec: function(iSearch) { iSearch.deactivate(true); },\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}, {\n
name: \'occurisearch\',\n
bindKey: \'Ctrl-O\',\n
exec: function(iSearch) {\n
var options = oop.mixin({}, iSearch.$options);\n
iSearch.deactivate();\n
occurStartCommand.exec(iSearch.$editor, options);\n
},\n
readOnly: true,\n
isIncrementalSearchCommand: true\n
}];\n
\n
function IncrementalSearchKeyboardHandler(iSearch) {\n
this.$iSearch = iSearch;\n
}\n
\n
oop.inherits(IncrementalSearchKeyboardHandler, HashHandler);\n
\n
;(function() {\n
\n
this.attach = function(editor) {\n
var iSearch = this.$iSearch;\n
HashHandler.call(this, exports.iSearchCommands, editor.commands.platform);\n
this.$commandExecHandler = editor.commands.addEventListener(\'exec\', function(e) {\n
if (!e.command.isIncrementalSearchCommand) return undefined;\n
e.stopPropagation();\n
e.preventDefault();\n
return e.command.exec(iSearch, e.args || {});\n
});\n
}\n
\n
this.detach = function(editor) {\n
if (!this.$commandExecHandler) return;\n
editor.commands.removeEventListener(\'exec\', this.$commandExecHandler);\n
delete this.$commandExecHandler;\n
}\n
\n
var handleKeyboard$super = this.handleKeyboard;\n
this.handleKeyboard = function(data, hashId, key, keyCode) {\n
var cmd = handleKeyboard$super.call(this, data, hashId, key, keyCode);\n
if (cmd.command) { return cmd; }\n
if (hashId == -1) {\n
var extendCmd = this.commands.extendSearchTerm;\n
if (extendCmd) { return {command: extendCmd, args: key}; }\n
}\n
return {command: "null", passEvent: hashId == 0 || hashId == 4};\n
}\n
\n
}).call(IncrementalSearchKeyboardHandler.prototype);\n
\n
\n
exports.IncrementalSearchKeyboardHandler = IncrementalSearchKeyboardHandler;\n
\n
});\n
\n
define(\'ace/commands/occur_commands\', [\'require\', \'exports\', \'module\' , \'ace/config\', \'ace/occur\', \'ace/keyboard/hash_handler\', \'ace/lib/oop\'], function(require, exports, module) {\n
\n
var config = require("../config"),\n
Occur = require("../occur").Occur;\n
var occurStartCommand = {\n
name: "occur",\n
exec: function(editor, options) {\n
var alreadyInOccur = !!editor.session.$occur;\n
var occurSessionActive = new Occur().enter(editor, options);\n
if (occurSessionActive && !alreadyInOccur)\n
OccurKeyboardHandler.installIn(editor);\n
},\n
readOnly: true\n
};\n
\n
var occurCommands = [{\n
name: "occurexit",\n
bindKey: \'esc|Ctrl-G\',\n
exec: function(editor) {\n
var occur = editor.session.$occur;\n
if (!occur) return;\n
occur.exit(editor, {});\n
if (!editor.session.$occur) OccurKeyboardHandler.uninstallFrom(editor);\n
},\n
readOnly: true\n
}, {\n
name: "occuraccept",\n
bindKey: \'enter\',\n
exec: function(editor) {\n
var occur = editor.session.$occur;\n
if (!occur) return;\n
occur.exit(editor, {translatePosition: true});\n
if (!editor.session.$occur) OccurKeyboardHandler.uninstallFrom(editor);\n
},\n
readOnly: true\n
}];\n
\n
var HashHandler = require("../keyboard/hash_handler").HashHandler;\n
var oop = require("../lib/oop");\n
\n
\n
function OccurKeyboardHandler() {}\n
\n
oop.inherits(OccurKeyboardHandler, HashHandler);\n
\n
;(function() {\n
\n
this.isOccurHandler = true;\n
\n
this.attach = function(editor) {\n
HashHandler.call(this, occurCommands, editor.commands.platform);\n
this.$editor = editor;\n
}\n
\n
var handleKeyboard$super = this.handleKeyboard;\n
this.handleKeyboard = function(data, hashId, key, keyCode) {\n
var cmd = handleKeyboard$super.call(this, data, hashId, key, keyCode);\n
return (cmd && cmd.command) ? cmd : undefined;\n
}\n
\n
}).call(OccurKeyboardHandler.prototype);\n
\n
OccurKeyboardHandler.installIn = function(editor) {\n
var handler = new this();\n
editor.keyBinding.addKeyboardHandler(handler);\n
editor.commands.addCommands(occurCommands);\n
}\n
\n
OccurKeyboardHandler.uninstallFrom = function(editor) {\n
editor.commands.removeCommands(occurCommands);\n
var handler = editor.getKeyboardHandler();\n
if (handler.isOccurHandler)\n
editor.keyBinding.removeKeyboardHandler(handler);\n
}\n
\n
exports.occurStartCommand = occurStartCommand;\n
\n
});\n
\n
define(\'ace/occur\', [\'require\', \'exports\', \'module\' , \'ace/lib/oop\', \'ace/range\', \'ace/search\', \'ace/edit_session\', \'ace/search_highlight\', \'ace/lib/dom\'], function(require, exports, module) {\n
\n
\n
var oop = require("./lib/oop");\n
var Range = require("./range").Range;\n
var Search = require("./search").Search;\n
var EditSession = require("./edit_session").EditSession;\n
var SearchHighlight = require("./search_highlight").SearchHighlight;\n
function Occur() {}\n
\n
oop.inherits(Occur, Search);\n
\n
(function() {\n
this.enter = function(editor, options) {\n
if (!options.needle) return false;\n
var pos = editor.getCursorPosition();\n
this.displayOccurContent(editor, options);\n
var translatedPos = this.originalToOccurPosition(editor.session, pos);\n
editor.moveCursorToPosition(translatedPos);\n
return true;\n
}\n
this.exit = function(editor, options) {\n
var pos = options.translatePosition && editor.getCursorPosition();\n
var translatedPos = pos && this.occurToOriginalPosition(editor.session, pos);\n
this.displayOriginalContent(editor);\n
if (translatedPos)\n
editor.moveCursorToPosition(translatedPos);\n
return true;\n
}\n
\n
this.highlight = function(sess, regexp) {\n
var hl = sess.$occurHighlight = sess.$occurHighlight || sess.addDynamicMarker(\n
new SearchHighlight(null, "ace_occur-highlight", "text"));\n
hl.setRegexp(regexp);\n
sess._emit("changeBackMarker"); // force highlight layer redraw\n
}\n
\n
this.displayOccurContent = function(editor, options) {\n
this.$originalSession = editor.session;\n
var found = this.matchingLines(editor.session, options);\n
var lines = found.map(function(foundLine) { return foundLine.content; });\n
var occurSession = new EditSession(lines.join(\'\\n\'));\n
occurSession.$occur = this;\n
occurSession.$occurMatchingLines = found;\n
editor.setSession(occurSession);\n
this.highlight(occurSession, options.re);\n
occurSession._emit(\'changeBackMarker\');\n
}\n
\n
this.displayOriginalContent = function(editor) {\n
editor.setSession(this.$originalSession);\n
}\n
this.originalToOccurPosition = function(session, pos) {\n
var lines = session.$occurMatchingLines;\n
var nullPos = {row: 0, column: 0};\n
if (!lines) return nullPos;\n
for (var i = 0; i < lines.length; i++) {\n
if (lines[i].row === pos.row)\n
return {row: i, column: pos.column};\n
}\n
return nullPos;\n
}\n
this.occurToOriginalPosition = function(session, pos) {\n
var lines = session.$occurMatchingLines;\n
if (!lines || !lines[pos.row])\n
return pos;\n
return {row: lines[pos.row].row, column: pos.column};\n
}\n
\n
this.matchingLines = function(session, options) {\n
options = oop.mixin({}, options);\n
if (!session || !options.needle) return [];\n
var search = new Search();\n
search.set(options);\n
return search.findAll(session).reduce(function(lines, range) {\n
var row = range.start.row;\n
var last = lines[lines.length-1];\n
return last && last.row === row ?\n
lines :\n
lines.concat({row: row, content: session.getLine(row)});\n
}, []);\n
}\n
\n
}).call(Occur.prototype);\n
\n
var dom = require(\'./lib/dom\');\n
dom.importCssString(".ace_occur-highlight {\\n\\\n
border-radius: 4px;\\n\\\n
background-color: rgba(87, 255, 8, 0.25);\\n\\\n
position: absolute;\\n\\\n
z-index: 4;\\n\\\n
-moz-box-sizing: border-box;\\n\\\n
-webkit-box-sizing: border-box;\\n\\\n
box-sizing: border-box;\\n\\\n
box-shadow: 0 0 4px rgb(91, 255, 50);\\n\\\n
}\\n\\\n
.ace_dark .ace_occur-highlight {\\n\\\n
background-color: rgb(80, 140, 85);\\n\\\n
box-shadow: 0 0 4px rgb(60, 120, 70);\\n\\\n
}\\n", "incremental-occur-highlighting");\n
\n
exports.Occur = Occur;\n
\n
});\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>36738</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>keybinding-emacs.js</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts76363589.24</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>keybinding-vim.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/* ***** BEGIN LICENSE BLOCK *****\n
* Distributed under the BSD license:\n
*\n
* Copyright (c) 2010, Ajax.org B.V.\n
* All rights reserved.\n
* \n
* Redistribution and use in source and binary forms, with or without\n
* modification, are permitted provided that the following conditions are met:\n
* * Redistributions of source code must retain the above copyright\n
* notice, this list of conditions and the following disclaimer.\n
* * Redistributions in binary form must reproduce the above copyright\n
* notice, this list of conditions and the following disclaimer in the\n
* documentation and/or other materials provided with the distribution.\n
* * Neither the name of Ajax.org B.V. nor the\n
* names of its contributors may be used to endorse or promote products\n
* derived from this software without specific prior written permission.\n
* \n
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND\n
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n
* DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY\n
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n
*\n
* ***** END LICENSE BLOCK ***** */\n
\n
define(\'ace/keyboard/vim\', [\'require\', \'exports\', \'module\' , \'ace/keyboard/vim/commands\', \'ace/keyboard/vim/maps/util\', \'ace/lib/useragent\'], function(require, exports, module) {\n
\n
\n
var cmds = require("./vim/commands");\n
var coreCommands = cmds.coreCommands;\n
var util = require("./vim/maps/util");\n
var useragent = require("../lib/useragent");\n
\n
var startCommands = {\n
"i": {\n
command: coreCommands.start\n
},\n
"I": {\n
command: coreCommands.startBeginning\n
},\n
"a": {\n
command: coreCommands.append\n
},\n
"A": {\n
command: coreCommands.appendEnd\n
},\n
"ctrl-f": {\n
command: "gotopagedown"\n
},\n
"ctrl-b": {\n
command: "gotopageup"\n
}\n
};\n
\n
exports.handler = {\n
\t$id: "ace/keyboard/vim",\n
handleMacRepeat: function(data, hashId, key) {\n
if (hashId == -1) {\n
data.inputChar = key;\n
data.lastEvent = "input";\n
} else if (data.inputChar && data.$lastHash == hashId && data.$lastKey == key) {\n
if (data.lastEvent == "input") {\n
data.lastEvent = "input1";\n
} else if (data.lastEvent == "input1") {\n
return true;\n
}\n
} else {\n
data.$lastHash = hashId;\n
data.$lastKey = key;\n
data.lastEvent = "keypress";\n
}\n
},\n
\n
handleKeyboard: function(data, hashId, key, keyCode, e) {\n
if (hashId != 0 && (key == "" || key == "\\x00"))\n
return null;\n
\n
var editor = data.editor;\n
\n
if (hashId == 1)\n
key = "ctrl-" + key;\n
if (key == "ctrl-c") {\n
if (!useragent.isMac && editor.getCopyText()) {\n
editor.once("copy", function() {\n
if (data.state == "start")\n
coreCommands.stop.exec(editor);\n
else\n
editor.selection.clearSelection();\n
});\n
return {command: "null", passEvent: true};\n
}\n
return {command: coreCommands.stop}; \n
} else if ((key == "esc" && hashId == 0) || key == "ctrl-[") {\n
return {command: coreCommands.stop};\n
} else if (data.state == "start") {\n
if (useragent.isMac && this.handleMacRepeat(data, hashId, key)) {\n
hashId = -1;\n
key = data.inputChar;\n
}\n
\n
if (hashId == -1 || hashId == 1 || hashId == 0 && key.length > 1) {\n
if (cmds.inputBuffer.idle && startCommands[key])\n
return startCommands[key];\n
cmds.inputBuffer.push(editor, key);\n
return {command: "null", passEvent: false}; \n
} // if no modifier || shift: wait for input.\n
else if (key.length == 1 && (hashId == 0 || hashId == 4)) {\n
return {command: "null", passEvent: true};\n
} else if (key == "esc" && hashId == 0) {\n
return {command: coreCommands.stop};\n
}\n
} else {\n
if (key == "ctrl-w") {\n
return {command: "removewordleft"};\n
}\n
}\n
},\n
\n
attach: function(editor) {\n
editor.on("click", exports.onCursorMove);\n
if (util.currentMode !== "insert")\n
cmds.coreCommands.stop.exec(editor);\n
editor.$vimModeHandler = this;\n
},\n
\n
detach: function(editor) {\n
editor.removeListener("click", exports.onCursorMove);\n
util.noMode(editor);\n
util.currentMode = "normal";\n
},\n
\n
actions: cmds.actions,\n
getStatusText: function() {\n
if (util.currentMode == "insert")\n
return "INSERT";\n
if (util.onVisualMode)\n
return (util.onVisualLineMode ? "VISUAL LINE " : "VISUAL ") + cmds.inputBuffer.status;\n
return cmds.inputBuffer.status;\n
}\n
};\n
\n
\n
exports.onCursorMove = function(e) {\n
cmds.onCursorMove(e.editor, e);\n
exports.onCursorMove.scheduled = false;\n
};\n
\n
});\n
\n
define(\'ace/keyboard/vim/commands\', [\'require\', \'exports\', \'module\' , \'ace/lib/lang\', \'ace/keyboard/vim/maps/util\', \'ace/keyboard/vim/maps/motions\', \'ace/keyboard/vim/maps/operators\', \'ace/keyboard/vim/maps/aliases\', \'ace/keyboard/vim/registers\'], function(require, exports, module) {\n
\n
"never use strict";\n
\n
var lang = require("../../lib/lang");\n
var util = require("./maps/util");\n
var motions = require("./maps/motions");\n
var operators = require("./maps/operators");\n
var alias = require("./maps/aliases");\n
var registers = require("./registers");\n
\n
var NUMBER = 1;\n
var OPERATOR = 2;\n
var MOTION = 3;\n
var ACTION = 4;\n
var HMARGIN = 8; // Minimum amount of line separation between margins;\n
\n
var repeat = function repeat(fn, count, args) {\n
while (0 < count--)\n
fn.apply(this, args);\n
};\n
\n
var ensureScrollMargin = function(editor) {\n
var renderer = editor.renderer;\n
var pos = renderer.$cursorLayer.getPixelPosition();\n
\n
var top = pos.top;\n
\n
var margin = HMARGIN * renderer.layerConfig.lineHeight;\n
if (2 * margin > renderer.$size.scrollerHeight)\n
margin = renderer.$size.scrollerHeight / 2;\n
\n
if (renderer.scrollTop > top - margin) {\n
renderer.session.setScrollTop(top - margin);\n
}\n
\n
if (renderer.scrollTop + renderer.$size.scrollerHeight < top + margin + renderer.lineHeight) {\n
renderer.session.setScrollTop(top + margin + renderer.lineHeight - renderer.$size.scrollerHeight);\n
}\n
};\n
\n
var actions = exports.actions = {\n
"z": {\n
param: true,\n
fn: function(editor, range, count, param) {\n
switch (param) {\n
case "z":\n
editor.renderer.alignCursor(null, 0.5);\n
break;\n
case "t":\n
editor.renderer.alignCursor(null, 0);\n
break;\n
case "b":\n
editor.renderer.alignCursor(null, 1);\n
break;\n
}\n
}\n
},\n
"r": {\n
param: true,\n
fn: function(editor, range, count, param) {\n
if (param && param.length) {\n
if (param.length > 1)\n
param = param == "return" ? "\\n" : param == "tab" ? "\\t" : param;\n
repeat(function() { editor.insert(param); }, count || 1);\n
editor.navigateLeft();\n
}\n
}\n
},\n
"R": {\n
fn: function(editor, range, count, param) {\n
util.insertMode(editor);\n
editor.setOverwrite(true);\n
}\n
},\n
"~": {\n
fn: function(editor, range, count) {\n
repeat(function() {\n
var range = editor.selection.getRange();\n
if (range.isEmpty())\n
range.end.column++;\n
var text = editor.session.getTextRange(range);\n
var toggled = text.toUpperCase();\n
if (toggled == text)\n
editor.navigateRight();\n
else\n
editor.session.replace(range, toggled);\n
}, count || 1);\n
}\n
},\n
"*": {\n
fn: function(editor, range, count, param) {\n
editor.selection.selectWord();\n
editor.findNext();\n
ensureScrollMargin(editor);\n
var r = editor.selection.getRange();\n
editor.selection.setSelectionRange(r, true);\n
}\n
},\n
"#": {\n
fn: function(editor, range, count, param) {\n
editor.selection.selectWord();\n
editor.findPrevious();\n
ensureScrollMargin(editor);\n
var r = editor.selection.getRange();\n
editor.selection.setSelectionRange(r, true);\n
}\n
},\n
"m": {\n
param: true,\n
fn: function(editor, range, count, param) {\n
var s = editor.session;\n
var markers = s.vimMarkers || (s.vimMarkers = {});\n
var c = editor.getCursorPosition();\n
if (!markers[param]) {\n
markers[param] = editor.session.doc.createAnchor(c);\n
}\n
markers[param].setPosition(c.row, c.column, true);\n
}\n
},\n
"n": {\n
fn: function(editor, range, count, param) {\n
var options = editor.getLastSearchOptions();\n
options.backwards = false;\n
\n
editor.selection.moveCursorRight();\n
editor.selection.clearSelection();\n
editor.findNext(options);\n
\n
ensureScrollMargin(editor);\n
var r = editor.selection.getRange();\n
r.end.row = r.start.row;\n
r.end.column = r.start.column;\n
editor.selection.setSelectionRange(r, true);\n
}\n
},\n
"N": {\n
fn: function(editor, range, count, param) {\n
var options = editor.getLastSearchOptions();\n
options.backwards = true;\n
\n
editor.findPrevious(options);\n
ensureScrollMargin(editor);\n
var r = editor.selection.getRange();\n
r.end.row = r.start.row;\n
r.end.column = r.start.column;\n
editor.selection.setSelectionRange(r, true);\n
}\n
},\n
"v": {\n
fn: function(editor, range, count, param) {\n
editor.selection.selectRight();\n
util.visualMode(editor, false);\n
},\n
acceptsMotion: true\n
},\n
"V": {\n
fn: function(editor, range, count, param) {\n
var row = editor.getCursorPosition().row;\n
editor.selection.clearSelection();\n
editor.selection.moveCursorTo(row, 0);\n
editor.selection.selectLineEnd();\n
editor.selection.visualLineStart = row;\n
\n
util.visualMode(editor, true);\n
},\n
acceptsMotion: true\n
},\n
"Y": {\n
fn: function(editor, range, count, param) {\n
util.copyLine(editor);\n
}\n
},\n
"p": {\n
fn: function(editor, range, count, param) {\n
var defaultReg = registers._default;\n
\n
editor.setOverwrite(false);\n
if (defaultReg.isLine) {\n
var pos = editor.getCursorPosition();\n
pos.column = editor.session.getLine(pos.row).length;\n
var text = lang.stringRepeat("\\n" + defaultReg.text, count || 1);\n
editor.session.insert(pos, text);\n
editor.moveCursorTo(pos.row + 1, 0);\n
}\n
else {\n
editor.navigateRight();\n
editor.insert(lang.stringRepeat(defaultReg.text, count || 1));\n
editor.navigateLeft();\n
}\n
editor.setOverwrite(true);\n
editor.selection.clearSelection();\n
}\n
},\n
"P": {\n
fn: function(editor, range, count, param) {\n
var defaultReg = registers._default;\n
editor.setOverwrite(false);\n
\n
if (defaultReg.isLine) {\n
var pos = editor.getCursorPosition();\n
pos.column = 0;\n
var text = lang.stringRepeat(defaultReg.text + "\\n", count || 1);\n
editor.session.insert(pos, text);\n
editor.moveCursorToPosition(pos);\n
}\n
else {\n
editor.insert(lang.stringRepeat(defaultReg.text, count || 1));\n
}\n
editor.setOverwrite(true);\n
editor.selection.clearSelection();\n
}\n
},\n
"J": {\n
fn: function(editor, range, count, param) {\n
var session = editor.session;\n
range = editor.getSelectionRange();\n
var pos = {row: range.start.row, column: range.start.column};\n
count = count || range.end.row - range.start.row;\n
var maxRow = Math.min(pos.row + (count || 1), session.getLength() - 1);\n
\n
range.start.column = session.getLine(pos.row).length;\n
range.end.column = session.getLine(maxRow).length;\n
range.end.row = maxRow;\n
\n
var text = "";\n
for (var i = pos.row; i < maxRow; i++) {\n
var nextLine = session.getLine(i + 1);\n
text += " " + /^\\s*(.*)$/.exec(nextLine)[1] || "";\n
}\n
\n
session.replace(range, text);\n
editor.moveCursorTo(pos.row, pos.column);\n
}\n
},\n
"u": {\n
fn: function(editor, range, count, param) {\n
count = parseInt(count || 1, 10);\n
for (var i = 0; i < count; i++) {\n
editor.undo();\n
}\n
editor.selection.clearSelection();\n
}\n
},\n
"ctrl-r": {\n
fn: function(editor, range, count, param) {\n
count = parseInt(count || 1, 10);\n
for (var i = 0; i < count; i++) {\n
editor.redo();\n
}\n
editor.selection.clearSelection();\n
}\n
},\n
":": {\n
fn: function(editor, range, count, param) {\n
var val = ":";\n
if (count > 1)\n
val = ".,.+" + count + val;\n
if (editor.showCommandLine)\n
editor.showCommandLine(val);\n
}\n
},\n
"/": {\n
fn: function(editor, range, count, param) {\n
if (editor.showCommandLine)\n
editor.showCommandLine("/");\n
}\n
},\n
"?": {\n
fn: function(editor, range, count, param) {\n
if (editor.showCommandLine)\n
editor.showCommandLine("?");\n
}\n
},\n
".": {\n
fn: function(editor, range, count, param) {\n
util.onInsertReplaySequence = inputBuffer.lastInsertCommands;\n
var previous = inputBuffer.previous;\n
if (previous) // If there is a previous action\n
inputBuffer.exec(editor, previous.action, previous.param);\n
}\n
},\n
"ctrl-x": {\n
fn: function(editor, range, count, param) {\n
editor.modifyNumber(-(count || 1));\n
}\n
},\n
"ctrl-a": {\n
fn: function(editor, range, count, param) {\n
editor.modifyNumber(count || 1);\n
}\n
}\n
};\n
\n
var inputBuffer = exports.inputBuffer = {\n
accepting: [NUMBER, OPERATOR, MOTION, ACTION],\n
currentCmd: null,\n
currentCount: "",\n
status: "",\n
operator: null,\n
motion: null,\n
\n
lastInsertCommands: [],\n
\n
push: function(editor, ch, keyId) {\n
var status = this.status;\n
var isKeyHandled = true;\n
this.idle = false;\n
var wObj = this.waitingForParam;\n
if (/^numpad\\d+$/i.test(ch))\n
ch = ch.substr(6);\n
\n
if (wObj) {\n
this.exec(editor, wObj, ch);\n
}\n
else if (!(ch === "0" && !this.currentCount.length) &&\n
(/^\\d+$/.test(ch) && this.isAccepting(NUMBER))) {\n
this.currentCount += ch;\n
this.currentCmd = NUMBER;\n
this.accepting = [NUMBER, OPERATOR, MOTION, ACTION];\n
}\n
else if (!this.operator && this.isAccepting(OPERATOR) && operators[ch]) {\n
this.operator = {\n
ch: ch,\n
count: this.getCount()\n
};\n
this.currentCmd = OPERATOR;\n
this.accepting = [NUMBER, MOTION, ACTION];\n
this.exec(editor, { operator: this.operator });\n
}\n
else if (motions[ch] && this.isAccepting(MOTION)) {\n
this.currentCmd = MOTION;\n
\n
var ctx = {\n
operator: this.operator,\n
motion: {\n
ch: ch,\n
count: this.getCount()\n
}\n
};\n
\n
if (motions[ch].param)\n
this.waitForParam(ctx);\n
else\n
this.exec(editor, ctx);\n
}\n
else if (alias[ch] && this.isAccepting(MOTION)) {\n
alias[ch].operator.count = this.getCount();\n
this.exec(editor, alias[ch]);\n
}\n
else if (actions[ch] && this.isAccepting(ACTION)) {\n
var actionObj = {\n
action: {\n
fn: actions[ch].fn,\n
count: this.getCount()\n
}\n
};\n
\n
if (actions[ch].param) {\n
this.waitForParam(actionObj);\n
}\n
else {\n
this.exec(editor, actionObj);\n
}\n
\n
if (actions[ch].acceptsMotion)\n
this.idle = false;\n
}\n
else if (this.operator) {\n
this.operator.count = this.getCount();\n
this.exec(editor, { operator: this.operator }, ch);\n
}\n
else {\n
isKeyHandled = ch.length == 1;\n
this.reset();\n
}\n
\n
if (this.waitingForParam || this.motion || this.operator) {\n
this.status += ch;\n
} else if (this.currentCount) {\n
this.status = this.currentCount;\n
} else if (this.status) {\n
this.status = "";\n
}\n
if (this.status != status)\n
editor._emit("changeStatus");\n
return isKeyHandled;\n
},\n
\n
waitForParam: function(cmd) {\n
this.waitingForParam = cmd;\n
},\n
\n
getCount: function() {\n
var count = this.currentCount;\n
this.currentCount = "";\n
return count && parseInt(count, 10);\n
},\n
\n
exec: function(editor, action, param) {\n
var m = action.motion;\n
var o = action.operator;\n
var a = action.action;\n
\n
if (!param)\n
param = action.param;\n
\n
if (o) {\n
this.previous = {\n
action: action,\n
param: param\n
};\n
}\n
\n
if (o && !editor.selection.isEmpty()) {\n
if (operators[o.ch].selFn) {\n
operators[o.ch].selFn(editor, editor.getSelectionRange(), o.count, param);\n
this.reset();\n
}\n
return;\n
}\n
else if (!m && !a && o && param) {\n
operators[o.ch].fn(editor, null, o.count, param);\n
this.reset();\n
}\n
else if (m) {\n
var run = function(fn) {\n
if (fn && typeof fn === "function") { // There should always be a motion\n
if (m.count && !motionObj.handlesCount)\n
repeat(fn, m.count, [editor, null, m.count, param]);\n
else\n
fn(editor, null, m.count, param);\n
}\n
};\n
\n
var motionObj = motions[m.ch];\n
var selectable = motionObj.sel;\n
\n
if (!o) {\n
if ((util.onVisualMode || util.onVisualLineMode) && selectable)\n
run(motionObj.sel);\n
else\n
run(motionObj.nav);\n
}\n
else if (selectable) {\n
repeat(function() {\n
run(motionObj.sel);\n
operators[o.ch].fn(editor, editor.getSelectionRange(), o.count, param);\n
}, o.count || 1);\n
}\n
this.reset();\n
}\n
else if (a) {\n
a.fn(editor, editor.getSelectionRange(), a.count, param);\n
this.reset();\n
}\n
handleCursorMove(editor);\n
},\n
\n
isAccepting: function(type) {\n
return this.accepting.indexOf(type) !== -1;\n
},\n
\n
reset: function() {\n
this.operator = null;\n
this.motion = null;\n
this.currentCount = "";\n
this.status = "";\n
this.accepting = [NUMBER, OPERATOR, MOTION, ACTION];\n
this.idle = true;\n
this.waitingForParam = null;\n
}\n
};\n
\n
function setPreviousCommand(fn) {\n
inputBuffer.previous = { action: { action: { fn: fn } } };\n
}\n
\n
exports.coreCommands = {\n
start: {\n
exec: function start(editor) {\n
util.insertMode(editor);\n
setPreviousCommand(start);\n
}\n
},\n
startBeginning: {\n
exec: function startBeginning(editor) {\n
editor.navigateLineStart();\n
util.insertMode(editor);\n
setPreviousCommand(startBeginning);\n
}\n
},\n
stop: {\n
exec: function stop(editor) {\n
inputBuffer.reset();\n
util.onVisualMode = false;\n
util.onVisualLineMode = false;\n
inputBuffer.lastInsertCommands = util.normalMode(editor);\n
}\n
},\n
append: {\n
exec: function append(editor) {\n
var pos = editor.getCursorPosition();\n
var lineLen = editor.session.getLine(pos.row).length;\n
if (lineLen)\n
editor.navigateRight();\n
util.insertMode(editor);\n
setPreviousCommand(append);\n
}\n
},\n
appendEnd: {\n
exec: function appendEnd(editor) {\n
editor.navigateLineEnd();\n
util.insertMode(editor);\n
setPreviousCommand(appendEnd);\n
}\n
}\n
};\n
\n
var handleCursorMove = exports.onCursorMove = function(editor, e) {\n
if (util.currentMode === \'insert\' || handleCursorMove.running)\n
return;\n
else if(!editor.selection.isEmpty()) {\n
handleCursorMove.running = true;\n
if (util.onVisualLineMode) {\n
var originRow = editor.selection.visualLineStart;\n
var cursorRow = editor.getCursorPosition().row;\n
if(originRow <= cursorRow) {\n
var endLine = editor.session.getLine(cursorRow);\n
editor.selection.clearSelection();\n
editor.selection.moveCursorTo(originRow, 0);\n
editor.selection.selectTo(cursorRow, endLine.length);\n
} else {\n
var endLine = editor.session.getLine(originRow);\n
editor.selection.clearSelection();\n
editor.selection.moveCursorTo(originRow, endLine.length);\n
editor.selection.selectTo(cursorRow, 0);\n
}\n
}\n
handleCursorMove.running = false;\n
return;\n
}\n
else {\n
if (e && (util.onVisualLineMode || util.onVisualMode)) {\n
editor.selection.clearSelection();\n
util.normalMode(editor);\n
}\n
\n
handleCursorMove.running = true;\n
var pos = editor.getCursorPosition();\n
var lineLen = editor.session.getLine(pos.row).length;\n
\n
if (lineLen && pos.column === lineLen)\n
editor.navigateLeft();\n
handleCursorMove.running = false;\n
}\n
};\n
});\n
define(\'ace/keyboard/vim/maps/util\', [\'require\', \'exports\', \'module\' , \'ace/keyboard/vim/registers\', \'ace/lib/dom\'], function(require, exports, module) {\n
var registers = require("../registers");\n
\n
var dom = require("../../../lib/dom");\n
dom.importCssString(\'.insert-mode .ace_cursor{\\\n
border-left: 2px solid #333333;\\\n
}\\\n
.ace_dark.insert-mode .ace_cursor{\\\n
border-left: 2px solid #eeeeee;\\\n
}\\\n
.normal-mode .ace_cursor{\\\n
border: 0!important;\\\n
background-color: red;\\\n
opacity: 0.5;\\\n
}\', \'vimMode\');\n
\n
module.exports = {\n
onVisualMode: false,\n
onVisualLineMode: false,\n
currentMode: \'normal\',\n
noMode: function(editor) {\n
editor.unsetStyle(\'insert-mode\');\n
editor.unsetStyle(\'normal-mode\');\n
if (editor.commands.recording)\n
editor.commands.toggleRecording(editor);\n
editor.setOverwrite(false);\n
},\n
insertMode: function(editor) {\n
this.currentMode = \'insert\';\n
editor.setStyle(\'insert-mode\');\n
editor.unsetStyle(\'normal-mode\');\n
\n
editor.setOverwrite(false);\n
editor.keyBinding.$data.buffer = "";\n
editor.keyBinding.$data.state = "insertMode";\n
this.onVisualMode = false;\n
this.onVisualLineMode = false;\n
if(this.onInsertReplaySequence) {\n
editor.commands.macro = this.onInsertReplaySequence;\n
editor.commands.replay(editor);\n
this.onInsertReplaySequence = null;\n
this.normalMode(editor);\n
} else {\n
editor._emit("changeStatus");\n
if(!editor.commands.recording)\n
editor.commands.toggleRecording(editor);\n
}\n
},\n
normalMode: function(editor) {\n
this.currentMode = \'normal\';\n
\n
editor.unsetStyle(\'insert-mode\');\n
editor.setStyle(\'normal-mode\');\n
editor.clearSelection();\n
\n
var pos;\n
if (!editor.getOverwrite()) {\n
pos = editor.getCursorPosition();\n
if (pos.column > 0)\n
editor.navigateLeft();\n
}\n
\n
editor.setOverwrite(true);\n
editor.keyBinding.$data.buffer = "";\n
editor.keyBinding.$data.state = "start";\n
this.onVisualMode = false;\n
this.onVisualLineMode = false;\n
editor._emit("changeStatus");\n
if (editor.commands.recording) {\n
editor.commands.toggleRecording(editor);\n
return editor.commands.macro;\n
}\n
else {\n
return [];\n
}\n
},\n
visualMode: function(editor, lineMode) {\n
if (\n
(this.onVisualLineMode && lineMode)\n
|| (this.onVisualMode && !lineMode)\n
) {\n
this.normalMode(editor);\n
return;\n
}\n
\n
editor.setStyle(\'insert-mode\');\n
editor.unsetStyle(\'normal-mode\');\n
\n
editor._emit("changeStatus");\n
if (lineMode) {\n
this.onVisualLineMode = true;\n
} else {\n
this.onVisualMode = true;\n
this.onVisualLineMode = false;\n
}\n
},\n
getRightNthChar: function(editor, cursor, ch, n) {\n
var line = editor.getSession().getLine(cursor.row);\n
var matches = line.substr(cursor.column + 1).split(ch);\n
\n
return n < matches.length ? matches.slice(0, n).join(ch).length : null;\n
},\n
getLeftNthChar: function(editor, cursor, ch, n) {\n
var line = editor.getSession().getLine(cursor.row);\n
var matches = line.substr(0, cursor.column).split(ch);\n
\n
return n < matches.length ? matches.slice(-1 * n).join(ch).length : null;\n
},\n
toRealChar: function(ch) {\n
if (ch.length === 1)\n
return ch;\n
\n
if (/^shift-./.test(ch))\n
return ch[ch.length - 1].toUpperCase();\n
else\n
return "";\n
},\n
copyLine: function(editor) {\n
var pos = editor.getCursorPosition();\n
editor.selection.clearSelection();\n
editor.moveCursorTo(pos.row, pos.column);\n
editor.selection.selectLine();\n
registers._default.isLine = true;\n
registers._default.text = editor.getCopyText().replace(/\\n$/, "");\n
editor.selection.clearSelection();\n
editor.moveCursorTo(pos.row, pos.column);\n
}\n
};\n
});\n
\n
define(\'ace/keyboard/vim/registers\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
\n
"never use strict";\n
\n
module.exports = {\n
_default: {\n
text: "",\n
isLine: false\n
}\n
};\n
\n
});\n
\n
\n
define(\'ace/keyboard/vim/maps/motions\', [\'require\', \'exports\', \'module\' , \'ace/keyboard/vim/maps/util\', \'ace/search\', \'ace/range\'], function(require, exports, module) {\n
\n
\n
var util = require("./util");\n
\n
var keepScrollPosition = function(editor, fn) {\n
var scrollTopRow = editor.renderer.getScrollTopRow();\n
var initialRow = editor.getCursorPosition().row;\n
var diff = initialRow - scrollTopRow;\n
fn && fn.call(editor);\n
editor.renderer.scrollToRow(editor.getCursorPosition().row - diff);\n
};\n
\n
function Motion(m) {\n
if (typeof m == "function") {\n
var getPos = m;\n
m = this;\n
} else {\n
var getPos = m.getPos;\n
}\n
m.nav = function(editor, range, count, param) {\n
var a = getPos(editor, range, count, param, false);\n
if (!a)\n
return;\n
editor.clearSelection();\n
editor.moveCursorTo(a.row, a.column);\n
};\n
m.sel = function(editor, range, count, param) {\n
var a = getPos(editor, range, count, param, true);\n
if (!a)\n
return;\n
editor.selection.selectTo(a.row, a.column);\n
};\n
return m;\n
}\n
\n
var nonWordRe = /[\\s.\\/\\\\()\\"\'-:,.;<>~!@#$%^&*|+=\\[\\]{}`~?]/;\n
var wordSeparatorRe = /[.\\/\\\\()\\"\'-:,.;<>~!@#$%^&*|+=\\[\\]{}`~?]/;\n
var whiteRe = /\\s/;\n
var StringStream = function(editor, cursor) {\n
var sel = editor.selection;\n
this.range = sel.getRange();\n
cursor = cursor || sel.selectionLead;\n
this.row = cursor.row;\n
this.col = cursor.column;\n
var line = editor.session.getLine(this.row);\n
var maxRow = editor.session.getLength();\n
this.ch = line[this.col] || \'\\n\';\n
this.skippedLines = 0;\n
\n
this.next = function() {\n
this.ch = line[++this.col] || this.handleNewLine(1);\n
return this.ch;\n
};\n
this.prev = function() {\n
this.ch = line[--this.col] || this.handleNewLine(-1);\n
return this.ch;\n
};\n
this.peek = function(dir) {\n
var ch = line[this.col + dir];\n
if (ch)\n
return ch;\n
if (dir == -1)\n
return \'\\n\';\n
if (this.col == line.length - 1)\n
return \'\\n\';\n
return editor.session.getLine(this.row + 1)[0] || \'\\n\';\n
};\n
\n
this.handleNewLine = function(dir) {\n
if (dir == 1){\n
if (this.col == line.length)\n
return \'\\n\';\n
if (this.row == maxRow - 1)\n
return \'\';\n
this.col = 0;\n
this.row ++;\n
line = editor.session.getLine(this.row);\n
this.skippedLines++;\n
return line[0] || \'\\n\';\n
}\n
if (dir == -1) {\n
if (this.row === 0)\n
return \'\';\n
this.row --;\n
line = editor.session.getLine(this.row);\n
this.col = line.length;\n
this.skippedLines--;\n
return \'\\n\';\n
}\n
};\n
this.debug = function() {\n
console.log(line.substring(0, this.col)+\'|\'+this.ch+\'\\\'\'+this.col+\'\\\'\'+line.substr(this.col+1));\n
};\n
};\n
\n
var Search = require("../../../search").Search;\n
var search = new Search();\n
\n
function find(editor, needle, dir) {\n
search.$options.needle = needle;\n
search.$options.backwards = dir == -1;\n
return search.find(editor.session);\n
}\n
\n
var Range = require("../../../range").Range;\n
\n
var LAST_SEARCH_MOTION = {};\n
\n
module.exports = {\n
"w": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
\n
if (str.ch && wordSeparatorRe.test(str.ch)) {\n
while (str.ch && wordSeparatorRe.test(str.ch))\n
str.next();\n
} else {\n
while (str.ch && !nonWordRe.test(str.ch))\n
str.next();\n
}\n
while (str.ch && whiteRe.test(str.ch) && str.skippedLines < 2)\n
str.next();\n
\n
str.skippedLines == 2 && str.prev();\n
return {column: str.col, row: str.row};\n
}),\n
"W": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
while(str.ch && !(whiteRe.test(str.ch) && !whiteRe.test(str.peek(1))) && str.skippedLines < 2)\n
str.next();\n
if (str.skippedLines == 2)\n
str.prev();\n
else\n
str.next();\n
\n
return {column: str.col, row: str.row};\n
}),\n
"b": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
\n
str.prev();\n
while (str.ch && whiteRe.test(str.ch) && str.skippedLines > -2)\n
str.prev();\n
\n
if (str.ch && wordSeparatorRe.test(str.ch)) {\n
while (str.ch && wordSeparatorRe.test(str.ch))\n
str.prev();\n
} else {\n
while (str.ch && !nonWordRe.test(str.ch))\n
str.prev();\n
}\n
str.ch && str.next();\n
return {column: str.col, row: str.row};\n
}),\n
"B": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
str.prev();\n
while(str.ch && !(!whiteRe.test(str.ch) && whiteRe.test(str.peek(-1))) && str.skippedLines > -2)\n
str.prev();\n
\n
if (str.skippedLines == -2)\n
str.next();\n
\n
return {column: str.col, row: str.row};\n
}),\n
"e": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
\n
str.next();\n
while (str.ch && whiteRe.test(str.ch))\n
str.next();\n
\n
if (str.ch && wordSeparatorRe.test(str.ch)) {\n
while (str.ch && wordSeparatorRe.test(str.ch))\n
str.next();\n
} else {\n
while (str.ch && !nonWordRe.test(str.ch))\n
str.next();\n
}\n
str.ch && str.prev();\n
return {column: str.col, row: str.row};\n
}),\n
"E": new Motion(function(editor) {\n
var str = new StringStream(editor);\n
str.next();\n
while(str.ch && !(!whiteRe.test(str.ch) && whiteRe.test(str.peek(1))))\n
str.next();\n
\n
return {column: str.col, row: str.row};\n
}),\n
\n
"l": {\n
nav: function(editor) {\n
var pos = editor.getCursorPosition();\n
var col = pos.column;\n
var lineLen = editor.session.getLine(pos.row).length;\n
if (lineLen && col !== lineLen)\n
editor.navigateRight();\n
},\n
sel: function(editor) {\n
var pos = editor.getCursorPosition();\n
var col = pos.column;\n
var lineLen = editor.session.getLine(pos.row).length;\n
if (lineLen && col !== lineLen) //In selection mode you can select the newline\n
editor.selection.selectRight();\n
}\n
},\n
"h": {\n
nav: function(editor) {\n
var pos = editor.getCursorPosition();\n
if (pos.column > 0)\n
editor.navigateLeft();\n
},\n
sel: function(editor) {\n
var pos = editor.getCursorPosition();\n
if (pos.column > 0)\n
editor.selection.selectLeft();\n
}\n
},\n
"H": {\n
nav: function(editor) {\n
var row = editor.renderer.getScrollTopRow();\n
editor.moveCursorTo(row);\n
},\n
sel: function(editor) {\n
var row = editor.renderer.getScrollTopRow();\n
editor.selection.selectTo(row);\n
}\n
},\n
"M": {\n
nav: function(editor) {\n
var topRow = editor.renderer.getScrollTopRow();\n
var bottomRow = editor.renderer.getScrollBottomRow();\n
var row = topRow + ((bottomRow - topRow) / 2);\n
editor.moveCursorTo(row);\n
},\n
sel: function(editor) {\n
var topRow = editor.renderer.getScrollTopRow();\n
var bottomRow = editor.renderer.getScrollBottomRow();\n
var row = topRow + ((bottomRow - topRow) / 2);\n
editor.selection.selectTo(row);\n
}\n
},\n
"L": {\n
nav: function(editor) {\n
var row = editor.renderer.getScrollBottomRow();\n
editor.moveCursorTo(row);\n
},\n
sel: function(editor) {\n
var row = editor.renderer.getScrollBottomRow();\n
editor.selection.selectTo(row);\n
}\n
},\n
"k": {\n
nav: function(editor) {\n
editor.navigateUp();\n
},\n
sel: function(editor) {\n
editor.selection.selectUp();\n
}\n
},\n
"j": {\n
nav: function(editor) {\n
editor.navigateDown();\n
},\n
sel: function(editor) {\n
editor.selection.selectDown();\n
}\n
},\n
\n
"i": {\n
param: true,\n
sel: function(editor, range, count, param) {\n
switch (param) {\n
case "w":\n
editor.selection.selectWord();\n
break;\n
case "W":\n
editor.selection.selectAWord();\n
break;\n
case "(":\n
case "{":\n
case "[":\n
var cursor = editor.getCursorPosition();\n
var end = editor.session.$findClosingBracket(param, cursor, /paren/);\n
if (!end)\n
return;\n
var start = editor.session.$findOpeningBracket(editor.session.$brackets[param], cursor, /paren/);\n
if (!start)\n
return;\n
start.column ++;\n
editor.selection.setSelectionRange(Range.fromPoints(start, end));\n
break;\n
case "\'":\n
case \'"\':\n
case "/":\n
var end = find(editor, param, 1);\n
if (!end)\n
return;\n
var start = find(editor, param, -1);\n
if (!start)\n
return;\n
editor.selection.setSelectionRange(Range.fromPoints(start.end, end.start));\n
break;\n
}\n
}\n
},\n
"a": {\n
param: true,\n
sel: function(editor, range, count, param) {\n
switch (param) {\n
case "w":\n
editor.selection.selectAWord();\n
break;\n
case "W":\n
editor.selection.selectAWord();\n
break;\n
case "(":\n
case "{":\n
case "[":\n
var cursor = editor.getCursorPosition();\n
var end = editor.session.$findClosingBracket(param, cursor, /paren/);\n
if (!end)\n
return;\n
var start = editor.session.$findOpeningBracket(editor.session.$brackets[param], cursor, /paren/);\n
if (!start)\n
return;\n
end.column ++;\n
editor.selection.setSelectionRange(Range.fromPoints(start, end));\n
break;\n
case "\'":\n
case "\\"":\n
case "/":\n
var end = find(editor, param, 1);\n
if (!end)\n
return;\n
var start = find(editor, param, -1);\n
if (!start)\n
return;\n
end.column ++;\n
editor.selection.setSelectionRange(Range.fromPoints(start.start, end.end));\n
break;\n
}\n
}\n
},\n
\n
"f": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel, isRepeat) {\n
if (!isRepeat)\n
LAST_SEARCH_MOTION = {ch: "f", param: param};\n
var cursor = editor.getCursorPosition();\n
var column = util.getRightNthChar(editor, cursor, param, count || 1);\n
\n
if (typeof column === "number") {\n
cursor.column += column + (isSel ? 2 : 1);\n
return cursor;\n
}\n
}\n
}),\n
"F": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel, isRepeat) {\n
if (!isRepeat)\n
LAST_SEARCH_MOTION = {ch: "F", param: param};\n
var cursor = editor.getCursorPosition();\n
var column = util.getLeftNthChar(editor, cursor, param, count || 1);\n
\n
if (typeof column === "number") {\n
cursor.column -= column + 1;\n
return cursor;\n
}\n
}\n
}),\n
"t": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel, isRepeat) {\n
if (!isRepeat)\n
LAST_SEARCH_MOTION = {ch: "t", param: param};\n
var cursor = editor.getCursorPosition();\n
var column = util.getRightNthChar(editor, cursor, param, count || 1);\n
\n
if (isRepeat && column == 0 && !(count > 1))\n
var column = util.getRightNthChar(editor, cursor, param, 2);\n
\n
if (typeof column === "number") {\n
cursor.column += column + (isSel ? 1 : 0);\n
return cursor;\n
}\n
}\n
}),\n
"T": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel, isRepeat) {\n
if (!isRepeat)\n
LAST_SEARCH_MOTION = {ch: "T", param: param};\n
var cursor = editor.getCursorPosition();\n
var column = util.getLeftNthChar(editor, cursor, param, count || 1);\n
\n
if (isRepeat && column == 0 && !(count > 1))\n
var column = util.getLeftNthChar(editor, cursor, param, 2);\n
\n
if (typeof column === "number") {\n
cursor.column -= column;\n
return cursor;\n
}\n
}\n
}),\n
";": new Motion({\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel) {\n
var ch = LAST_SEARCH_MOTION.ch;\n
if (!ch)\n
return;\n
return module.exports[ch].getPos(\n
editor, range, count, LAST_SEARCH_MOTION.param, isSel, true\n
);\n
}\n
}),\n
",": new Motion({\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel) {\n
var ch = LAST_SEARCH_MOTION.ch;\n
if (!ch)\n
return;\n
var up = ch.toUpperCase();\n
ch = ch === up ? ch.toLowerCase() : up;\n
\n
return module.exports[ch].getPos(\n
editor, range, count, LAST_SEARCH_MOTION.param, isSel, true\n
);\n
}\n
}),\n
\n
"^": {\n
nav: function(editor) {\n
editor.navigateLineStart();\n
},\n
sel: function(editor) {\n
editor.selection.selectLineStart();\n
}\n
},\n
"$": {\n
nav: function(editor) {\n
editor.navigateLineEnd();\n
},\n
sel: function(editor) {\n
editor.selection.selectLineEnd();\n
}\n
},\n
"0": new Motion(function(ed) {\n
return {row: ed.selection.lead.row, column: 0};\n
}),\n
"G": {\n
nav: function(editor, range, count, param) {\n
if (!count && count !== 0) { // Stupid JS\n
count = editor.session.getLength();\n
}\n
editor.gotoLine(count);\n
},\n
sel: function(editor, range, count, param) {\n
if (!count && count !== 0) { // Stupid JS\n
count = editor.session.getLength();\n
}\n
editor.selection.selectTo(count, 0);\n
}\n
},\n
"g": {\n
param: true,\n
nav: function(editor, range, count, param) {\n
switch(param) {\n
case "m":\n
console.log("Middle line");\n
break;\n
case "e":\n
console.log("End of prev word");\n
break;\n
case "g":\n
editor.gotoLine(count || 0);\n
case "u":\n
editor.gotoLine(count || 0);\n
case "U":\n
editor.gotoLine(count || 0);\n
}\n
},\n
sel: function(editor, range, count, param) {\n
switch(param) {\n
case "m":\n
console.log("Middle line");\n
break;\n
case "e":\n
console.log("End of prev word");\n
break;\n
case "g":\n
editor.selection.selectTo(count || 0, 0);\n
}\n
}\n
},\n
"o": {\n
nav: function(editor, range, count, param) {\n
count = count || 1;\n
var content = "";\n
while (0 < count--)\n
content += "\\n";\n
\n
if (content.length) {\n
editor.navigateLineEnd()\n
editor.insert(content);\n
util.insertMode(editor);\n
}\n
}\n
},\n
"O": {\n
nav: function(editor, range, count, param) {\n
var row = editor.getCursorPosition().row;\n
count = count || 1;\n
var content = "";\n
while (0 < count--)\n
content += "\\n";\n
\n
if (content.length) {\n
if(row > 0) {\n
editor.navigateUp();\n
editor.navigateLineEnd()\n
editor.insert(content);\n
} else {\n
editor.session.insert({row: 0, column: 0}, content);\n
editor.navigateUp();\n
}\n
util.insertMode(editor);\n
}\n
}\n
},\n
"%": new Motion(function(editor){\n
var brRe = /[\\[\\]{}()]/g;\n
var cursor = editor.getCursorPosition();\n
var ch = editor.session.getLine(cursor.row)[cursor.column];\n
if (!brRe.test(ch)) {\n
var range = find(editor, brRe);\n
if (!range)\n
return;\n
cursor = range.start;\n
}\n
var match = editor.session.findMatchingBracket({\n
row: cursor.row,\n
column: cursor.column + 1\n
});\n
\n
return match;\n
}),\n
"{": new Motion(function(ed) {\n
var session = ed.session;\n
var row = session.selection.lead.row;\n
while(row > 0 && !/\\S/.test(session.getLine(row)))\n
row--;\n
while(/\\S/.test(session.getLine(row)))\n
row--;\n
return {column: 0, row: row};\n
}),\n
"}": new Motion(function(ed) {\n
var session = ed.session;\n
var l = session.getLength();\n
var row = session.selection.lead.row;\n
while(row < l && !/\\S/.test(session.getLine(row)))\n
row++;\n
while(/\\S/.test(session.getLine(row)))\n
row++;\n
return {column: 0, row: row};\n
}),\n
"ctrl-d": {\n
nav: function(editor, range, count, param) {\n
editor.selection.clearSelection();\n
keepScrollPosition(editor, editor.gotoPageDown);\n
},\n
sel: function(editor, range, count, param) {\n
keepScrollPosition(editor, editor.selectPageDown);\n
}\n
},\n
"ctrl-u": {\n
nav: function(editor, range, count, param) {\n
editor.selection.clearSelection();\n
keepScrollPosition(editor, editor.gotoPageUp);\n
},\n
sel: function(editor, range, count, param) {\n
keepScrollPosition(editor, editor.selectPageUp);\n
}\n
},\n
"`": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel) {\n
var s = editor.session;\n
var marker = s.vimMarkers && s.vimMarkers[param];\n
if (marker) {\n
return marker.getPosition();\n
}\n
}\n
}),\n
"\'": new Motion({\n
param: true,\n
handlesCount: true,\n
getPos: function(editor, range, count, param, isSel) {\n
var s = editor.session;\n
var marker = s.vimMarkers && s.vimMarkers[param];\n
if (marker) {\n
var pos = marker.getPosition();\n
var line = editor.session.getLine(pos.row); \n
pos.column = line.search(/\\S/);\n
if (pos.column == -1)\n
pos.column = line.length;\n
return pos;\n
}\n
}\n
})\n
};\n
\n
module.exports.backspace = module.exports.left = module.exports.h;\n
module.exports.space = module.exports[\'return\'] = module.exports.right = module.exports.l;\n
module.exports.up = module.exports.k;\n
module.exports.down = module.exports.j;\n
module.exports.pagedown = module.exports["ctrl-d"];\n
module.exports.pageup = module.exports["ctrl-u"];\n
\n
});\n
\n
define(\'ace/keyboard/vim/maps/operators\', [\'require\', \'exports\', \'module\' , \'ace/keyboard/vim/maps/util\', \'ace/keyboard/vim/registers\'], function(require, exports, module) {\n
\n
\n
\n
var util = require("./util");\n
var registers = require("../registers");\n
\n
module.exports = {\n
"d": {\n
selFn: function(editor, range, count, param) {\n
registers._default.text = editor.getCopyText();\n
registers._default.isLine = util.onVisualLineMode;\n
if(util.onVisualLineMode)\n
editor.removeLines();\n
else\n
editor.session.remove(range);\n
util.normalMode(editor);\n
},\n
fn: function(editor, range, count, param) {\n
count = count || 1;\n
switch (param) {\n
case "d":\n
registers._default.text = "";\n
registers._default.isLine = true;\n
for (var i = 0; i < count; i++) {\n
editor.selection.selectLine();\n
registers._default.text += editor.getCopyText();\n
var selRange = editor.getSelectionRange();\n
if (!selRange.isMultiLine()) {\n
var row = selRange.start.row - 1;\n
var col = editor.session.getLine(row).length\n
selRange.setStart(row, col);\n
editor.session.remove(selRange);\n
editor.selection.clearSelection();\n
break;\n
}\n
editor.session.remove(selRange);\n
editor.selection.clearSelection();\n
}\n
registers._default.text = registers._default.text.replace(/\\n$/, "");\n
break;\n
default:\n
if (range) {\n
editor.selection.setSelectionRange(range);\n
registers._default.text = editor.getCopyText();\n
registers._default.isLine = false;\n
editor.session.remove(range);\n
editor.selection.clearSelection();\n
}\n
}\n
}\n
},\n
"c": {\n
selFn: function(editor, range, count, param) {\n
editor.session.remove(range);\n
util.insertMode(editor);\n
},\n
fn: function(editor, range, count, param) {\n
count = count || 1;\n
switch (param) {\n
case "c":\n
for (var i = 0; i < count; i++) {\n
editor.removeLines();\n
util.insertMode(editor);\n
}\n
\n
break;\n
default:\n
if (range) {\n
editor.session.remove(range);\n
util.insertMode(editor);\n
}\n
}\n
}\n
},\n
"y": {\n
selFn: function(editor, range, count, param) {\n
registers._default.text = editor.getCopyText();\n
registers._default.isLine = util.onVisualLineMode;\n
editor.selection.clearSelection();\n
util.normalMode(editor);\n
},\n
fn: function(editor, range, count, param) {\n
count = count || 1;\n
switch (param) {\n
case "y":\n
var pos = editor.getCursorPosition();\n
editor.selection.selectLine();\n
for (var i = 0; i < count - 1; i++) {\n
editor.selection.moveCursorDown();\n
}\n
registers._default.text = editor.getCopyText().replace(/\\n$/, "");\n
editor.selection.clearSelection();\n
registers._default.isLine = true;\n
editor.moveCursorToPosition(pos);\n
break;\n
default:\n
if (range) {\n
var pos = editor.getCursorPosition();\n
editor.selection.setSelectionRange(range);\n
registers._default.text = editor.getCopyText();\n
registers._default.isLine = false;\n
editor.selection.clearSelection();\n
editor.moveCursorTo(pos.row, pos.column);\n
}\n
}\n
}\n
},\n
">": {\n
selFn: function(editor, range, count, param) {\n
count = count || 1;\n
for (var i = 0; i < count; i++) {\n
editor.indent();\n
}\n
util.normalMode(editor);\n
},\n
fn: function(editor, range, count, param) {\n
count = parseInt(count || 1, 10);\n
switch (param) {\n
case ">":\n
var pos = editor.getCursorPosition();\n
editor.selection.selectLine();\n
for (var i = 0; i < count - 1; i++) {\n
editor.selection.moveCursorDown();\n
}\n
editor.indent();\n
editor.selection.clearSelection();\n
editor.moveCursorToPosition(pos);\n
editor.navigateLineEnd();\n
editor.navigateLineStart();\n
break;\n
}\n
}\n
},\n
"<": {\n
selFn: function(editor, range, count, param) {\n
count = count || 1;\n
for (var i = 0; i < count; i++) {\n
editor.blockOutdent();\n
}\n
util.normalMode(editor);\n
},\n
fn: function(editor, range, count, param) {\n
count = count || 1;\n
switch (param) {\n
case "<":\n
var pos = editor.getCursorPosition();\n
editor.selection.selectLine();\n
for (var i = 0; i < count - 1; i++) {\n
editor.selection.moveCursorDown();\n
}\n
editor.blockOutdent();\n
editor.selection.clearSelection();\n
editor.moveCursorToPosition(pos);\n
editor.navigateLineEnd();\n
editor.navigateLineStart();\n
break;\n
}\n
}\n
}\n
};\n
});\n
\n
"use strict"\n
\n
define(\'ace/keyboard/vim/maps/aliases\', [\'require\', \'exports\', \'module\' ], function(require, exports, module) {\n
module.exports = {\n
"x": {\n
operator: {\n
ch: "d",\n
count: 1\n
},\n
motion: {\n
ch: "l",\n
count: 1\n
}\n
},\n
"X": {\n
operator: {\n
ch: "d",\n
count: 1\n
},\n
motion: {\n
ch: "h",\n
count: 1\n
}\n
},\n
"D": {\n
operator: {\n
ch: "d",\n
count: 1\n
},\n
motion: {\n
ch: "$",\n
count: 1\n
}\n
},\n
"C": {\n
operator: {\n
ch: "c",\n
count: 1\n
},\n
motion: {\n
ch: "$",\n
count: 1\n
}\n
},\n
"s": {\n
operator: {\n
ch: "c",\n
count: 1\n
},\n
motion: {\n
ch: "l",\n
count: 1\n
}\n
},\n
"S": {\n
operator: {\n
ch: "c",\n
count: 1\n
},\n
param: "c"\n
}\n
};\n
});\n
\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>55892</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>keybinding-vim.js</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
......@@ -173,6 +173,8 @@
tal:attributes="src string:${portal_url}/ace/ace.js"></script>\n
<script type="text/javascript"\n
tal:attributes="src string:${portal_url}/ace/mode-python.js"></script>\n
<script type="text/javascript"\n
tal:attributes="src string:${portal_url}/ace/ext-settings_menu.js"></script>\n
<script type="text/javascript"\n
tal:define=\'fullscreen_button string:<input type="button" value="Fullscreen" onclick="switchToFullScreen()" class="ace_editor_action_button" />;\n
save_button string:<button class="ace_editor_save_button" onclick="saveDocument(event)"><img src="images/save2.png" width="30" height="30" border="0" /></button>;\'\n
......@@ -354,6 +356,15 @@
window.onresize = setContainerDivSize;\n
\n
ace_editor = ace.edit(\'${div_id}\');\n
\n
ace.require(\'ace/ext/settings_menu\').init(ace_editor);\n
ace_editor.commands.addCommands([{\n
name: \'showSettingsMenu\',\n
bindKey: {win: \'Alt-p\', mac: \'Alt-p\'},\n
exec: function(editor) { editor.showSettingsMenu(); },\n
readOnly: true\n
}]);\n
\n
ace_editor.resize();\n
\n
var PythonMode = require(\'ace/mode/python\').Mode;\n
......
2013-08-13 arnaud.fontaine
* ZODB Components: Add Ace Editor settings menu (Alt+p) to set up keybinding styles for example.
2013-08-13 arnaud.fontaine
* ZODB Components: Add JS file required to find text within Ace Editor.
......
11
\ No newline at end of file
12
\ No newline at end of file
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