From acce02adcd4a0b43217f0ae1b937fee04bdc2ebd Mon Sep 17 00:00:00 2001 From: bootstraponline Date: Mon, 1 Oct 2012 21:06:25 -0600 Subject: [PATCH 01/66] Fix removeLicenceComments typo. --- Makefile.dryice.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 6c55a5bd..814b1c5e 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -269,7 +269,7 @@ function buildAce(options) { copy.filter.moduleDefines, filterTextPlugin, removeUseStrict, - removeLicenceCmments + removeLicenceComments ]; if (options.noconflict) { @@ -370,7 +370,7 @@ function buildAce(options) { copy.filter.moduleDefines, filterTextPlugin, removeUseStrict, - removeLicenceCmments + removeLicenceComments ]; options.workers.forEach(function(mode) { @@ -466,7 +466,7 @@ function removeUseStrict(text) { return text.replace(/['"]use strict['"];/g, ""); } -function removeLicenceCmments(text) { +function removeLicenceComments(text) { return text.replace(/(;)\s*\/\*[\d\D]*?\*\//g, "$1"); } From 6eecc42409d0c67abd1a4275545df8d612040af5 Mon Sep 17 00:00:00 2001 From: bootstraponline Date: Mon, 1 Oct 2012 21:06:53 -0600 Subject: [PATCH 02/66] Add missing ; --- Makefile.dryice.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 814b1c5e..807058a2 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -336,7 +336,7 @@ function buildAce(options) { dest: targetDir + "/theme-" + theme + ".js" });*/ // use this instead, to not create separate modules for js and css - var themePath = ACE_HOME + "/lib/ace/theme/" + theme + var themePath = ACE_HOME + "/lib/ace/theme/" + theme; var js = fs.readFileSync(themePath + ".js", "utf8"); js = js.replace("define(", "define('ace/theme/" + theme + "', ['require', 'exports', 'module', 'ace/lib/dom'], "); From 3e5fa146a1e14e96df83ccb3fed70acf409472ae Mon Sep 17 00:00:00 2001 From: bootstraponline Date: Mon, 1 Oct 2012 21:08:56 -0600 Subject: [PATCH 03/66] Include ext in dryice. Fix #986. --- Makefile.dryice.js | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 807058a2..2239215b 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -245,6 +245,10 @@ function buildAce(options) { themes: fs.readdirSync(ACE_HOME + "/lib/ace/theme").map(function(x){ return x.slice(-3) == ".js" && x.slice(0, -3); }).filter(function(x){ return !!x; }), + extensions: fs.readdirSync(ACE_HOME + "/lib/ace/ext").map(function(x){ + if (x.slice(-3) == ".js" && !/_test/.test(x)) + return x.slice(0, -3); + }).filter(function(x){ return !!x; }), workers: ["javascript", "coffee", "css", "json", "xquery"], keybindings: ["vim", "emacs"] }; @@ -349,6 +353,21 @@ function buildAce(options) { fs.writeFileSync(targetDir + "/theme-" + theme + ".js", js); }); + console.log('# ace extensions ---------'); + + project.assumeAllFilesLoaded(); + options.extensions.forEach(function(ext) { + console.log("extensions " + ext); + copy({ + source: [{ + project: cloneProject(project), + require: [ 'ace/ext/' + ext ] + }], + filter: filters, + dest: targetDir + "/ext-" + ext + ".js" + }); + }); + console.log('# ace key bindings ---------'); // copy key bindings From 6cfe9617c2328eae6f9cbf1b8d42ef089ff8b15f Mon Sep 17 00:00:00 2001 From: bootstraponline Date: Tue, 2 Oct 2012 17:18:08 -0600 Subject: [PATCH 04/66] Fix filterTextPlugin. Code from @nightwing on #1000 --- Makefile.dryice.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 2239215b..3a9f75f1 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -478,7 +478,7 @@ function quoteString(str) { } function filterTextPlugin(text) { - return text.replace(/(['"])ace\/requirejs\/text\!/g, "$1text!"); + return text.replace(/(['"])(ace|[.\/]+?)\/requirejs\/text\!/g, "$1"); } function removeUseStrict(text) { From 2b08cebd56b2e57fb3bbb01b1ab70855c3925600 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 6 Oct 2012 14:40:13 +0400 Subject: [PATCH 05/66] do not call install on sm update --- install.js | 49 +++++++++++++++++++++++++++++-------------------- package.json | 2 +- 2 files changed, 30 insertions(+), 21 deletions(-) diff --git a/install.js b/install.js index 4f96d891..730fc12c 100644 --- a/install.js +++ b/install.js @@ -33,27 +33,36 @@ * ***** END LICENSE BLOCK ***** */ var buildAce = require("./Makefile.dryice").buildAce; - +var fs = require("fs"); var ACE_HOME = __dirname; -try { - var aceProject = { - roots: [ - ACE_HOME + '/lib', - ACE_HOME + '/demo' - ], - textPluginPattern: /^ace\/requirejs\/text!/ - }; - buildAce(aceProject, { - compress: false, - noconflict: false, - suffix: "", - compat: true, - name: "ace" - }); -} catch (e) { - console.log("--- Ace Build error ---"); - console.log(e); - process.exit(0); +function getVersion(path) { + if (fs.existsSync(path + "/.git-ref")) + return fs.readFileSync(path + "/.git-ref", "utf8"); + if (fs.existsSync(path + "/.git/ORIG_HEAD")) + return fs.readFileSync(path + "/.git/ORIG_HEAD", "utf8"); } + +if (process.argv.indexOf("-c") > 0) try { + var version = getVersion(ACE_HOME); + var oldVersion = getVersion(ACE_HOME + "/build"); + if (version && oldVersion == version) { + console.log("ace build is up to date"); + process.exit(0); + } + fs.writeFileSync(ACE_HOME + "/build/.git-ref", version, "utf8"); +} catch (e) {} + +try { + buildAce({ + compress: false, + noconflict: false, + suffix: "", + name: "ace" + }); +} catch (e) { + console.log("--- Ace Build error ---"); + console.log(e); + process.exit(0); +} \ No newline at end of file diff --git a/package.json b/package.json index 86b2fd8e..bd226318 100644 --- a/package.json +++ b/package.json @@ -29,7 +29,7 @@ }, "scripts": { "test": "node lib/ace/test/all.js", - "postinstall": "node ./install.js" + "postinstall": "node ./install.js -c" }, "config": { "github.com/sourcemint/bundler-js/0/-meta/config/0": { From 60723e3b960252e1f3f653061d6f10e0a8213582 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 6 Oct 2012 14:43:25 +0400 Subject: [PATCH 06/66] small cleanup --- Makefile.dryice.js | 84 +++++++++++++++++++++++++--------------------- 1 file changed, 45 insertions(+), 39 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 3a9f75f1..a6cb8720 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -4,7 +4,7 @@ * * Copyright (c) 2010, Ajax.org B.V. * All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * Redistributions of source code must retain the above copyright @@ -15,7 +15,7 @@ * * Neither the name of Ajax.org B.V. nor the * names of its contributors may be used to endorse or promote products * derived from this software without specific prior written permission. - * + * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE @@ -44,7 +44,7 @@ function main(args) { return "-" + x; return x; }); - + if (args[2] && (args[2][0] != "-" || args[2].indexOf("h") != -1)) type = args[2]; @@ -166,23 +166,26 @@ function demo() { ref = ""; version = ""; } - var changeComments = function(data) { - return (data - .replace(//g, "") - .replace(/PACKAGE\-\->|/g, "") + .replace(/PACKAGE\-\->| Date: Sat, 6 Oct 2012 14:48:03 +0400 Subject: [PATCH 07/66] silence annoying messages from dryice --- Makefile.dryice.js | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index a6cb8720..583e2f8c 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -429,15 +429,28 @@ var buildAce = function(options) { }); - console.log('# combining files into one ---------'); - if (options.shrinkwrap) { + console.log('# combining files into one ---------'); copy({ source: { root:targetDir, exclude:/^worker\-/ }, dest: BUILD_DIR + '/ace-min.js' }); } -} +}; + +// silence annoying messages from dryice +var buildAce = function(fn) { + return function() { + var log = console.log + console.log = function() { + if (typeof arguments[0] == "string" && /Ignoring requirement/.test(arguments[0])) + return; + log.apply(console, arguments); + } + fn.apply(null, arguments); + console.log = log; + } +}(buildAce); // TODO: replace with project.clone once it is fixed in dryice function cloneProject(project) { From 73f66d94088f42c5ab7344c61e18620794ca3f53 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 6 Oct 2012 14:54:27 +0400 Subject: [PATCH 08/66] move css strings inline to avoid problems with text plugin --- Makefile.dryice.js | 126 +++++++++++++++++++++++++++------------------ 1 file changed, 76 insertions(+), 50 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 583e2f8c..d7c31851 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -244,6 +244,33 @@ function addSuffix(options) { options.suffix += "-noconflict"; } } + +function getWriteFilters(options, projectType) { + var filters = [ + copy.filter.moduleDefines, + inlineTextModules, + removeUseStrict, + removeLicenceComments + ]; + + if (projectType == "worker") + return filters; + + if (options.noconflict) + filters.push(namespace(options.ns)); + + if (options.compress) + filters.push(copy.filter.uglifyjs); + + if (options.exportModule && projectType == "main") { + if (options.noconflict) + filters.push(exportAce(options.ns, options.exportModule, options.ns)); + else + filters.push(exportAce(options.ns, options.exportModule)); + } + return filters; +} + var buildAce = function(options) { var aceProject = { roots: [ACE_HOME + '/lib', ACE_HOME + '/demo'], @@ -275,24 +302,6 @@ var buildAce = function(options) { if (!options.requires) options.requires = [options.exportModule]; - var filters = [ - copy.filter.moduleDefines, - filterTextPlugin, - removeUseStrict, - removeLicenceComments - ]; - - if (options.noconflict) { - filters.push(namespace(options.ns)); - if (options.exportModule) - var exportFilter = exportAce(options.ns, options.exportModule, options.ns); - } else if (options.exportModule) { - var exportFilter = exportAce(options.ns, options.exportModule); - } - - if (options.compress) - filters.push(copy.filter.uglifyjs); - var targetDir = options.targetDir + options.suffix; var name = options.name; @@ -313,7 +322,7 @@ var buildAce = function(options) { copy({ source: ace, - filter: exportFilter ? filters.concat(exportFilter) : filters, + filter: getWriteFilters(options, "main"), dest: targetDir + '/' + name + ".js" }); @@ -327,7 +336,7 @@ var buildAce = function(options) { project: cloneProject(project), require: [ 'ace/mode/' + mode ] }], - filter: filters, + filter: getWriteFilters(options, "mode"), dest: targetDir + "/mode-" + mode + ".js" }); }); @@ -337,26 +346,14 @@ var buildAce = function(options) { project.assumeAllFilesLoaded(); options.themes.forEach(function(theme) { console.log("theme " + theme); - /*copy({ + copy({ source: [{ project: cloneProject(project), require: ["ace/theme/" + theme] }], - filter: filters, - dest: targetDir + "/theme-" + theme + ".js" - });*/ - // use this instead, to not create separate modules for js and css - var themePath = ACE_HOME + "/lib/ace/theme/" + theme; - var js = fs.readFileSync(themePath + ".js", "utf8"); - js = js.replace("define(", "define('ace/theme/" + theme + "', ['require', 'exports', 'module', 'ace/lib/dom'], "); - - if (fs.existsSync(themePath + ".css", "utf8")) { - var css = fs.readFileSync(themePath + ".css", "utf8") - js = js.replace(/require\(.ace\/requirejs\/text!.*?\)/, quoteString(css)) - } - filters.forEach(function(f) {js = f(js); }); - - fs.writeFileSync(targetDir + "/theme-" + theme + ".js", js); + filter: getWriteFilters(options, "theme"), + dest: targetDir + "/theme-" + theme.replace("_theme", "") + ".js" + }); }); console.log('# ace extensions ---------'); @@ -369,7 +366,7 @@ var buildAce = function(options) { project: cloneProject(project), require: [ 'ace/ext/' + ext ] }], - filter: filters, + filter: getWriteFilters(options, "ext"), dest: targetDir + "/ext-" + ext + ".js" }); }); @@ -384,19 +381,12 @@ var buildAce = function(options) { project: cloneProject(project), require: [ 'ace/keyboard/' + keybinding ] }], - filter: filters, + filter: getWriteFilters(options, "keybinding"), dest: targetDir + "/keybinding-" + keybinding + ".js" }); }); console.log('# ace worker ---------'); - - filters = [ - copy.filter.moduleDefines, - filterTextPlugin, - removeUseStrict, - removeLicenceComments - ]; options.workers.forEach(function(mode) { console.log("worker for " + mode + " mode"); @@ -415,7 +405,7 @@ var buildAce = function(options) { 'ace/mode/' + mode + '_worker' ] }], - filter: filters, + filter: getWriteFilters(options, "worker"), dest: worker }); copy({ @@ -452,6 +442,45 @@ var buildAce = function(fn) { } }(buildAce); +var textModules = {} +var detectTextModules = function(input, source) { + if (!source) + throw new Error('Missing filename for text module'); + + if (typeof input !== 'string') + input = input.toString(); + + var module = source.isLocation ? source.path : source; + + input = input.replace(/\\/g, "\\\\").replace(/"/g, '\\"'); + input = '"' + input.replace(/\n/g, '\\n\\\n') + '"'; + textModules[module] = input; + + return ""; +}; +detectTextModules.onRead = true; +copy.filter.addDefines = detectTextModules; + +function inlineTextModules(text) { + var lastDep = ""; + return text.replace(/, *['"]ace\/requirejs\/text!(.*?)['"]|= *require\(['"](?:ace|[.\/]+)\/requirejs\/text!(.*?)['"]\)/g, function(_, dep, call) { + if (dep) { + if (!lastDep) { + lastDep = dep; + return ""; + } + } else if (call) { + call = textModules[lastDep]; + delete textModules[lastDep]; + lastDep = ""; + if (call) + return "= " + call; + } + console.log(dep, lastDep, call); + throw "inlining of multiple text modules is not supported"; + }); +} + // TODO: replace with project.clone once it is fixed in dryice function cloneProject(project) { var clone = copy.createCommonJsProject({ @@ -470,6 +499,7 @@ function cloneProject(project) { return clone; } + function copyFileSync(srcFile, destFile) { var BUF_LENGTH = 64*1024, buf = new Buffer(BUF_LENGTH), @@ -496,10 +526,6 @@ function quoteString(str) { return '"' + str.replace(/\\/, "\\\\").replace(/"/g, '\\"').replace(/\n/g, "\\\n") + '"'; } -function filterTextPlugin(text) { - return text.replace(/(['"])(ace|[.\/]+?)\/requirejs\/text\!/g, "$1"); -} - function removeUseStrict(text) { return text.replace(/['"]use strict['"];/g, ""); } From 20a7a6307daaa11ad11e9a0e75287894c7a20604 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 6 Oct 2012 14:55:43 +0400 Subject: [PATCH 09/66] remove state handler from build --- lib/ace/ace.js | 1 - 1 file changed, 1 deletion(-) diff --git a/lib/ace/ace.js b/lib/ace/ace.js index 3dd08504..b0fc073d 100644 --- a/lib/ace/ace.js +++ b/lib/ace/ace.js @@ -53,7 +53,6 @@ var MultiSelect = require("./multi_select").MultiSelect; // The following require()s are for inclusion in the built ace file require("./worker/worker_client"); require("./keyboard/hash_handler"); -require("./keyboard/state_handler"); require("./placeholder"); exports.config = require("./config"); /** From a2d34bf2918c754fa39dbbb217710feff3440478 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 6 Oct 2012 15:52:15 +0400 Subject: [PATCH 10/66] fix demo build --- Makefile.dryice.js | 48 +++++++++++++++++++++++++++++----------------- 1 file changed, 30 insertions(+), 18 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index d7c31851..4f525c39 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -66,8 +66,7 @@ function main(args) { } else if (type == "bm") { bookmarklet(); } else if (type == "full") { - ace(); - demo(); + demo(ace()); bookmarklet(); } } @@ -120,7 +119,7 @@ function ace() { console.log('# ace ---------'); // uncompressed - buildAce({ + var project = buildAce({ compress: false, noconflict: false }); @@ -153,9 +152,16 @@ function ace() { source: ACE_HOME + "/ChangeLog.txt", dest: BUILD_DIR + "/ChangeLog.txt" }); + + return project; } -function demo() { +function demo(project) { + project = project || buildAce({ + compress: false, + noconflict: false, + coreOnly: true + }); console.log('# kitchen sink ---------'); var version, ref; @@ -185,7 +191,7 @@ function demo() { copy({ source: ACE_HOME + "/kitchen-sink.html", dest: BUILD_DIR + "/kitchen-sink.html", - filter: [changeComments, fixDocPaths] + filter: [changeComments, fixDocPaths] }); copy({ @@ -202,20 +208,17 @@ function demo() { }); var demo = copy.createDataObject(); + + project.assumeAllFilesLoaded(); copy({ - source: ACE_HOME + "/demo/kitchen-sink/demo.js", - dest: demo, - filter: [changeComments, fixDocPaths, function(data) { - return data.replace("define(", "define('kitchen-sink/demo',"); - }] - }); - copy({ - source: ACE_HOME + "/lib/ace/split.js", - dest: demo, - filter: [changeComments, function(data) { - return data.replace("define(", "define('ace/split',"); - }] + source: [{ + project: cloneProject(project), + require: [ "kitchen-sink/demo" ] + }], + filter: getWriteFilters({filters:[fixDocPaths]}, "demo"), + dest: demo }); + copy({ source: demo, dest: BUILD_DIR + "/kitchen-sink/demo.js", @@ -253,6 +256,9 @@ function getWriteFilters(options, projectType) { removeLicenceComments ]; + if (options.filters) + filters = filters.concat(options.filters); + if (projectType == "worker") return filters; @@ -319,6 +325,9 @@ var buildAce = function(options) { filter: [ copy.filter.moduleDefines ], dest: ace }); + + if (options.coreOnly) + return project; copy({ source: ace, @@ -426,6 +435,8 @@ var buildAce = function(options) { dest: BUILD_DIR + '/ace-min.js' }); } + + return project; }; // silence annoying messages from dryice @@ -437,8 +448,9 @@ var buildAce = function(fn) { return; log.apply(console, arguments); } - fn.apply(null, arguments); + var ret = fn.apply(null, arguments); console.log = log; + return ret; } }(buildAce); From 8c310caf8bef1fbf39d868d2d47e279e85379df4 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 13 Oct 2012 17:06:43 +0400 Subject: [PATCH 11/66] include fold_mode in main build since it is used by all modes --- lib/ace/ace.js | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/ace/ace.js b/lib/ace/ace.js index b0fc073d..f0e7f50b 100644 --- a/lib/ace/ace.js +++ b/lib/ace/ace.js @@ -54,6 +54,7 @@ var MultiSelect = require("./multi_select").MultiSelect; require("./worker/worker_client"); require("./keyboard/hash_handler"); require("./placeholder"); +require("./mode/folding/fold_mode"); exports.config = require("./config"); /** * Ace.edit(el) -> Editor From 0ccab0463c56f9515848124e1b5f75e17d83f438 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 13 Oct 2012 17:25:35 +0400 Subject: [PATCH 12/66] make generated file a little smaller --- Makefile.dryice.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 4f525c39..3109f84f 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -251,9 +251,9 @@ function addSuffix(options) { function getWriteFilters(options, projectType) { var filters = [ copy.filter.moduleDefines, - inlineTextModules, removeUseStrict, - removeLicenceComments + removeLicenceComments, + inlineTextModules ]; if (options.filters) @@ -465,7 +465,8 @@ var detectTextModules = function(input, source) { var module = source.isLocation ? source.path : source; input = input.replace(/\\/g, "\\\\").replace(/"/g, '\\"'); - input = '"' + input.replace(/\n/g, '\\n\\\n') + '"'; + input = input.replace(/\n\s+/g, "\n"); + input = '"' + input.replace(/\n/g, '\\\n') + '"'; textModules[module] = input; return ""; @@ -543,7 +544,7 @@ function removeUseStrict(text) { } function removeLicenceComments(text) { - return text.replace(/(;)\s*\/\*[\d\D]*?\*\//g, "$1"); + return text.replace(/(?:(;)|\n)\s*\/\*[\d\D]*?\*\/|\n\s*\/\/.*/g, "$1"); } function namespace(ns) { From 872125db46c7f1d44989710a2967d1f55109b681 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 13 Oct 2012 17:46:44 +0400 Subject: [PATCH 13/66] use relative paths everywhere --- lib/ace/ext/textarea.js | 2 +- lib/ace/keyboard/vim/maps/motions.js | 4 ++-- lib/ace/mode/jade.js | 4 ++-- lib/ace/placeholder.js | 2 +- lib/ace/placeholder_test.js | 4 ++-- lib/ace/requirejs/text.js | 2 +- lib/ace/theme/ambiance.js | 2 +- lib/ace/theme/chrome.js | 2 +- lib/ace/theme/clouds.js | 2 +- lib/ace/theme/clouds_midnight.js | 2 +- lib/ace/theme/cobalt.js | 2 +- lib/ace/theme/crimson_editor.js | 2 +- lib/ace/theme/dawn.js | 2 +- lib/ace/theme/dreamweaver.js | 2 +- lib/ace/theme/eclipse.js | 2 +- lib/ace/theme/github.js | 2 +- lib/ace/theme/idle_fingers.js | 2 +- lib/ace/theme/kr_theme.js | 2 +- lib/ace/theme/merbivore.js | 2 +- lib/ace/theme/merbivore_soft.js | 2 +- lib/ace/theme/mono_industrial.css | 2 +- lib/ace/theme/mono_industrial.js | 2 +- lib/ace/theme/monokai.js | 2 +- lib/ace/theme/pastel_on_dark.js | 2 +- lib/ace/theme/solarized_dark.js | 2 +- lib/ace/theme/solarized_light.js | 2 +- lib/ace/theme/textmate.js | 2 +- lib/ace/theme/tomorrow.js | 2 +- lib/ace/theme/tomorrow_night.js | 2 +- lib/ace/theme/tomorrow_night_blue.js | 2 +- lib/ace/theme/tomorrow_night_bright.js | 2 +- lib/ace/theme/tomorrow_night_eighties.js | 2 +- lib/ace/theme/twilight.js | 2 +- lib/ace/theme/vibrant_ink.js | 2 +- lib/ace/theme/xcode.js | 2 +- lib/ace/virtual_renderer.js | 2 +- tool/tmtheme.js | 2 +- 37 files changed, 40 insertions(+), 40 deletions(-) diff --git a/lib/ace/ext/textarea.js b/lib/ace/ext/textarea.js index ddb57df0..a8f6317f 100644 --- a/lib/ace/ext/textarea.js +++ b/lib/ace/ext/textarea.js @@ -36,7 +36,7 @@ var UA = require("../lib/useragent"); var net = require("../lib/net"); var ace = require("../ace"); -require("ace/theme/textmate"); +require("../theme/textmate"); module.exports = exports = ace; diff --git a/lib/ace/keyboard/vim/maps/motions.js b/lib/ace/keyboard/vim/maps/motions.js index 227862b9..f5e0f163 100644 --- a/lib/ace/keyboard/vim/maps/motions.js +++ b/lib/ace/keyboard/vim/maps/motions.js @@ -127,7 +127,7 @@ var StringStream = function(editor, cursor) { }; }; -var Search = require("ace/search").Search; +var Search = require("../../../search").Search; var search = new Search(); function find(editor, needle, dir) { @@ -136,7 +136,7 @@ function find(editor, needle, dir) { return search.find(editor.session); } -var Range = require("ace/range").Range; +var Range = require("../../../range").Range; module.exports = { "w": new Motion(function(editor) { diff --git a/lib/ace/mode/jade.js b/lib/ace/mode/jade.js index 03b54306..076b29c8 100644 --- a/lib/ace/mode/jade.js +++ b/lib/ace/mode/jade.js @@ -40,8 +40,8 @@ var oop = require("../lib/oop"); var TextMode = require("./text").Mode; var Tokenizer = require("../tokenizer").Tokenizer; var JadeHighlightRules = require("./jade_highlight_rules").JadeHighlightRules; -// var JavascriptMode = require("ace/mode/javascript").Mode; -// var CssMode = require("ace/mode/css").Mode; +// var JavascriptMode = require("../mode/javascript").Mode; +// var CssMode = require("../mode/css").Mode; var Mode = function() { var highlighter = new JadeHighlightRules(); diff --git a/lib/ace/placeholder.js b/lib/ace/placeholder.js index 8a93ee54..3306cba1 100644 --- a/lib/ace/placeholder.js +++ b/lib/ace/placeholder.js @@ -30,7 +30,7 @@ define(function(require, exports, module) { "use strict"; -var Range = require('./range').Range; +var Range = require("./range").Range; var EventEmitter = require("./lib/event_emitter").EventEmitter; var oop = require("./lib/oop"); diff --git a/lib/ace/placeholder_test.js b/lib/ace/placeholder_test.js index f395042b..97e561fd 100644 --- a/lib/ace/placeholder_test.js +++ b/lib/ace/placeholder_test.js @@ -41,8 +41,8 @@ var Editor = require("./editor").Editor; var MockRenderer = require("./test/mockrenderer").MockRenderer; var assert = require("./test/assertions"); var JavaScriptMode = require("./mode/javascript").Mode; -var PlaceHolder = require('./placeholder').PlaceHolder; -var UndoManager = require('./undomanager').UndoManager; +var PlaceHolder = require("./placeholder").PlaceHolder; +var UndoManager = require("./undomanager").UndoManager; module.exports = { diff --git a/lib/ace/requirejs/text.js b/lib/ace/requirejs/text.js index 66123169..cba62eef 100644 --- a/lib/ace/requirejs/text.js +++ b/lib/ace/requirejs/text.js @@ -44,7 +44,7 @@ define(function (require, exports, module) { if (globalRequire && globalRequire.nodeRequire) onLoad(globalRequire.nodeRequire('fs').readFileSync(req.toUrl(name), 'utf8')); else - require("ace/lib/net").get(req.toUrl(name), onLoad); + require("../lib/net").get(req.toUrl(name), onLoad); }; }); diff --git a/lib/ace/theme/ambiance.js b/lib/ace/theme/ambiance.js index 4c74d6f8..475c2e87 100644 --- a/lib/ace/theme/ambiance.js +++ b/lib/ace/theme/ambiance.js @@ -25,7 +25,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-ambiance"; -exports.cssText = require("ace/requirejs/text!./ambiance.css"); +exports.cssText = require("../requirejs/text!./ambiance.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/chrome.js b/lib/ace/theme/chrome.js index b0d02480..dafa99c2 100644 --- a/lib/ace/theme/chrome.js +++ b/lib/ace/theme/chrome.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-chrome"; -exports.cssText = require('ace/requirejs/text!./chrome.css'); +exports.cssText = require("../requirejs/text!./chrome.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/clouds.js b/lib/ace/theme/clouds.js index 13d66603..f9b7c6bf 100644 --- a/lib/ace/theme/clouds.js +++ b/lib/ace/theme/clouds.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-clouds"; -exports.cssText = require('ace/requirejs/text!./clouds.css'); +exports.cssText = require("../requirejs/text!./clouds.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/clouds_midnight.js b/lib/ace/theme/clouds_midnight.js index 9359d120..a7b76d65 100644 --- a/lib/ace/theme/clouds_midnight.js +++ b/lib/ace/theme/clouds_midnight.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-clouds-midnight"; -exports.cssText = require('ace/requirejs/text!./clouds_midnight.css'); +exports.cssText = require("../requirejs/text!./clouds_midnight.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/cobalt.js b/lib/ace/theme/cobalt.js index 0964e9a6..6e2f3d0a 100644 --- a/lib/ace/theme/cobalt.js +++ b/lib/ace/theme/cobalt.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-cobalt"; -exports.cssText = require('ace/requirejs/text!./cobalt.css'); +exports.cssText = require("../requirejs/text!./cobalt.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/crimson_editor.js b/lib/ace/theme/crimson_editor.js index 943930d9..a5971075 100644 --- a/lib/ace/theme/crimson_editor.js +++ b/lib/ace/theme/crimson_editor.js @@ -30,7 +30,7 @@ define(function(require, exports, module) { exports.isDark = false; -exports.cssText = require('ace/requirejs/text!./crimson_editor.css'); +exports.cssText = require("../requirejs/text!./crimson_editor.css"); exports.cssClass = "ace-crimson-editor"; diff --git a/lib/ace/theme/dawn.js b/lib/ace/theme/dawn.js index 88b5ae38..f31f00b8 100644 --- a/lib/ace/theme/dawn.js +++ b/lib/ace/theme/dawn.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-dawn"; -exports.cssText = require('ace/requirejs/text!./dawn.css'); +exports.cssText = require("../requirejs/text!./dawn.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/dreamweaver.js b/lib/ace/theme/dreamweaver.js index 25a7fcba..943dc692 100644 --- a/lib/ace/theme/dreamweaver.js +++ b/lib/ace/theme/dreamweaver.js @@ -31,7 +31,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-dreamweaver"; -exports.cssText = require('ace/requirejs/text!./dreamweaver.css'); +exports.cssText = require("../requirejs/text!./dreamweaver.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/eclipse.js b/lib/ace/theme/eclipse.js index aabeeab2..329b8b79 100644 --- a/lib/ace/theme/eclipse.js +++ b/lib/ace/theme/eclipse.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { "use strict"; exports.isDark = false; -exports.cssText = require('ace/requirejs/text!./eclipse.css'); +exports.cssText = require("../requirejs/text!./eclipse.css"); exports.cssClass = "ace-eclipse"; diff --git a/lib/ace/theme/github.js b/lib/ace/theme/github.js index b5839dd4..de013c8c 100644 --- a/lib/ace/theme/github.js +++ b/lib/ace/theme/github.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-github"; -exports.cssText = require('ace/requirejs/text!./github.css'); +exports.cssText = require("../requirejs/text!./github.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/idle_fingers.js b/lib/ace/theme/idle_fingers.js index fcb3be31..5da497f0 100644 --- a/lib/ace/theme/idle_fingers.js +++ b/lib/ace/theme/idle_fingers.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-idle-fingers"; -exports.cssText = require('ace/requirejs/text!./idle_fingers.css'); +exports.cssText = require("../requirejs/text!./idle_fingers.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/kr_theme.js b/lib/ace/theme/kr_theme.js index 81faf395..2018a962 100644 --- a/lib/ace/theme/kr_theme.js +++ b/lib/ace/theme/kr_theme.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-kr-theme"; -exports.cssText = require('ace/requirejs/text!./kr_theme.css'); +exports.cssText = require("../requirejs/text!./kr_theme.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/merbivore.js b/lib/ace/theme/merbivore.js index bba49410..699fb2eb 100644 --- a/lib/ace/theme/merbivore.js +++ b/lib/ace/theme/merbivore.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-merbivore"; -exports.cssText = require('ace/requirejs/text!./merbivore.css'); +exports.cssText = require("../requirejs/text!./merbivore.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/merbivore_soft.js b/lib/ace/theme/merbivore_soft.js index 5848e289..873a6023 100644 --- a/lib/ace/theme/merbivore_soft.js +++ b/lib/ace/theme/merbivore_soft.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-merbivore-soft"; -exports.cssText = require('ace/requirejs/text!./merbivore_soft.css'); +exports.cssText = require("../requirejs/text!./merbivore_soft.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/mono_industrial.css b/lib/ace/theme/mono_industrial.css index 09c765b4..b5eb68b2 100644 --- a/lib/ace/theme/mono_industrial.css +++ b/lib/ace/theme/mono_industrial.css @@ -135,4 +135,4 @@ .ace-mono-industrial .ace_indent-guide { background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAEklEQVQImWNQ0tH4zzBz5sz/ABAOBECKH+evAAAAAElFTkSuQmCC) right repeat-y -} +} \ No newline at end of file diff --git a/lib/ace/theme/mono_industrial.js b/lib/ace/theme/mono_industrial.js index 288cd710..af763292 100644 --- a/lib/ace/theme/mono_industrial.js +++ b/lib/ace/theme/mono_industrial.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-mono-industrial"; -exports.cssText = require('ace/requirejs/text!./mono_industrial.css'); +exports.cssText = require("../requirejs/text!./mono_industrial.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/monokai.js b/lib/ace/theme/monokai.js index fe4283c6..a33326bd 100644 --- a/lib/ace/theme/monokai.js +++ b/lib/ace/theme/monokai.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-monokai"; -exports.cssText = require('ace/requirejs/text!./monokai.css'); +exports.cssText = require("../requirejs/text!./monokai.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/pastel_on_dark.js b/lib/ace/theme/pastel_on_dark.js index 93776772..5c11fd4c 100644 --- a/lib/ace/theme/pastel_on_dark.js +++ b/lib/ace/theme/pastel_on_dark.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-pastel-on-dark"; -exports.cssText = require('ace/requirejs/text!./pastel_on_dark.css'); +exports.cssText = require("../requirejs/text!./pastel_on_dark.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/solarized_dark.js b/lib/ace/theme/solarized_dark.js index f2ef096b..d7ad4f90 100644 --- a/lib/ace/theme/solarized_dark.js +++ b/lib/ace/theme/solarized_dark.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-solarized-dark"; -exports.cssText = require('ace/requirejs/text!./solarized_dark.css'); +exports.cssText = require("../requirejs/text!./solarized_dark.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/solarized_light.js b/lib/ace/theme/solarized_light.js index a8e9e10f..eda2c45c 100644 --- a/lib/ace/theme/solarized_light.js +++ b/lib/ace/theme/solarized_light.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-solarized-light"; -exports.cssText = require('ace/requirejs/text!./solarized_light.css'); +exports.cssText = require("../requirejs/text!./solarized_light.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/textmate.js b/lib/ace/theme/textmate.js index 47bbae0b..75e19745 100644 --- a/lib/ace/theme/textmate.js +++ b/lib/ace/theme/textmate.js @@ -33,7 +33,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-tm"; -exports.cssText = require('ace/requirejs/text!./textmate.css'); +exports.cssText = require("../requirejs/text!./textmate.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/tomorrow.js b/lib/ace/theme/tomorrow.js index acf984f9..603c92a5 100644 --- a/lib/ace/theme/tomorrow.js +++ b/lib/ace/theme/tomorrow.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-tomorrow"; -exports.cssText = require('ace/requirejs/text!./tomorrow.css'); +exports.cssText = require("../requirejs/text!./tomorrow.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/tomorrow_night.js b/lib/ace/theme/tomorrow_night.js index f3fcdbc9..8a2454ea 100644 --- a/lib/ace/theme/tomorrow_night.js +++ b/lib/ace/theme/tomorrow_night.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-tomorrow-night"; -exports.cssText = require('ace/requirejs/text!./tomorrow_night.css'); +exports.cssText = require("../requirejs/text!./tomorrow_night.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/tomorrow_night_blue.js b/lib/ace/theme/tomorrow_night_blue.js index 0b496d20..dafd1f53 100644 --- a/lib/ace/theme/tomorrow_night_blue.js +++ b/lib/ace/theme/tomorrow_night_blue.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-tomorrow-night-blue"; -exports.cssText = require('ace/requirejs/text!./tomorrow_night_blue.css'); +exports.cssText = require("../requirejs/text!./tomorrow_night_blue.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/tomorrow_night_bright.js b/lib/ace/theme/tomorrow_night_bright.js index 18bc4aa9..12c961ef 100644 --- a/lib/ace/theme/tomorrow_night_bright.js +++ b/lib/ace/theme/tomorrow_night_bright.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-tomorrow-night-bright"; -exports.cssText = require('ace/requirejs/text!./tomorrow_night_bright.css'); +exports.cssText = require("../requirejs/text!./tomorrow_night_bright.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/tomorrow_night_eighties.js b/lib/ace/theme/tomorrow_night_eighties.js index 8217cdbd..fc2cd15c 100644 --- a/lib/ace/theme/tomorrow_night_eighties.js +++ b/lib/ace/theme/tomorrow_night_eighties.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-tomorrow-night-eighties"; -exports.cssText = require('ace/requirejs/text!./tomorrow_night_eighties.css'); +exports.cssText = require("../requirejs/text!./tomorrow_night_eighties.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/twilight.js b/lib/ace/theme/twilight.js index 5c1d3eef..216f09de 100644 --- a/lib/ace/theme/twilight.js +++ b/lib/ace/theme/twilight.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-twilight"; -exports.cssText = require('ace/requirejs/text!./twilight.css'); +exports.cssText = require("../requirejs/text!./twilight.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/vibrant_ink.js b/lib/ace/theme/vibrant_ink.js index 584f8d29..b41b1d47 100644 --- a/lib/ace/theme/vibrant_ink.js +++ b/lib/ace/theme/vibrant_ink.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = true; exports.cssClass = "ace-vibrant-ink"; -exports.cssText = require('ace/requirejs/text!./vibrant_ink.css'); +exports.cssText = require("../requirejs/text!./vibrant_ink.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/theme/xcode.js b/lib/ace/theme/xcode.js index c6cba5b9..19827338 100644 --- a/lib/ace/theme/xcode.js +++ b/lib/ace/theme/xcode.js @@ -32,7 +32,7 @@ define(function(require, exports, module) { exports.isDark = false; exports.cssClass = "ace-xcode"; -exports.cssText = require('ace/requirejs/text!./xcode.css'); +exports.cssText = require("../requirejs/text!./xcode.css"); var dom = require("../lib/dom"); dom.importCssString(exports.cssText, exports.cssClass); diff --git a/lib/ace/virtual_renderer.js b/lib/ace/virtual_renderer.js index fbb1661c..757db95c 100644 --- a/lib/ace/virtual_renderer.js +++ b/lib/ace/virtual_renderer.js @@ -44,7 +44,7 @@ var CursorLayer = require("./layer/cursor").Cursor; var ScrollBar = require("./scrollbar").ScrollBar; var RenderLoop = require("./renderloop").RenderLoop; var EventEmitter = require("./lib/event_emitter").EventEmitter; -var editorCss = require("ace/requirejs/text!./css/editor.css"); +var editorCss = require("./requirejs/text!./css/editor.css"); dom.importCssString(editorCss, "ace_editor"); diff --git a/tool/tmtheme.js b/tool/tmtheme.js index 39570e05..ab40d4a5 100755 --- a/tool/tmtheme.js +++ b/tool/tmtheme.js @@ -278,7 +278,7 @@ function convertTheme(name) { var js = fillTemplate(jsTemplate, { name: name, - css: "require('ace/requirejs/text!./" + name + ".css')", // quoteString(css), // + css: 'require("../requirejs/text!./' + name + '.css")', // quoteString(css), // cssClass: "ace-" + hyphenate(name), isDark: styles.isDark }); From 2950c67e3e8c86ea2df56cddfae910e6ccf61f93 Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Thu, 18 Oct 2012 10:23:55 +0200 Subject: [PATCH 14/66] Don't surround bracketize brackets when you're trying to overwrite them --- lib/ace/mode/behaviour/cstyle.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index e4dea304..5f2e48b4 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -40,7 +40,7 @@ var CstyleBehaviour = function () { if (text == '{') { var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "") { + if (selected !== "" && selected !== "}") { return { text: '{' + selected + '}', selection: false @@ -100,7 +100,7 @@ var CstyleBehaviour = function () { if (text == '(') { var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "") { + if (selected !== "" && selected !== ")") { return { text: '(' + selected + ')', selection: false @@ -143,7 +143,7 @@ var CstyleBehaviour = function () { if (text == '[') { var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "") { + if (selected !== "" && selected !== "]") { return { text: '[' + selected + ']', selection: false @@ -187,7 +187,7 @@ var CstyleBehaviour = function () { var quote = text; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "") { + if (selected !== "" && selected !== "'") { return { text: quote + selected + quote, selection: false From 5ed0998ce77ccc25ad7d1141df23864f854f4e6b Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Thu, 18 Oct 2012 14:41:35 +0200 Subject: [PATCH 15/66] Be selective when auto-inserting brackets --- lib/ace/mode/behaviour/cstyle.js | 38 ++++++++++++++++++++++++++++---- 1 file changed, 34 insertions(+), 4 deletions(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index 5f2e48b4..0efac142 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -33,14 +33,40 @@ define(function(require, exports, module) { var oop = require("../../lib/oop"); var Behaviour = require("../behaviour").Behaviour; +var TokenIterator = require("../../token_iterator").TokenIterator; var CstyleBehaviour = function () { + + CstyleBehaviour.isSaneInsertion = function(editor, session) { + var cursor = editor.getCursorPosition(); + var iterator = new TokenIterator(session, cursor.row, cursor.column); + + // Don't insert in the middle of a keyword/identifier/lexical + if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text"])) { + // Look ahead in case we're at the end of a token + iterator = new TokenIterator(session, cursor.row, cursor.column + 1); + if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text"])) + return false; + } + + // Don't insert in front of identifiers or brackets + iterator.stepForward(); + if (this.$matchTokenType(iterator.getCurrentToken() || "text", ["identifier", "paren.lparen"])) + return false; + return true; + }; + + CstyleBehaviour.$matchTokenType = function(token, types) { + return types.indexOf(token.type || token) > -1; + }; this.add("braces", "insertion", function (state, action, editor, session, text) { if (text == '{') { + if (!CstyleBehaviour.isSaneInsertion(editor, session)) + return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "" && selected !== "}") { + if (selected !== "" && selected !== "{") { return { text: '{' + selected + '}', selection: false @@ -98,9 +124,11 @@ var CstyleBehaviour = function () { this.add("parens", "insertion", function (state, action, editor, session, text) { if (text == '(') { + if (!CstyleBehaviour.isSaneInsertion(editor, session)) + return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "" && selected !== ")") { + if (selected !== "") { return { text: '(' + selected + ')', selection: false @@ -141,9 +169,11 @@ var CstyleBehaviour = function () { this.add("brackets", "insertion", function (state, action, editor, session, text) { if (text == '[') { + if (!CstyleBehaviour.isSaneInsertion(editor, session)) + return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "" && selected !== "]") { + if (selected !== "") { return { text: '[' + selected + ']', selection: false @@ -187,7 +217,7 @@ var CstyleBehaviour = function () { var quote = text; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); - if (selected !== "" && selected !== "'") { + if (selected !== "") { return { text: quote + selected + quote, selection: false From b126f5d314945d57c402e34cf40c39262126ed1a Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Thu, 18 Oct 2012 15:32:31 +0200 Subject: [PATCH 16/66] Allow multiple bracket closing insertionss like {{{}}} --- lib/ace/mode/behaviour/cstyle.js | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index 0efac142..259180f3 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -45,15 +45,14 @@ var CstyleBehaviour = function () { if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text"])) { // Look ahead in case we're at the end of a token iterator = new TokenIterator(session, cursor.row, cursor.column + 1); - if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text"])) + if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text", "paren.rparen"])) return false; } - // Don't insert in front of identifiers or brackets + // Only insert in front of whitespace/comments iterator.stepForward(); - if (this.$matchTokenType(iterator.getCurrentToken() || "text", ["identifier", "paren.lparen"])) - return false; - return true; + return iterator.getCurrentTokenRow() !== cursor.row || + this.$matchTokenType(iterator.getCurrentToken() || "text", ["text", "comment", "paren.rparen"]); }; CstyleBehaviour.$matchTokenType = function(token, types) { From 99f695310821d81d176be48dcb80c3b89a3750b5 Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Thu, 18 Oct 2012 15:55:33 +0200 Subject: [PATCH 17/66] Only skip closing brackets if they were just auto-inserted --- lib/ace/mode/behaviour/cstyle.js | 39 +++++++++++++++++++++++++++++--- 1 file changed, 36 insertions(+), 3 deletions(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index 259180f3..b8d84157 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -35,6 +35,10 @@ var oop = require("../../lib/oop"); var Behaviour = require("../behaviour").Behaviour; var TokenIterator = require("../../token_iterator").TokenIterator; +var autoInsertedBrackets = 0; +var autoInsertedRow = -1; +var autoInsertedLineEnd = ""; + var CstyleBehaviour = function () { CstyleBehaviour.isSaneInsertion = function(editor, session) { @@ -58,6 +62,29 @@ var CstyleBehaviour = function () { CstyleBehaviour.$matchTokenType = function(token, types) { return types.indexOf(token.type || token) > -1; }; + + CstyleBehaviour.recordAutoInsert = function(editor, session, bracket) { + var cursor = editor.getCursorPosition(); + var line = session.doc.getLine(cursor.row); + // Reset previous state if text or context changed too much + if (!this.isAutoInsertedClosing(cursor, line, autoInsertedLineEnd[0])) + autoInsertedBrackets = 0; + autoInsertedRow = cursor.row; + autoInsertedLineEnd = bracket + line.substr(cursor.column); + autoInsertedBrackets++; + }; + + CstyleBehaviour.isAutoInsertedClosing = function(cursor, line, bracket) { + return autoInsertedBrackets > 0 && + cursor.row === autoInsertedRow && + bracket === autoInsertedLineEnd[0] && + line.substr(cursor.column) === autoInsertedLineEnd; + }; + + CstyleBehaviour.popAutoInsertedClosing = function() { + autoInsertedLineEnd = autoInsertedLineEnd.substr(1); + autoInsertedBrackets--; + }; this.add("braces", "insertion", function (state, action, editor, session, text) { if (text == '{') { @@ -71,6 +98,7 @@ var CstyleBehaviour = function () { selection: false }; } else { + CstyleBehaviour.recordAutoInsert(editor, session, "}"); return { text: '{}', selection: [1, 1] @@ -82,7 +110,8 @@ var CstyleBehaviour = function () { var rightChar = line.substring(cursor.column, cursor.column + 1); if (rightChar == '}') { var matching = session.$findOpeningBracket('}', {column: cursor.column + 1, row: cursor.row}); - if (matching !== null) { + if (matching !== null && CstyleBehaviour.isAutoInsertedClosing(cursor, line, text)) { + CstyleBehaviour.popAutoInsertedClosing(); return { text: '', selection: [1, 1] @@ -133,6 +162,7 @@ var CstyleBehaviour = function () { selection: false }; } else { + CstyleBehaviour.recordAutoInsert(editor, session, ")"); return { text: '()', selection: [1, 1] @@ -144,7 +174,8 @@ var CstyleBehaviour = function () { var rightChar = line.substring(cursor.column, cursor.column + 1); if (rightChar == ')') { var matching = session.$findOpeningBracket(')', {column: cursor.column + 1, row: cursor.row}); - if (matching !== null) { + if (matching !== null && CstyleBehaviour.isAutoInsertedClosing(cursor, line, text)) { + CstyleBehaviour.popAutoInsertedClosing(); return { text: '', selection: [1, 1] @@ -178,6 +209,7 @@ var CstyleBehaviour = function () { selection: false }; } else { + CstyleBehaviour.recordAutoInsert(editor, session, "]"); return { text: '[]', selection: [1, 1] @@ -189,7 +221,8 @@ var CstyleBehaviour = function () { var rightChar = line.substring(cursor.column, cursor.column + 1); if (rightChar == ']') { var matching = session.$findOpeningBracket(']', {column: cursor.column + 1, row: cursor.row}); - if (matching !== null) { + if (matching !== null && CstyleBehaviour.isAutoInsertedClosing(cursor, line, text)) { + CstyleBehaviour.popAutoInsertedClosing(); return { text: '', selection: [1, 1] From 40bc5ee79af4097ea13fc19d5022c16d46834c13 Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Thu, 18 Oct 2012 17:29:15 +0200 Subject: [PATCH 18/66] Allow bracket insertion after closing bracket: }() --- lib/ace/mode/behaviour/cstyle.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index b8d84157..76e12fc3 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -46,7 +46,7 @@ var CstyleBehaviour = function () { var iterator = new TokenIterator(session, cursor.row, cursor.column); // Don't insert in the middle of a keyword/identifier/lexical - if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text"])) { + if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text", "paren.rparen"])) { // Look ahead in case we're at the end of a token iterator = new TokenIterator(session, cursor.row, cursor.column + 1); if (!this.$matchTokenType(iterator.getCurrentToken() || "text", ["text", "paren.rparen"])) From 281a1ca2a8efb2c9447f76c04a066416b9c48fde Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Fri, 19 Oct 2012 12:56:44 +0200 Subject: [PATCH 19/66] add sortLines functionality in all modes --- lib/ace/commands/default_commands.js | 5 ++++ lib/ace/editor.js | 35 +++++++++++++++++++++++++++- 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index ab7f6688..9da2dd1d 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -321,6 +321,11 @@ exports.commands = [{ bindKey: bindKey("Ctrl-Shift-D", "Command-Shift-D"), exec: function(editor) { editor.duplicateSelection(); }, multiSelectAction: "forEach" +}, { + name: "sortlines", + bindKey: bindKey("Ctrl-Alt-S", "Command-Alt-S"), + exec: function(editor) { editor.sortLines(); }, + multiSelectAction: "forEach" }, { name: "togglecomment", bindKey: bindKey("Ctrl-/", "Command-/"), diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 1010a49d..cbfe06ac 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1277,10 +1277,43 @@ var Editor = function(renderer, session) { }; /** - * Editor.toggleCommentLines() + * Editor.sortLines() * * Given the currently selected range, this function either comments all lines or uncomments all lines (depending on whether it's commented or not). **/ + this.sortLines = function() { + var state = this.session.getState(this.getCursorPosition().row); + var rows = this.$getSelectedRows(); + var doc = this.session; + + var lines = []; + for(i = rows.first; i <= rows.last; i++) { + lines.push( doc.getLine(i) ); + } + lines.sort( + function(a, b) { + if (a.toLowerCase() < b.toLowerCase()) return -1; + if (a.toLowerCase() > b.toLowerCase()) return 1; + return 0; + } + ); + + var deleteRange = new Range(0, 0, 0, 0); + for (var i=rows.first; i<= rows.last; i++) + { + var line = doc.getLine(i); + deleteRange.start.row = i; + deleteRange.end.row = i; + deleteRange.end.column = line.length; + doc.replace(deleteRange, lines[i-rows.first]); + } + }; + + /** + * Editor.toggleCommentLines() + * + * Given the currently selected range, this function sorts the lines alphabetically ascending. + **/ this.toggleCommentLines = function() { var state = this.session.getState(this.getCursorPosition().row); var rows = this.$getSelectedRows(); From 8f46921e5dbd20cc15cc1ed643b5477882a1dfdb Mon Sep 17 00:00:00 2001 From: Steve Valaitis Date: Fri, 19 Oct 2012 15:51:53 -0500 Subject: [PATCH 20/66] Add keywords insert,update,delete for SQL mode --- lib/ace/mode/sql_highlight_rules.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/mode/sql_highlight_rules.js b/lib/ace/mode/sql_highlight_rules.js index 31f609d7..e16ac9ab 100644 --- a/lib/ace/mode/sql_highlight_rules.js +++ b/lib/ace/mode/sql_highlight_rules.js @@ -37,7 +37,7 @@ var TextHighlightRules = require("./text_highlight_rules").TextHighlightRules; var SqlHighlightRules = function() { var keywords = ( - "select|from|where|and|or|group|by|order|limit|offset|having|as|case|" + + "select|insert|update|delete|from|where|and|or|group|by|order|limit|offset|having|as|case|" + "when|else|end|type|left|right|join|on|outer|desc|asc" ); From 27ac92f9b00ab02fab0af24a9b5a1e7526b6fc15 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sun, 21 Oct 2012 00:45:45 +0400 Subject: [PATCH 21/66] cleanup --- lib/ace/editor.js | 66 +++++++++++++++++++++-------------------------- 1 file changed, 29 insertions(+), 37 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index cbfe06ac..937e0e73 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1276,43 +1276,35 @@ var Editor = function(renderer, session) { this.session.outdentRows(selection.getRange()); }; - /** - * Editor.sortLines() - * - * Given the currently selected range, this function either comments all lines or uncomments all lines (depending on whether it's commented or not). - **/ + // TODO: move out of core when we have good mechanism for managing extensions this.sortLines = function() { - var state = this.session.getState(this.getCursorPosition().row); var rows = this.$getSelectedRows(); - var doc = this.session; + var session = this.session; var lines = []; - for(i = rows.first; i <= rows.last; i++) { - lines.push( doc.getLine(i) ); - } - lines.sort( - function(a, b) { - if (a.toLowerCase() < b.toLowerCase()) return -1; - if (a.toLowerCase() > b.toLowerCase()) return 1; - return 0; - } - ); + for (i = rows.first; i <= rows.last; i++) + lines.push(session.getLine(i)); + + lines.sort(function(a, b) { + if (a.toLowerCase() < b.toLowerCase()) return -1; + if (a.toLowerCase() > b.toLowerCase()) return 1; + return 0; + }); var deleteRange = new Range(0, 0, 0, 0); - for (var i=rows.first; i<= rows.last; i++) - { - var line = doc.getLine(i); + for (var i = rows.first; i <= rows.last; i++) { + var line = session.getLine(i); deleteRange.start.row = i; deleteRange.end.row = i; deleteRange.end.column = line.length; - doc.replace(deleteRange, lines[i-rows.first]); + session.replace(deleteRange, lines[i-rows.first]); } }; /** * Editor.toggleCommentLines() * - * Given the currently selected range, this function sorts the lines alphabetically ascending. + * Given the currently selected range, this function either comments all lines or uncomments all lines (depending on whether it's commented or not). **/ this.toggleCommentLines = function() { var state = this.session.getState(this.getCursorPosition().row); @@ -1341,20 +1333,20 @@ var Editor = function(renderer, session) { this.duplicateSelection = function() { var sel = this.selection; - var doc = this.session; - var range = sel.getRange(); - if (range.isEmpty()) { - var row = range.start.row; - doc.duplicateLines(row, row); - } else { - var reverse = sel.isBackwards() - var point = sel.isBackwards() ? range.start : range.end; - var endPoint = doc.insert(point, doc.getTextRange(range), false); - range.start = point; - range.end = endPoint; - - sel.setSelectionRange(range, reverse) - } + var doc = this.session; + var range = sel.getRange(); + if (range.isEmpty()) { + var row = range.start.row; + doc.duplicateLines(row, row); + } else { + var reverse = sel.isBackwards() + var point = sel.isBackwards() ? range.start : range.end; + var endPoint = doc.insert(point, doc.getTextRange(range), false); + range.start = point; + range.end = endPoint; + + sel.setSelectionRange(range, reverse) + } }; /** related to: EditSession.moveLinesDown @@ -2134,4 +2126,4 @@ var Editor = function(renderer, session) { exports.Editor = Editor; -}); +}); \ No newline at end of file From 72dde40c76c50f08b1bb21a3cd5acfc3ac188166 Mon Sep 17 00:00:00 2001 From: Lennart Kats Date: Mon, 22 Oct 2012 14:17:08 +0200 Subject: [PATCH 22/66] Make sure wrapping behaves the same as before --- lib/ace/mode/behaviour/cstyle.js | 12 +++--------- 1 file changed, 3 insertions(+), 9 deletions(-) diff --git a/lib/ace/mode/behaviour/cstyle.js b/lib/ace/mode/behaviour/cstyle.js index 76e12fc3..8397e79c 100644 --- a/lib/ace/mode/behaviour/cstyle.js +++ b/lib/ace/mode/behaviour/cstyle.js @@ -88,8 +88,6 @@ var CstyleBehaviour = function () { this.add("braces", "insertion", function (state, action, editor, session, text) { if (text == '{') { - if (!CstyleBehaviour.isSaneInsertion(editor, session)) - return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); if (selected !== "" && selected !== "{") { @@ -97,7 +95,7 @@ var CstyleBehaviour = function () { text: '{' + selected + '}', selection: false }; - } else { + } else if (CstyleBehaviour.isSaneInsertion(editor, session)) { CstyleBehaviour.recordAutoInsert(editor, session, "}"); return { text: '{}', @@ -152,8 +150,6 @@ var CstyleBehaviour = function () { this.add("parens", "insertion", function (state, action, editor, session, text) { if (text == '(') { - if (!CstyleBehaviour.isSaneInsertion(editor, session)) - return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); if (selected !== "") { @@ -161,7 +157,7 @@ var CstyleBehaviour = function () { text: '(' + selected + ')', selection: false }; - } else { + } else if (CstyleBehaviour.isSaneInsertion(editor, session)) { CstyleBehaviour.recordAutoInsert(editor, session, ")"); return { text: '()', @@ -199,8 +195,6 @@ var CstyleBehaviour = function () { this.add("brackets", "insertion", function (state, action, editor, session, text) { if (text == '[') { - if (!CstyleBehaviour.isSaneInsertion(editor, session)) - return; var selection = editor.getSelectionRange(); var selected = session.doc.getTextRange(selection); if (selected !== "") { @@ -208,7 +202,7 @@ var CstyleBehaviour = function () { text: '[' + selected + ']', selection: false }; - } else { + } else if (CstyleBehaviour.isSaneInsertion(editor, session)) { CstyleBehaviour.recordAutoInsert(editor, session, "]"); return { text: '[]', From f48d6ab5045c33d9e030d2df5a4d14ee26ab6ede Mon Sep 17 00:00:00 2001 From: C9 Date: Wed, 24 Oct 2012 01:48:41 -0400 Subject: [PATCH 23/66] Site updates --- doc/site/images/ideone-logo.png | Bin 0 -> 2938 bytes doc/site/style.css | 8 ++++++++ index.html | 5 +++++ 3 files changed, 13 insertions(+) create mode 100644 doc/site/images/ideone-logo.png diff --git a/doc/site/images/ideone-logo.png b/doc/site/images/ideone-logo.png new file mode 100644 index 0000000000000000000000000000000000000000..cbee7fadf2737aa24df8a011d4b195b57e9849f8 GIT binary patch literal 2938 zcmV-=3x)KFP)Px#24YJ`L;(K){{a7>y{D4^000SaNLh0L01FZT01FZU(%pXi00007bV*G`2iyu4 z2@*8Gd)fa001Em^L_t(&-tAj|kd;*#ex7@G7eP!EL=*(n#70!$91~4aCq~Wbm!&mo z&ZwnRf0zzMC7L0cWjQ&OPUF-VGtH>!MB<>MSyR&wO`XocBvC*eL{m^;L1C9=ckk05 zzQ+!q-*@-!F80@+8D_ux-SfTQ`}=*~_gsK%dGCqBa?ZWyUMtIc5AS{1{TfEruop`d z`w0M_wC^4XAuRXaBZPn<8t^hnCy?v_@Z%7|vm zfCn%RK)<9mlI!0I)bPCRc>utt&2XQJF+P|pIgfJh{jmU!1u)H=N&sq-Hj{itQj9U~ z&V^6>l+fw`Fjvx%BqsytlSGm=Nu4CuN?I9X+*(%8z4z?^P6IFo07D25*!^h$P62S3 zq*`)JNh<;TE5`VG1wBaGgGcAwi6mzMI0!()=(Lf11wafTtg6BqWvKE}N#C|;`3Zmp z$&*3|a?W)CSV;0J0234VNYQ1V`<-)71GpSOR}NBg&kP~Rt`}SHI37TI5!l#s4FEg6 z_rC#fO$cFgGF~o}bM8=*HvqWUTG4tQ>DhIIq?~ih0DLFLxUNtZ_6KkmfQj~wNdSH* z>3ou-O3Hyq(tCfuq=hlYmx_vwF~T`FiR3~_mykT5nDsIp_ImF-0sIocbs+@ha<&Xk z?7=pY50ktp87=V+V5j|qq&i7Y@?iio%Ti=Anse@M0M`SUB&j`9#M>mh0CcCcPI5nU zhQE04+d~Km2`9Rft-=4YIc43R?Mbvq?##+W9l#ezuCh$iEREd<;Nr|^y+(6~Iacz@ z&yoz@`$>tvq;Til1d{&%@C|d)nk48Qfp-Gfp?A^(B(+PL2;f>t_oeKT_^XwGiAKT8 zb1z*8;A4^+c5gX=vjNNmFbBYFk|&Y820*8zgC!kDQe}Y0Id>_53o>u}1%R_i9%m_d zj-*+VPLXs=#>+91ZnS6Gvif)f$#J%)Ptt7wP9%A}@i#}(Y?2PZLP^~w=O_R_GWxa5 z8TLI_uuJpKZJC!KS5kX$WkQdQxVbVZgD zuL~i3ufp5c0eIYd-$!zh@%DM=+~N>IK8^WeCc`B$#=Dv%k(JK5e@lAA=$+}k9~VN{ zR-zA*+#+dSs@)~)Yu@`;0o-h#F9PtDEK&{z@bN4io)bcNq=MFS0RH5?zaPLkcJBfJ zcUSgtO?s_EEfN4=H-KLikx!mxVvL;tmKc-0C8%;V0B7&p3gEY8NUHF8sihW3nnd!1 ztkBN}Fv{N1os5=JRT-j-G5$V{C`d=Y%(m3F+T6TZ>!=@(j6q!4;4CxL;Z+Vy@(*^|UnaA2 zt`=k5?wsqgS_}XO09bF=hvzuOfY!S<$c+E4ypoi zT`fGe1Hc9VA1t9aHB->G7-L@x0BN&xZcS#e12e@=&rs!#zEs~zRMz()btK&9Fn~Es9iGllv zF_Ud%?>Je~$z@Zetf9|8%c8A$#FZ(npd_|3#|$BC^WJX&FuO`vn?CeN+F|IeRQSxH zQlB$E>+ym@y& zeO~OG8bV#j8B?y6C^Dt>jevra4disnNrqg`_}{5oS?g;Zx-nl zYqIzLY5*PPK;4p_8VGm{6|ewU3E(y3+ex}Ccl-)@=L6V3bMW4#sIvIdG&=I$-v;0e z`|hIv)_d>o1@PDG-0cvOC)v4PIs~0iA=|Bz?zQVHz4!9~ECuk2q=pS5`T%?Yz+5|H z+hY)$ryEJP1Gt`KKgq@3`}vZVTMFz?rwNi~lKc#S6AZ=H0sK0I(Cxjig%BEptY4*w zF#UDT)j|lHy!UqkxX!lS;hZ~z^ek}k}m_@NkMQ&icW<>~g6Mogd; z-us(LUTsD?NYWJ~uc&~%*GlpLK4&!RxuRo?_c`ZI0`=A%sOXlzjrgHftnz0qB<0V-dCr!1*DB?*rJLHOk#t zUZ-7u9l$(E%WcNEHKVx;z%Dzm+zQ|&06zyXBZTmv)xZ9%7IwuLKSJ_L0G=Yb5x`qH zE&KPDq0p6fFgq*8xXpW?r~3wgR{*?agI=`~agsLJ3Bi^eNg8d%7|#Z99?2DwUNgCh z{B_y%XRRF*9T7r!DX-IIBd?#5ywg7JOibm!ISC;=3gA)i{Y0C}r{9OP0azVE*q8~l z0Kg)Wl(aR=>&hbUF#wO5fYT*SwGm4C&B<;6uf`ZRlzDkNX-@P)2ulGhwHkaB$pf=- zRh{H^No!(^JDb>|(+-X6E&d8SMe6C style="position: relative; left: 10px;top: -5px;width: 80px;" /> SpanDeX.io +
  • + + Ideone.com +
  • Sky Edit
  • From 47cb2d5871bce2ef2f3e3f3364dc59fb53bfdb3e Mon Sep 17 00:00:00 2001 From: nightwing Date: Wed, 24 Oct 2012 18:24:03 +0400 Subject: [PATCH 24/66] 'Monaco' looks better than 'Menlo' --- lib/ace/css/editor.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/css/editor.css b/lib/ace/css/editor.css index c3a7fc8e..da284a2e 100644 --- a/lib/ace/css/editor.css +++ b/lib/ace/css/editor.css @@ -1,7 +1,7 @@ .ace_editor { position: absolute; overflow: hidden; - font-family: 'Menlo', 'Monaco', 'Ubuntu Mono', 'Consolas', 'source-code-pro', monospace; + font-family: 'Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', 'source-code-pro', monospace; font-size: 12px; } From 074ed41db00477eb2e8a302aff32c6765043a996 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Fri, 12 Oct 2012 22:59:51 +1100 Subject: [PATCH 25/66] Clipboard API support, context menu Delete command support --- lib/ace/editor.js | 11 +- lib/ace/keyboard/textinput.js | 276 ++++++++++++++++------------------ 2 files changed, 136 insertions(+), 151 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 937e0e73..340e8e7f 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -656,6 +656,15 @@ var Editor = function(renderer, session) { this.insert(text); }; + /** + * Editor.onDelete() + * + * called whenever a text "delete" happens. + **/ + this.onDelete = function() { + this.commands.exec("del", this); + }; + /** * Editor.insert(text) * - text (String): The new text to add @@ -2126,4 +2135,4 @@ var Editor = function(renderer, session) { exports.Editor = Editor; -}); \ No newline at end of file +}); diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 7204c022..876872f0 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -54,69 +54,46 @@ var TextInput = function(parentNode, host) { parentNode.insertBefore(text, parentNode.firstChild); var PLACEHOLDER = useragent.isIE ? "\x01" : "\x00"; - reset(true); if (isFocused()) host.onFocus(); - var inCompostion = false; - var copied = false; var pasted = false; + var inCompostion = false; + var isSelectionEmpty = true; var tempStyle = ''; - function reset(full) { - try { - if (full) { - text.value = PLACEHOLDER; - text.selectionStart = 0; - text.selectionEnd = 1; - } else - text.select(); - } catch (e) {} - } - - function sendText(valueToSend) { - if (!copied) { - var value = valueToSend || text.value; - if (value) { - if (value.length > 1) { - if (value.charAt(0) == PLACEHOLDER) - value = value.substr(1); - else if (value.charAt(value.length - 1) == PLACEHOLDER) - value = value.slice(0, -1); - } - - if (value && value != PLACEHOLDER) { - if (pasted) - host.onPaste(value); - else - host.onTextInput(value); - } - } + host.addEventListener('changeSelection', function(){ + if (host.selection.isEmpty() != isSelectionEmpty) { + isSelectionEmpty = !isSelectionEmpty; + text.value = isSelectionEmpty ? '' : PLACEHOLDER; + text.select(); } + }); - copied = false; - pasted = false; + var onInput = function(e) { + if (inCompostion) + return; - // Safari doesn't fire copy events if no text is selected - reset(true); - } + if (pasted) { + var data = text.value; + if (data) + host.onPaste(data); + pasted = false; + } else { + var data = text.value; + if (data) + host.onTextInput(data); + else + host.onDelete(); + } + text.value = ""; - var onTextInput = function(e) { - if (!inCompostion) - sendText(e.data); - setTimeout(function () { - if (!inCompostion) - reset(true); - }, 0); - }; - - var onPropertyChange = function(e) { - setTimeout(function() { - if (!inCompostion) - if(text.value != "") { - sendText(); - } - }, 0); + //http://code.google.com/p/chromium/issues/detail?id=76516 + if (useragent.isWebKit) + setTimeout(function(){ + text.blur(); + text.focus(); + }); }; var onCompositionStart = function(e) { @@ -135,37 +112,106 @@ var TextInput = function(parentNode, host) { host.onCompositionEnd(); }; - var onCopy = function(e) { - copied = true; - var copyText = host.getCopyText(); - if(copyText) - text.value = copyText; - else - e.preventDefault(); - reset(); - setTimeout(function () { - sendText(); - }, 0); + var onCut = function(e) { + var data = host.getCopyText(); + if (!data) { + event.preventDefault(e); + return; + } + + e.clipboardData = e.clipboardData || window.clipboardData; + + if (e.clipboardData) { + // Safari 5 has clipboardData object, but does not handle setData() + var supported = e.clipboardData.setData("Text", data); + if (supported) { + host.onCut(); + event.preventDefault(e); + } + } + + if (!supported) { + text.value = data; + text.select(); + setTimeout(function(){ host.onCut() }); + } }; - var onCut = function(e) { - copied = true; - var copyText = host.getCopyText(); - if(copyText) { - text.value = copyText; - host.onCut(); - } else - e.preventDefault(); - reset(); - setTimeout(function () { - sendText(); - }, 0); + var onCopy = function(e) { + var data = host.getCopyText(); + if (!data) { + event.preventDefault(e); + return; + } + + e.clipboardData = e.clipboardData || window.clipboardData; + + if (e.clipboardData) { + // Safari 5 has clipboardData object, but does not handle setData() + var supported = e.clipboardData.setData("Text", data); + if (supported) { + host.onCopy(); + event.preventDefault(e); + } + } + if (!supported) { + text.value = data; + text.select(); + setTimeout(function(){ host.onCopy() }); + } + + + }; + + var onPaste = function(e) { + e.clipboardData = e.clipboardData || window.clipboardData; + + if (e.clipboardData) { + var data = e.clipboardData.getData("Text"); + if (data) + host.onPaste(data); + event.preventDefault(e); + } + else { + pasted = true; + } }; event.addCommandKeyListener(text, host.onCommandKey.bind(host)); - event.addListener(text, "input", onTextInput); - + + event.addListener(text, "input", onInput); + + event.addListener(text, "cut", onCut); + event.addListener(text, "copy", onCopy); + event.addListener(text, "paste", onPaste); + + + // Opera has no clipboard events + if (!('oncut' in text) || !('oncopy' in text) || !('onpaste' in text)){ + event.addListener(parentNode, "keydown", function(e) { + if ((useragent.isMac && !e.metaKey) || !e.ctrlKey) + return; + + switch (e.keyCode) { + case 67: + onCopy(e); + break; + case 86: + onPaste(e); + break; + case 88: + onCut(e); + break; + } + }); + } + if (useragent.isOldIE) { + event.addListener(text, "propertychange", function(e){ + if (text.value != "" && text.value != PLACEHOLDER) + onInput(e); + }); + var keytable = { 13:1, 27:1 }; event.addListener(text, "keyup", function (e) { if (inCompostion && (!text.value || keytable[e.keyCode])) @@ -175,70 +221,6 @@ var TextInput = function(parentNode, host) { } inCompostion ? onCompositionUpdate() : onCompositionStart(); }); - - event.addListener(text, "propertychange", function() { - if (text.value != PLACEHOLDER) - setTimeout(sendText, 0); - }); - } - - event.addListener(text, "paste", function(e) { - // Mark that the next input text comes from past. - pasted = true; - // Some browsers support the event.clipboardData API. Use this to get - // the pasted content which increases speed if pasting a lot of lines. - if (e.clipboardData && e.clipboardData.getData) { - sendText(e.clipboardData.getData("text/plain")); - e.preventDefault(); - } - else { - // If a browser doesn't support any of the things above, use the regular - // method to detect the pasted input. - onPropertyChange(); - } - }); - - if ("onbeforecopy" in text && typeof clipboardData !== "undefined") { - event.addListener(text, "beforecopy", function(e) { - if (tempStyle) - return; // without this text is copied when contextmenu is shown - var copyText = host.getCopyText(); - if (copyText) - clipboardData.setData("Text", copyText); - else - e.preventDefault(); - }); - event.addListener(parentNode, "keydown", function(e) { - if (e.ctrlKey && e.keyCode == 88) { - var copyText = host.getCopyText(); - if (copyText) { - clipboardData.setData("Text", copyText); - host.onCut(); - } - event.preventDefault(e); - } - }); - event.addListener(text, "cut", onCut); // for ie9 context menu - } - else if (useragent.isOpera && !("KeyboardEvent" in window)) { - event.addListener(parentNode, "keydown", function(e) { - if ((useragent.isMac && !e.metaKey) || !e.ctrlKey) - return; - - if ((e.keyCode == 88 || e.keyCode == 67)) { - var copyText = host.getCopyText(); - if (copyText) { - text.value = copyText; - text.select(); - if (e.keyCode == 88) - host.onCut(); - } - } - }); - } - else { - event.addListener(text, "copy", onCopy); - event.addListener(text, "cut", onCut); } event.addListener(text, "compositionstart", onCompositionStart); @@ -256,11 +238,11 @@ var TextInput = function(parentNode, host) { event.addListener(text, "focus", function() { host.onFocus(); - reset(); + text.select(); }); this.focus = function() { - reset(); + text.select(); text.focus(); }; @@ -286,11 +268,6 @@ var TextInput = function(parentNode, host) { (useragent.isIE ? "background:rgba(0, 0, 0, 0.03); opacity:0.1;" : "") + //"background:rgba(250, 0, 0, 0.3); opacity:1;" + "left:" + (e.clientX - 2) + "px; top:" + (e.clientY - 2) + "px;"; - if (host.selection.isEmpty()) - text.value = ""; - else - reset(true); - if (e.type != "mousedown") return; @@ -311,7 +288,6 @@ var TextInput = function(parentNode, host) { text.style.cssText = tempStyle; tempStyle = ''; } - sendText(); if (host.renderer.$keepTextAreaAtCursor == null) { host.renderer.$keepTextAreaAtCursor = true; host.renderer.$moveTextAreaToCursor(); From 0604b753108a15bcb508aa54358b1cadbbccf7e8 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Sat, 20 Oct 2012 19:21:32 +1100 Subject: [PATCH 26/66] change selection instead of text.value --- lib/ace/keyboard/textinput.js | 81 +++++++++++++++++++++++++---------- 1 file changed, 58 insertions(+), 23 deletions(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 876872f0..7889a09a 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -53,22 +53,54 @@ var TextInput = function(parentNode, host) { text.style.top = "-2em"; parentNode.insertBefore(text, parentNode.firstChild); - var PLACEHOLDER = useragent.isIE ? "\x01" : "\x00"; + var PLACEHOLDER = useragent.isIE || useragent.isOpera ? "\x01" : "\x00"; + + resetValue(); + if (isFocused()) host.onFocus(); + // Somehow fixes problem with firing onpropertychange on first typed char + if (useragent.isOldIE) { + resetSelection(); + resetValue(); + setTimeout(resetSelection); + } + var pasted = false; + var inCompostion = false; + var isSelectionEmpty = true; + var tempStyle = ''; - host.addEventListener('changeSelection', function(){ - if (host.selection.isEmpty() != isSelectionEmpty) { - isSelectionEmpty = !isSelectionEmpty; - text.value = isSelectionEmpty ? '' : PLACEHOLDER; - text.select(); + function resetValue() { + //http://code.google.com/p/chromium/issues/detail?id=76516 + if (!useragent.isWebKit) + text.value = PLACEHOLDER; + else + setTimeout(function(){ + text.value = PLACEHOLDER; + }); + }; + + function resetSelection() { + var selectionStart = isSelectionEmpty ? 1 : 0; + var selectionEnd = 1; + + if (text.setSelectionRange) { + text.setSelectionRange(selectionStart, selectionEnd); } - }); + // IE8 does not support setSelectionRange + else if (text.createTextRange) { + var range = text.createTextRange(); + range.collapse(true); + range.moveEnd('character', selectionEnd); + range.moveStart('character', selectionStart); + range.select(); + } + }; var onInput = function(e) { if (inCompostion) @@ -76,24 +108,19 @@ var TextInput = function(parentNode, host) { if (pasted) { var data = text.value; + resetValue(); if (data) host.onPaste(data); pasted = false; - } else { - var data = text.value; - if (data) - host.onTextInput(data); - else - host.onDelete(); + return; } - text.value = ""; - //http://code.google.com/p/chromium/issues/detail?id=76516 - if (useragent.isWebKit) - setTimeout(function(){ - text.blur(); - text.focus(); - }); + var data = text.value.substring(isSelectionEmpty ? 1 : 0); + resetValue(); + if (data) + host.onTextInput(data); + else + host.onDelete(); }; var onCompositionStart = function(e) { @@ -173,6 +200,7 @@ var TextInput = function(parentNode, host) { event.preventDefault(e); } else { + text.value = ""; pasted = true; } }; @@ -238,11 +266,10 @@ var TextInput = function(parentNode, host) { event.addListener(text, "focus", function() { host.onFocus(); - text.select(); + resetSelection(); }); this.focus = function() { - text.select(); text.focus(); }; @@ -300,8 +327,16 @@ var TextInput = function(parentNode, host) { if (!useragent.isGecko) event.addListener(text, "contextmenu", function(e) { host.textInput.onContextMenu(e); - onContextMenuClose() + onContextMenuClose(); }); + + + host.addEventListener('changeSelection', function(){ + if (host.selection.isEmpty() != isSelectionEmpty) { + isSelectionEmpty = !isSelectionEmpty; + resetSelection(); + } + }); }; exports.TextInput = TextInput; From 473ddfd353734b49691432eff97f7ada2f4e0058 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Sat, 20 Oct 2012 19:22:34 +1100 Subject: [PATCH 27/66] Add Select All context menu command support --- lib/ace/keyboard/textinput.js | 29 +++++++++++++++++++++++++---- 1 file changed, 25 insertions(+), 4 deletions(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 7889a09a..2082510a 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -53,7 +53,7 @@ var TextInput = function(parentNode, host) { text.style.top = "-2em"; parentNode.insertBefore(text, parentNode.firstChild); - var PLACEHOLDER = useragent.isIE || useragent.isOpera ? "\x01" : "\x00"; + var PLACEHOLDER = useragent.isIE || useragent.isOpera ? "\x01\x01" : "\x00\x00"; resetValue(); @@ -67,6 +67,8 @@ var TextInput = function(parentNode, host) { setTimeout(resetSelection); } + var cut = false + var copied = false; var pasted = false; var inCompostion = false; @@ -86,8 +88,8 @@ var TextInput = function(parentNode, host) { }; function resetSelection() { - var selectionStart = isSelectionEmpty ? 1 : 0; - var selectionEnd = 1; + var selectionStart = isSelectionEmpty ? 2 : 1; + var selectionEnd = 2; if (text.setSelectionRange) { text.setSelectionRange(selectionStart, selectionEnd); @@ -102,6 +104,21 @@ var TextInput = function(parentNode, host) { } }; + var onSelect = function(e) { + if (cut) { + cut = false; + return; + } + if (copied) { + copied = false; + return; + } + if (text.selectionStart === 0 && text.selectionEnd === text.value.length) { + host.selectAll(); + resetSelection(); + } + }; + var onInput = function(e) { if (inCompostion) return; @@ -115,7 +132,7 @@ var TextInput = function(parentNode, host) { return; } - var data = text.value.substring(isSelectionEmpty ? 1 : 0); + var data = text.value.substring(isSelectionEmpty ? 2 : 1); resetValue(); if (data) host.onTextInput(data); @@ -160,6 +177,7 @@ var TextInput = function(parentNode, host) { if (!supported) { text.value = data; text.select(); + cut = true; setTimeout(function(){ host.onCut() }); } }; @@ -184,6 +202,7 @@ var TextInput = function(parentNode, host) { if (!supported) { text.value = data; text.select(); + copided = true; setTimeout(function(){ host.onCopy() }); } @@ -207,6 +226,8 @@ var TextInput = function(parentNode, host) { event.addCommandKeyListener(text, host.onCommandKey.bind(host)); + event.addListener(text, "select", onSelect); + event.addListener(text, "input", onInput); event.addListener(text, "cut", onCut); From 38ef17528bd58be42df13a6c18dab5556a5df6e6 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Sun, 21 Oct 2012 03:40:07 +1100 Subject: [PATCH 28/66] Fix mistype and opera copy/cut selectAll triggering --- lib/ace/keyboard/textinput.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 2082510a..58c49967 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -175,9 +175,9 @@ var TextInput = function(parentNode, host) { } if (!supported) { + cut = true; text.value = data; text.select(); - cut = true; setTimeout(function(){ host.onCut() }); } }; @@ -200,9 +200,9 @@ var TextInput = function(parentNode, host) { } } if (!supported) { + copied = true; text.value = data; text.select(); - copided = true; setTimeout(function(){ host.onCopy() }); } From a49a0b9ad3bcc946b997c7e5fe6d483a626c34c1 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Sun, 21 Oct 2012 04:48:12 +1100 Subject: [PATCH 29/66] Fix webkit text.oninput value changing workaround --- lib/ace/keyboard/textinput.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 58c49967..05df68fa 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -78,12 +78,12 @@ var TextInput = function(parentNode, host) { var tempStyle = ''; function resetValue() { + text.value = PLACEHOLDER; //http://code.google.com/p/chromium/issues/detail?id=76516 - if (!useragent.isWebKit) - text.value = PLACEHOLDER; - else + if (useragent.isWebKit) setTimeout(function(){ text.value = PLACEHOLDER; + resetSelection(); }); }; From fcbe904435fb9026c95b077a967c8004e217eba1 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Sun, 21 Oct 2012 12:59:25 +1100 Subject: [PATCH 30/66] fix clipboardData reference --- lib/ace/keyboard/textinput.js | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 05df68fa..1a9bd3c5 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -163,11 +163,11 @@ var TextInput = function(parentNode, host) { return; } - e.clipboardData = e.clipboardData || window.clipboardData; + var clipboardData = e.clipboardData || window.clipboardData; - if (e.clipboardData) { + if (clipboardData) { // Safari 5 has clipboardData object, but does not handle setData() - var supported = e.clipboardData.setData("Text", data); + var supported = clipboardData.setData("Text", data); if (supported) { host.onCut(); event.preventDefault(e); @@ -189,11 +189,11 @@ var TextInput = function(parentNode, host) { return; } - e.clipboardData = e.clipboardData || window.clipboardData; + var clipboardData = e.clipboardData || window.clipboardData; - if (e.clipboardData) { + if (clipboardData) { // Safari 5 has clipboardData object, but does not handle setData() - var supported = e.clipboardData.setData("Text", data); + var supported = clipboardData.setData("Text", data); if (supported) { host.onCopy(); event.preventDefault(e); @@ -210,10 +210,10 @@ var TextInput = function(parentNode, host) { }; var onPaste = function(e) { - e.clipboardData = e.clipboardData || window.clipboardData; + var clipboardData = e.clipboardData || window.clipboardData; - if (e.clipboardData) { - var data = e.clipboardData.getData("Text"); + if (clipboardData) { + var data = clipboardData.getData("Text"); if (data) host.onPaste(data); event.preventDefault(e); From 00f6b46cd3e50a48a114f59ef65fd4605e9a1512 Mon Sep 17 00:00:00 2001 From: nightwing Date: Fri, 26 Oct 2012 01:45:32 +0400 Subject: [PATCH 31/66] disable autocapitalize to improve behavior on mobile browsers --- lib/ace/keyboard/textinput.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 1a9bd3c5..970a5ed0 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -48,6 +48,8 @@ var TextInput = function(parentNode, host) { text.setAttribute("x-palm-disable-auto-cap", true); text.wrap = "off"; + text.autocorrect = "off"; + text.autocapitalize = "off"; text.spellcheck = false; text.style.top = "-2em"; From 3677c36a14105cfd29ac7fda76d91ea743b2d25e Mon Sep 17 00:00:00 2001 From: nightwing Date: Fri, 26 Oct 2012 01:50:45 +0400 Subject: [PATCH 32/66] add editor.execCommand function --- lib/ace/editor.js | 10 +++------- lib/ace/keyboard/textinput.js | 2 +- 2 files changed, 4 insertions(+), 8 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 340e8e7f..67a296f8 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -656,13 +656,9 @@ var Editor = function(renderer, session) { this.insert(text); }; - /** - * Editor.onDelete() - * - * called whenever a text "delete" happens. - **/ - this.onDelete = function() { - this.commands.exec("del", this); + + this.execCommand = function(command, args) { + this.commands.exec(command, this, args); }; /** diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 970a5ed0..1e215071 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -139,7 +139,7 @@ var TextInput = function(parentNode, host) { if (data) host.onTextInput(data); else - host.onDelete(); + host.execCommand("del", {source: "ace"}); }; var onCompositionStart = function(e) { From c2c650db1cd1db06126bbd9faa2b894f64e9be2f Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Tue, 2 Oct 2012 03:36:42 +1000 Subject: [PATCH 33/66] Simplify update method of cursor layer --- lib/ace/layer/cursor.js | 58 +++++++++++++++++------------------------ 1 file changed, 24 insertions(+), 34 deletions(-) diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 9d688b57..db208f3d 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -141,57 +141,47 @@ var Cursor = function(parentEl) { this.update = function(config) { this.config = config; - if (this.session.selectionMarkerCount > 0) { - var selections = this.session.$selectionMarkers; - var i = 0, sel, cursorIndex = 0; + var selections = this.session.$selectionMarkers; + var i = 0, cursorIndex = 0; - for (var i = selections.length; i--; ) { - sel = selections[i]; - var pixelPos = this.getPixelPosition(sel.cursor, true); - if ((pixelPos.top > config.height + config.offset || - pixelPos.top < -config.offset) && i > 1) { - continue; - } + if (selections === undefined || selections.length === 0){ + selections = [{cursor: null}]; + } - var style = (this.cursors[cursorIndex++] || this.addCursor()).style; - - style.left = pixelPos.left + "px"; - style.top = pixelPos.top + "px"; - style.width = config.characterWidth + "px"; - style.height = config.lineHeight + "px"; + for (var i = selections.length; i--; ) { + var pixelPos = this.getPixelPosition(selections[i].cursor, true); + if ((pixelPos.top > config.height + config.offset || + pixelPos.top < -config.offset) && i > 1) { + continue; } - if (cursorIndex > 1) - while (this.cursors.length > cursorIndex) - this.removeCursor(); - } else { - var pixelPos = this.getPixelPosition(null, true); - var style = this.cursor.style; + + var style = (this.cursors[cursorIndex++] || this.addCursor()).style; + style.left = pixelPos.left + "px"; style.top = pixelPos.top + "px"; style.width = config.characterWidth + "px"; style.height = config.lineHeight + "px"; - - while (this.cursors.length > 1) - this.removeCursor(); } + while (this.cursors.length > cursorIndex) + this.removeCursor(); var overwrite = this.session.getOverwrite(); - if (overwrite != this.overwrite) - this.$setOverwrite(overwrite); + this.$setOverwrite(overwrite); // cache for textarea and gutter highlight this.$pixelPos = pixelPos; - this.restartTimer(); }; this.$setOverwrite = function(overwrite) { - this.overwrite = overwrite; - for (var i = this.cursors.length; i--; ) { - if (overwrite) - dom.addCssClass(this.cursors[i], "ace_overwrite"); - else - dom.removeCssClass(this.cursors[i], "ace_overwrite"); + if (overwrite != this.overwrite) { + this.overwrite = overwrite; + for (var i = this.cursors.length; i--; ) { + if (overwrite) + dom.addCssClass(this.cursors[i], "ace_overwrite"); + else + dom.removeCssClass(this.cursors[i], "ace_overwrite"); + } } }; From 4a38512616dbf69982c1393eff2166f990d0ec85 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Tue, 2 Oct 2012 03:51:24 +1000 Subject: [PATCH 34/66] Rename restartTimer to resetTimer in cursor, refactor this method --- lib/ace/layer/cursor.js | 49 ++++++++++++++++++++++++----------------- 1 file changed, 29 insertions(+), 20 deletions(-) diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index db208f3d..694ab2a5 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -58,8 +58,7 @@ var Cursor = function(parentEl) { this.setBlinking = function(blinking) { this.isBlinking = blinking; - if (blinking) - this.restartTimer(); + this.resetTimer(); }; this.addCursor = function() { @@ -88,32 +87,41 @@ var Cursor = function(parentEl) { this.isVisible = false; for (var i = this.cursors.length; i--; ) dom.addCssClass(this.cursors[i], "ace_hidden"); - clearInterval(this.blinkId); + this.resetTimer(); }; this.showCursor = function() { this.isVisible = true; for (var i = this.cursors.length; i--; ) dom.removeCssClass(this.cursors[i], "ace_hidden"); - - this.element.style.visibility = ""; - this.restartTimer(); + this.resetTimer(); }; - this.restartTimer = function() { - clearInterval(this.blinkId); - if (!this.isBlinking) - return; - if (!this.isVisible) + this.resetTimer = function() { + clearInterval(this.intervalId); + clearTimeout(this.timeoutId); + for (var i = this.cursors.length; i--; ) + this.cursors[i].style.visibility = ""; + + if (!this.isBlinking || !this.isVisible) return; - var element = this.cursors.length == 1 ? this.cursor : this.element; - this.blinkId = setInterval(function() { - element.style.visibility = "hidden"; - setTimeout(function() { - element.style.visibility = ""; - }, 400); - }, 1000); + var blink = function(){ + this.timeoutId = setTimeout(function() { + for (var i = this.cursors.length; i--; ) { + this.cursors[i].style.visibility = "hidden"; + } + }.bind(this), 0.6 * 1000); + }.bind(this); + + this.intervalId = setInterval(function() { + for (var i = this.cursors.length; i--; ) { + this.cursors[i].style.visibility = ""; + } + blink(); + }.bind(this), 1000); + + blink(); }; this.getPixelPosition = function(position, onScreen) { @@ -170,7 +178,7 @@ var Cursor = function(parentEl) { // cache for textarea and gutter highlight this.$pixelPos = pixelPos; - this.restartTimer(); + this.resetTimer(); }; this.$setOverwrite = function(overwrite) { @@ -186,7 +194,8 @@ var Cursor = function(parentEl) { }; this.destroy = function() { - clearInterval(this.blinkId); + clearInterval(this.intervalId); + clearTimeout(this.timeoutId); } }).call(Cursor.prototype); From aa9962aafd246b0652f77276f147eaa5dd830b04 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Tue, 2 Oct 2012 03:58:34 +1000 Subject: [PATCH 35/66] Add blinkInterval option to cursor --- lib/ace/layer/cursor.js | 22 ++++++++++++++++------ 1 file changed, 16 insertions(+), 6 deletions(-) diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 694ab2a5..710958b8 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -40,6 +40,7 @@ var Cursor = function(parentEl) { this.isVisible = false; this.isBlinking = true; + this.blinkInterval = 1000; this.cursors = []; this.cursor = this.addCursor(); @@ -57,8 +58,17 @@ var Cursor = function(parentEl) { }; this.setBlinking = function(blinking) { - this.isBlinking = blinking; - this.resetTimer(); + if (blinking != this.isBlinking){ + this.isBlinking = blinking; + this.resetTimer(); + } + }; + + this.setBlinkInterval = function(blinkInterval) { + if (blinkInterval != this.blinkInterval){ + this.blinkInterval = blinkInterval; + this.resetTimer(); + } }; this.addCursor = function() { @@ -103,7 +113,7 @@ var Cursor = function(parentEl) { for (var i = this.cursors.length; i--; ) this.cursors[i].style.visibility = ""; - if (!this.isBlinking || !this.isVisible) + if (!this.isBlinking || !this.blinkInterval || !this.isVisible) return; var blink = function(){ @@ -111,7 +121,7 @@ var Cursor = function(parentEl) { for (var i = this.cursors.length; i--; ) { this.cursors[i].style.visibility = "hidden"; } - }.bind(this), 0.6 * 1000); + }.bind(this), 0.6 * this.blinkInterval); }.bind(this); this.intervalId = setInterval(function() { @@ -119,7 +129,7 @@ var Cursor = function(parentEl) { this.cursors[i].style.visibility = ""; } blink(); - }.bind(this), 1000); + }.bind(this), this.blinkInterval); blink(); }; @@ -196,7 +206,7 @@ var Cursor = function(parentEl) { this.destroy = function() { clearInterval(this.intervalId); clearTimeout(this.timeoutId); - } + }; }).call(Cursor.prototype); From 1557004dfacc0680569d52e855cec40220461965 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Tue, 2 Oct 2012 04:11:56 +1000 Subject: [PATCH 36/66] Add smoothBlinking option to cursor --- lib/ace/css/editor.css | 12 ++++++++++++ lib/ace/layer/cursor.js | 25 ++++++++++++++++++++++--- 2 files changed, 34 insertions(+), 3 deletions(-) diff --git a/lib/ace/css/editor.css b/lib/ace/css/editor.css index c3a7fc8e..2603efcd 100644 --- a/lib/ace/css/editor.css +++ b/lib/ace/css/editor.css @@ -152,6 +152,18 @@ opacity: 0.2; } +.ace_smooth-blinking .ace_cursor { + -moz-transition: opacity 0.18s; + -webkit-transition: opacity 0.18s; + -o-transition: opacity 0.18s; + -ms-transition: opacity 0.18s; + transition: opacity 0.18s; +} + +.ace_cursor[style*="opacity: 0"]{ + -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)"; +} + .ace_editor.ace_multiselect .ace_cursor { border-left-width: 1px; } diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 710958b8..8bcc5423 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -41,6 +41,7 @@ var Cursor = function(parentEl) { this.isVisible = false; this.isBlinking = true; this.blinkInterval = 1000; + this.smoothBlinking = false; this.cursors = []; this.cursor = this.addCursor(); @@ -71,6 +72,17 @@ var Cursor = function(parentEl) { } }; + this.setSmoothBlinking = function(smoothBlinking) { + if (smoothBlinking != this.smoothBlinking) { + this.smoothBlinking = smoothBlinking; + if (smoothBlinking) + dom.addCssClass(this.element, "ace_smooth-blinking"); + else + dom.removeCssClass(this.element, "ace_smooth-blinking"); + this.resetTimer(); + } + }; + this.addCursor = function() { var el = dom.createElement("div"); var className = "ace_cursor"; @@ -110,23 +122,30 @@ var Cursor = function(parentEl) { this.resetTimer = function() { clearInterval(this.intervalId); clearTimeout(this.timeoutId); + if (this.smoothBlinking) + dom.removeCssClass(this.element, "ace_smooth-blinking"); for (var i = this.cursors.length; i--; ) - this.cursors[i].style.visibility = ""; + this.cursors[i].style.opacity = ""; if (!this.isBlinking || !this.blinkInterval || !this.isVisible) return; + if (this.smoothBlinking) + setTimeout(function(){ + dom.addCssClass(this.element, "ace_smooth-blinking"); + }.bind(this)); + var blink = function(){ this.timeoutId = setTimeout(function() { for (var i = this.cursors.length; i--; ) { - this.cursors[i].style.visibility = "hidden"; + this.cursors[i].style.opacity = 0; } }.bind(this), 0.6 * this.blinkInterval); }.bind(this); this.intervalId = setInterval(function() { for (var i = this.cursors.length; i--; ) { - this.cursors[i].style.visibility = ""; + this.cursors[i].style.opacity = ""; } blink(); }.bind(this), this.blinkInterval); From 73f68abfc124531bda1806b3eb1cda57e66de4f1 Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Tue, 2 Oct 2012 05:01:23 +1000 Subject: [PATCH 37/66] Retarget css-class changing from each cursor to whole cursor layer --- lib/ace/css/editor.css | 2 +- lib/ace/keyboard/emacs.js | 2 +- lib/ace/layer/cursor.js | 24 +++++++---------------- lib/ace/theme/ambiance.css | 2 +- lib/ace/theme/chrome.css | 2 +- lib/ace/theme/clouds.css | 2 +- lib/ace/theme/clouds_midnight.css | 2 +- lib/ace/theme/cobalt.css | 2 +- lib/ace/theme/crimson_editor.css | 2 +- lib/ace/theme/dawn.css | 2 +- lib/ace/theme/dreamweaver.css | 2 +- lib/ace/theme/github.css | 2 +- lib/ace/theme/idle_fingers.css | 2 +- lib/ace/theme/kr_theme.css | 2 +- lib/ace/theme/merbivore.css | 2 +- lib/ace/theme/merbivore_soft.css | 2 +- lib/ace/theme/mono_industrial.css | 4 ++-- lib/ace/theme/monokai.css | 2 +- lib/ace/theme/pastel_on_dark.css | 2 +- lib/ace/theme/solarized_dark.css | 2 +- lib/ace/theme/solarized_light.css | 2 +- lib/ace/theme/textmate.css | 2 +- lib/ace/theme/tomorrow.css | 2 +- lib/ace/theme/tomorrow_night.css | 2 +- lib/ace/theme/tomorrow_night_blue.css | 2 +- lib/ace/theme/tomorrow_night_bright.css | 2 +- lib/ace/theme/tomorrow_night_eighties.css | 2 +- lib/ace/theme/twilight.css | 2 +- lib/ace/theme/vibrant_ink.css | 2 +- lib/ace/theme/xcode.css | 2 +- tool/Theme.tmpl.css | 2 +- 31 files changed, 38 insertions(+), 48 deletions(-) diff --git a/lib/ace/css/editor.css b/lib/ace/css/editor.css index 2603efcd..07da6796 100644 --- a/lib/ace/css/editor.css +++ b/lib/ace/css/editor.css @@ -148,7 +148,7 @@ box-sizing: border-box; } -.ace_cursor.ace_hidden { +.ace_hidden-cursors .ace_cursor { opacity: 0.2; } diff --git a/lib/ace/keyboard/emacs.js b/lib/ace/keyboard/emacs.js index a1248759..8fc3aeeb 100644 --- a/lib/ace/keyboard/emacs.js +++ b/lib/ace/keyboard/emacs.js @@ -66,7 +66,7 @@ exports.handler.attach = function(editor) { opacity: 1;\ background-color: transparent;\ }\ - .emacs-mode .ace_cursor.ace_overwrite {\ + .emacs-mode .ace_overwrite-cursors .ace_cursor {\ opacity: 1;\ background-color: transparent;\ border-width: 0 0 2px 2px !important;\ diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 8bcc5423..d42b1d28 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -85,13 +85,7 @@ var Cursor = function(parentEl) { this.addCursor = function() { var el = dom.createElement("div"); - var className = "ace_cursor"; - if (!this.isVisible) - className += " ace_hidden"; - if (this.overwrite) - className += " ace_overwrite"; - - el.className = className; + el.className = "ace_cursor"; this.element.appendChild(el); this.cursors.push(el); return el; @@ -107,15 +101,13 @@ var Cursor = function(parentEl) { this.hideCursor = function() { this.isVisible = false; - for (var i = this.cursors.length; i--; ) - dom.addCssClass(this.cursors[i], "ace_hidden"); + dom.addCssClass(this.element, "ace_hidden-cursors"); this.resetTimer(); }; this.showCursor = function() { this.isVisible = true; - for (var i = this.cursors.length; i--; ) - dom.removeCssClass(this.cursors[i], "ace_hidden"); + dom.removeCssClass(this.element, "ace_hidden-cursors"); this.resetTimer(); }; @@ -213,12 +205,10 @@ var Cursor = function(parentEl) { this.$setOverwrite = function(overwrite) { if (overwrite != this.overwrite) { this.overwrite = overwrite; - for (var i = this.cursors.length; i--; ) { - if (overwrite) - dom.addCssClass(this.cursors[i], "ace_overwrite"); - else - dom.removeCssClass(this.cursors[i], "ace_overwrite"); - } + if (overwrite) + dom.addCssClass(this.element, "ace_overwrite-cursors"); + else + dom.removeCssClass(this.element, "ace_overwrite-cursors"); } }; diff --git a/lib/ace/theme/ambiance.css b/lib/ace/theme/ambiance.css index 65a25bbd..524ad03a 100644 --- a/lib/ace/theme/ambiance.css +++ b/lib/ace/theme/ambiance.css @@ -66,7 +66,7 @@ border-left: 1px solid #7991E8; } -.ace-ambiance .ace_cursor.ace_overwrite { +.ace-ambiance .ace_overwrite-cursors .ace_cursor { border: 1px solid #FFE300; background: #766B13; } diff --git a/lib/ace/theme/chrome.css b/lib/ace/theme/chrome.css index 8e166a90..773c213c 100644 --- a/lib/ace/theme/chrome.css +++ b/lib/ace/theme/chrome.css @@ -17,7 +17,7 @@ border-left: 2px solid black; } -.ace-chrome .ace_cursor.ace_overwrite { +.ace-chrome .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid black; } diff --git a/lib/ace/theme/clouds.css b/lib/ace/theme/clouds.css index 1f64a7cd..4ff7e7c2 100644 --- a/lib/ace/theme/clouds.css +++ b/lib/ace/theme/clouds.css @@ -20,7 +20,7 @@ border-left: 2px solid #000000 } -.ace-clouds .ace_cursor.ace_overwrite { +.ace-clouds .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #000000 } diff --git a/lib/ace/theme/clouds_midnight.css b/lib/ace/theme/clouds_midnight.css index 632dc4e5..6bc319d1 100644 --- a/lib/ace/theme/clouds_midnight.css +++ b/lib/ace/theme/clouds_midnight.css @@ -20,7 +20,7 @@ border-left: 2px solid #7DA5DC } -.ace-clouds-midnight .ace_cursor.ace_overwrite { +.ace-clouds-midnight .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #7DA5DC } diff --git a/lib/ace/theme/cobalt.css b/lib/ace/theme/cobalt.css index 3c8d61f9..3717ba64 100644 --- a/lib/ace/theme/cobalt.css +++ b/lib/ace/theme/cobalt.css @@ -20,7 +20,7 @@ border-left: 2px solid #FFFFFF } -.ace-cobalt .ace_cursor.ace_overwrite { +.ace-cobalt .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } diff --git a/lib/ace/theme/crimson_editor.css b/lib/ace/theme/crimson_editor.css index f8032fa4..2d4a0eef 100644 --- a/lib/ace/theme/crimson_editor.css +++ b/lib/ace/theme/crimson_editor.css @@ -26,7 +26,7 @@ border-left: 2px solid black; } -.ace-crimson-editor .ace_cursor.ace_overwrite { +.ace-crimson-editor .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid black; } diff --git a/lib/ace/theme/dawn.css b/lib/ace/theme/dawn.css index fcfd5e89..ca544fea 100644 --- a/lib/ace/theme/dawn.css +++ b/lib/ace/theme/dawn.css @@ -20,7 +20,7 @@ border-left: 2px solid #000000 } -.ace-dawn .ace_cursor.ace_overwrite { +.ace-dawn .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #000000 } diff --git a/lib/ace/theme/dreamweaver.css b/lib/ace/theme/dreamweaver.css index 04983385..30f77cbf 100644 --- a/lib/ace/theme/dreamweaver.css +++ b/lib/ace/theme/dreamweaver.css @@ -23,7 +23,7 @@ border-left: 2px solid black; } -.ace-dreamweaver .ace_cursor.ace_overwrite { +.ace-dreamweaver .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid black; } diff --git a/lib/ace/theme/github.css b/lib/ace/theme/github.css index 12ffa256..5b059727 100644 --- a/lib/ace/theme/github.css +++ b/lib/ace/theme/github.css @@ -70,7 +70,7 @@ border-left: 2px solid black; } -.ace-github .ace_cursor.ace_overwrite { +.ace-github .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid black; } diff --git a/lib/ace/theme/idle_fingers.css b/lib/ace/theme/idle_fingers.css index 1b735dff..43eff698 100644 --- a/lib/ace/theme/idle_fingers.css +++ b/lib/ace/theme/idle_fingers.css @@ -20,7 +20,7 @@ border-left: 2px solid #91FF00 } -.ace-idle-fingers .ace_cursor.ace_overwrite { +.ace-idle-fingers .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #91FF00 } diff --git a/lib/ace/theme/kr_theme.css b/lib/ace/theme/kr_theme.css index ffefb03a..0f42c384 100644 --- a/lib/ace/theme/kr_theme.css +++ b/lib/ace/theme/kr_theme.css @@ -20,7 +20,7 @@ border-left: 2px solid #FF9900 } -.ace-kr-theme .ace_cursor.ace_overwrite { +.ace-kr-theme .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FF9900 } diff --git a/lib/ace/theme/merbivore.css b/lib/ace/theme/merbivore.css index a842b716..69e81376 100644 --- a/lib/ace/theme/merbivore.css +++ b/lib/ace/theme/merbivore.css @@ -20,7 +20,7 @@ border-left: 2px solid #FFFFFF } -.ace-merbivore .ace_cursor.ace_overwrite { +.ace-merbivore .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } diff --git a/lib/ace/theme/merbivore_soft.css b/lib/ace/theme/merbivore_soft.css index 7e276a89..ddd417f8 100644 --- a/lib/ace/theme/merbivore_soft.css +++ b/lib/ace/theme/merbivore_soft.css @@ -20,7 +20,7 @@ border-left: 2px solid #FFFFFF } -.ace-merbivore-soft .ace_cursor.ace_overwrite { +.ace-merbivore-soft .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } diff --git a/lib/ace/theme/mono_industrial.css b/lib/ace/theme/mono_industrial.css index b5eb68b2..f9a318fc 100644 --- a/lib/ace/theme/mono_industrial.css +++ b/lib/ace/theme/mono_industrial.css @@ -20,7 +20,7 @@ border-left: 2px solid #FFFFFF } -.ace-mono-industrial .ace_cursor.ace_overwrite { +.ace-mono-industrial .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } @@ -135,4 +135,4 @@ .ace-mono-industrial .ace_indent-guide { background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAEklEQVQImWNQ0tH4zzBz5sz/ABAOBECKH+evAAAAAElFTkSuQmCC) right repeat-y -} \ No newline at end of file +} diff --git a/lib/ace/theme/monokai.css b/lib/ace/theme/monokai.css index 1a34fed4..ed876c79 100644 --- a/lib/ace/theme/monokai.css +++ b/lib/ace/theme/monokai.css @@ -20,7 +20,7 @@ border-left: 2px solid #F8F8F0 } -.ace-monokai .ace_cursor.ace_overwrite { +.ace-monokai .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #F8F8F0 } diff --git a/lib/ace/theme/pastel_on_dark.css b/lib/ace/theme/pastel_on_dark.css index 18f61d85..b517f22a 100644 --- a/lib/ace/theme/pastel_on_dark.css +++ b/lib/ace/theme/pastel_on_dark.css @@ -20,7 +20,7 @@ border-left: 2px solid #A7A7A7 } -.ace-pastel-on-dark .ace_cursor.ace_overwrite { +.ace-pastel-on-dark .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #A7A7A7 } diff --git a/lib/ace/theme/solarized_dark.css b/lib/ace/theme/solarized_dark.css index 26b206b0..4d47fb76 100644 --- a/lib/ace/theme/solarized_dark.css +++ b/lib/ace/theme/solarized_dark.css @@ -22,7 +22,7 @@ border-left: 2px solid #D30102 } -.ace-solarized-dark .ace_cursor.ace_overwrite { +.ace-solarized-dark .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #D30102 } diff --git a/lib/ace/theme/solarized_light.css b/lib/ace/theme/solarized_light.css index e00b9b39..65dfe8df 100644 --- a/lib/ace/theme/solarized_light.css +++ b/lib/ace/theme/solarized_light.css @@ -20,7 +20,7 @@ border-left: 2px solid #000000 } -.ace-solarized-light .ace_cursor.ace_overwrite { +.ace-solarized-light .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #000000 } diff --git a/lib/ace/theme/textmate.css b/lib/ace/theme/textmate.css index ef0be415..538700f2 100644 --- a/lib/ace/theme/textmate.css +++ b/lib/ace/theme/textmate.css @@ -20,7 +20,7 @@ border-left: 2px solid black; } -.ace-tm .ace_cursor.ace_overwrite { +.ace-tm .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid black; } diff --git a/lib/ace/theme/tomorrow.css b/lib/ace/theme/tomorrow.css index 90c397bf..a5d88b6c 100644 --- a/lib/ace/theme/tomorrow.css +++ b/lib/ace/theme/tomorrow.css @@ -20,7 +20,7 @@ border-left: 2px solid #AEAFAD } -.ace-tomorrow .ace_cursor.ace_overwrite { +.ace-tomorrow .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #AEAFAD } diff --git a/lib/ace/theme/tomorrow_night.css b/lib/ace/theme/tomorrow_night.css index 8a62bac2..0baaf323 100644 --- a/lib/ace/theme/tomorrow_night.css +++ b/lib/ace/theme/tomorrow_night.css @@ -20,7 +20,7 @@ border-left: 2px solid #AEAFAD } -.ace-tomorrow-night .ace_cursor.ace_overwrite { +.ace-tomorrow-night .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #AEAFAD } diff --git a/lib/ace/theme/tomorrow_night_blue.css b/lib/ace/theme/tomorrow_night_blue.css index ca0a84fe..daebddb1 100644 --- a/lib/ace/theme/tomorrow_night_blue.css +++ b/lib/ace/theme/tomorrow_night_blue.css @@ -21,7 +21,7 @@ border-left: 2px solid #FFFFFF } -.ace-tomorrow-night-blue .ace_cursor.ace_overwrite { +.ace-tomorrow-night-blue .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } diff --git a/lib/ace/theme/tomorrow_night_bright.css b/lib/ace/theme/tomorrow_night_bright.css index 24f4469c..065e2f00 100644 --- a/lib/ace/theme/tomorrow_night_bright.css +++ b/lib/ace/theme/tomorrow_night_bright.css @@ -20,7 +20,7 @@ border-left: 2px solid #9F9F9F } -.ace-tomorrow-night-bright .ace_cursor.ace_overwrite { +.ace-tomorrow-night-bright .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #9F9F9F } diff --git a/lib/ace/theme/tomorrow_night_eighties.css b/lib/ace/theme/tomorrow_night_eighties.css index c1695b0d..5584d62d 100644 --- a/lib/ace/theme/tomorrow_night_eighties.css +++ b/lib/ace/theme/tomorrow_night_eighties.css @@ -21,7 +21,7 @@ border-left: 2px solid #CCCCCC } -.ace-tomorrow-night-eighties .ace_cursor.ace_overwrite { +.ace-tomorrow-night-eighties .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #CCCCCC } diff --git a/lib/ace/theme/twilight.css b/lib/ace/theme/twilight.css index 3051a3e6..3ef9de2e 100644 --- a/lib/ace/theme/twilight.css +++ b/lib/ace/theme/twilight.css @@ -20,7 +20,7 @@ border-left: 2px solid #A7A7A7 } -.ace-twilight .ace_cursor.ace_overwrite { +.ace-twilight .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #A7A7A7 } diff --git a/lib/ace/theme/vibrant_ink.css b/lib/ace/theme/vibrant_ink.css index fdd965f1..c611681d 100644 --- a/lib/ace/theme/vibrant_ink.css +++ b/lib/ace/theme/vibrant_ink.css @@ -20,7 +20,7 @@ border-left: 2px solid #FFFFFF } -.ace-vibrant-ink .ace_cursor.ace_overwrite { +.ace-vibrant-ink .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #FFFFFF } diff --git a/lib/ace/theme/xcode.css b/lib/ace/theme/xcode.css index 16db2006..463703b0 100644 --- a/lib/ace/theme/xcode.css +++ b/lib/ace/theme/xcode.css @@ -22,7 +22,7 @@ border-left: 2px solid #000000 } -.ace-xcode .ace_cursor.ace_overwrite { +.ace-xcode .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid #000000 } diff --git a/tool/Theme.tmpl.css b/tool/Theme.tmpl.css index 3b83c5ba..180132f2 100644 --- a/tool/Theme.tmpl.css +++ b/tool/Theme.tmpl.css @@ -22,7 +22,7 @@ border-left: 2px solid %cursor%; } -.%cssClass% .ace_cursor.ace_overwrite { +.%cssClass% .ace_overwrite-cursors .ace_cursor { border-left: 0px; border-bottom: 1px solid %overwrite%; } From 9179b0443829dae4007e6aca9328bed8415693b5 Mon Sep 17 00:00:00 2001 From: nightwing Date: Fri, 26 Oct 2012 19:46:37 +0400 Subject: [PATCH 38/66] undo rename --- lib/ace/layer/cursor.js | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index d42b1d28..f4c1ae97 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -61,14 +61,14 @@ var Cursor = function(parentEl) { this.setBlinking = function(blinking) { if (blinking != this.isBlinking){ this.isBlinking = blinking; - this.resetTimer(); + this.restartTimer(); } }; this.setBlinkInterval = function(blinkInterval) { if (blinkInterval != this.blinkInterval){ this.blinkInterval = blinkInterval; - this.resetTimer(); + this.restartTimer(); } }; @@ -79,7 +79,7 @@ var Cursor = function(parentEl) { dom.addCssClass(this.element, "ace_smooth-blinking"); else dom.removeCssClass(this.element, "ace_smooth-blinking"); - this.resetTimer(); + this.restartTimer(); } }; @@ -102,16 +102,16 @@ var Cursor = function(parentEl) { this.hideCursor = function() { this.isVisible = false; dom.addCssClass(this.element, "ace_hidden-cursors"); - this.resetTimer(); + this.restartTimer(); }; this.showCursor = function() { this.isVisible = true; dom.removeCssClass(this.element, "ace_hidden-cursors"); - this.resetTimer(); + this.restartTimer(); }; - this.resetTimer = function() { + this.restartTimer = function() { clearInterval(this.intervalId); clearTimeout(this.timeoutId); if (this.smoothBlinking) @@ -199,7 +199,7 @@ var Cursor = function(parentEl) { // cache for textarea and gutter highlight this.$pixelPos = pixelPos; - this.resetTimer(); + this.restartTimer(); }; this.$setOverwrite = function(overwrite) { From f4507df5642539508b80f15082ad8a22d89136dd Mon Sep 17 00:00:00 2001 From: nightwing Date: Sun, 30 Sep 2012 14:30:38 +0400 Subject: [PATCH 39/66] do not break subpixel positioning of markers --- lib/ace/layer/cursor.js | 3 +-- lib/ace/layer/marker.js | 14 +++++--------- 2 files changed, 6 insertions(+), 11 deletions(-) diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 9d688b57..79d768b5 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -127,8 +127,7 @@ var Cursor = function(parentEl) { if (!position) position = this.session.selection.getCursor(); var pos = this.session.documentToScreenPosition(position); - var cursorLeft = Math.round(this.$padding + - pos.column * this.config.characterWidth); + var cursorLeft = this.$padding + pos.column * this.config.characterWidth; var cursorTop = (pos.row - (onScreen ? this.config.firstRowScreen : 0)) * this.config.lineHeight; diff --git a/lib/ace/layer/marker.js b/lib/ace/layer/marker.js index 7470bfd7..444ecdc3 100644 --- a/lib/ace/layer/marker.js +++ b/lib/ace/layer/marker.js @@ -78,9 +78,7 @@ var Marker = function(parentEl) { range = range.toScreenRange(this.session); if (marker.renderer) { var top = this.$getTop(range.start.row, config); - var left = Math.round( - this.$padding + range.start.column * config.characterWidth - ); + var left = this.$padding + range.start.column * config.characterWidth; marker.renderer(html, range, left, top, config); } else if (range.isMultiLine()) { @@ -137,7 +135,7 @@ var Marker = function(parentEl) { // from selection start to the end of the line var height = config.lineHeight; var top = this.$getTop(range.start.row, config); - var left = Math.round(padding + range.start.column * config.characterWidth); + var left = padding + range.start.column * config.characterWidth; stringBuilder.push( "
    Date: Fri, 26 Oct 2012 21:49:53 +0400 Subject: [PATCH 42/66] Actually fix "Cannot read property env of null" --- lib/ace/ace.js | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/lib/ace/ace.js b/lib/ace/ace.js index f0e7f50b..b40ab454 100644 --- a/lib/ace/ace.js +++ b/lib/ace/ace.js @@ -66,9 +66,8 @@ exports.config = require("./config"); exports.edit = function(el) { if (typeof(el) == "string") { var _id = el; - if (!(el = document.getElementById(el))) { - console.log("can't match div #" + _id); - } + if (!(el = document.getElementById(el))) + throw "ace.edit can't find div #" + _id; } if (el.env && el.env.editor instanceof Editor) From f7786930e9218e0304710bebf098328a21bc78ff Mon Sep 17 00:00:00 2001 From: nightwing Date: Mon, 1 Oct 2012 17:08:52 +0400 Subject: [PATCH 43/66] add fullLine type for markers --- lib/ace/layer/marker.js | 49 +++++++++++++++++++++++------------------ 1 file changed, 27 insertions(+), 22 deletions(-) diff --git a/lib/ace/layer/marker.js b/lib/ace/layer/marker.js index 444ecdc3..e09a3c9b 100644 --- a/lib/ace/layer/marker.js +++ b/lib/ace/layer/marker.js @@ -81,21 +81,17 @@ var Marker = function(parentEl) { var left = this.$padding + range.start.column * config.characterWidth; marker.renderer(html, range, left, top, config); } + if (marker.type == "fullLine") { + this.drawFullLineMarker(html, range, marker.clazz, config); + } else if (range.isMultiLine()) { - if (marker.type == "text") { + if (marker.type == "text") this.drawTextMarker(html, range, marker.clazz, config); - } else { - this.drawMultiLineMarker( - html, range, marker.clazz, config, - marker.type - ); - } + else + this.drawMultiLineMarker(html, range, marker.clazz, config); } else { - this.drawSingleLineMarker( - html, range, marker.clazz + " ace_start", config, - null, marker.type - ); + this.drawSingleLineMarker(html, range, marker.clazz + " ace_start", config); } } this.element = dom.setInnerHtml(this.element, html.join("")); @@ -131,8 +127,8 @@ var Marker = function(parentEl) { // Draws a multi line marker, where lines span the full width this.drawMultiLineMarker = function(stringBuilder, range, clazz, config, type) { - var padding = type === "background" ? 0 : this.$padding; // from selection start to the end of the line + var padding = this.$padding; var height = config.lineHeight; var top = this.$getTop(range.start.row, config); var left = padding + range.start.column * config.characterWidth; @@ -173,17 +169,12 @@ var Marker = function(parentEl) { }; // Draws a marker which covers part or whole width of a single screen line - this.drawSingleLineMarker = function(stringBuilder, range, clazz, layerConfig, extraLength, type) { - var padding = type === "background" ? 0 : this.$padding; - var height = layerConfig.lineHeight; + this.drawSingleLineMarker = function(stringBuilder, range, clazz, config, extraLength) { + var height = config.lineHeight; + var width = (range.end.column + (extraLength || 0) - range.start.column) * config.characterWidth; - if (type === "background") - var width = layerConfig.width; - else - width = (range.end.column + (extraLength || 0) - range.start.column) * layerConfig.characterWidth; - - var top = this.$getTop(range.start.row, layerConfig); - var left = padding + range.start.column * layerConfig.characterWidth; + var top = this.$getTop(range.start.row, config); + var left = this.$padding + range.start.column * config.characterWidth; stringBuilder.push( "
    " + ); + } + }).call(Marker.prototype); exports.Marker = Marker; From dfe918e339dc2c1d4adef0bfa0f850b387964326 Mon Sep 17 00:00:00 2001 From: nightwing Date: Mon, 1 Oct 2012 17:12:42 +0400 Subject: [PATCH 44/66] fix line highlight on the last line Issue #934 --- lib/ace/edit_session.js | 33 +++++++++++++++++++++++++-------- lib/ace/editor.js | 32 ++++++++++++++------------------ 2 files changed, 39 insertions(+), 26 deletions(-) diff --git a/lib/ace/edit_session.js b/lib/ace/edit_session.js index a739b677..d24888da 100644 --- a/lib/ace/edit_session.js +++ b/lib/ace/edit_session.js @@ -375,14 +375,7 @@ var EditSession = function(text, mode) { token.start = c - token.value.length; return token; }; - - this.highlight = function(re) { - if (!this.$searchHighlight) { - var highlight = new SearchHighlight(null, "ace_selected-word", "text"); - this.$searchHighlight = this.addDynamicMarker(highlight); - } - this.$searchHighlight.setRegexp(re); - } + /** * EditSession.setUndoManager(undoManager) * - undoManager (UndoManager): The new undo manager @@ -736,6 +729,30 @@ var EditSession = function(text, mode) { return inFront ? this.$frontMarkers : this.$backMarkers; }; + this.highlight = function(re) { + if (!this.$searchHighlight) { + var highlight = new SearchHighlight(null, "ace_selected-word", "text"); + this.$searchHighlight = this.addDynamicMarker(highlight); + } + this.$searchHighlight.setRegexp(re); + } + + // experimental + this.highlightLines = function(startRow, endRow, clazz, inFront) { + if (typeof endRow != "number") { + clazz = endRow; + endRow = startRow; + } + if (!clazz) + clazz = "ace_step"; + + var range = new Range(startRow, 0, endRow, Infinity); + + var id = this.addMarker(range, clazz, "fullLine", inFront); + range.id = id; + return range; + }, + /* * Error: * { diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 937e0e73..16588ec0 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -481,28 +481,24 @@ var Editor = function(renderer, session) { this.$updateHighlightActiveLine = function() { var session = this.getSession(); - if (session.$highlightLineMarker) - session.removeMarker(session.$highlightLineMarker); - - session.$highlightLineMarker = null; - + var highlight; if (this.$highlightActiveLine) { - var cursor = this.getCursorPosition(); - var foldLine = this.session.getFoldLine(cursor.row); + if ((this.$selectionStyle != "line" || !this.selection.isMultiLine())) + highlight = this.getCursorPosition(); + } - if ((this.getSelectionStyle() != "line" || !this.selection.isMultiLine())) { - var range; - if (foldLine) { - range = new Range(foldLine.start.row, 0, foldLine.end.row + 1, 0); - } else { - range = new Range(cursor.row, 0, cursor.row+1, 0); - } - session.$highlightLineMarker = session.addMarker(range, "ace_active-line", "background"); - } + if (session.$highlightLineMarker && !highlight) { + session.removeMarker(session.$highlightLineMarker.id); + session.$highlightLineMarker = null; + } else if (!session.$highlightLineMarker && highlight) { + session.$highlightLineMarker = session.highlightLines(highlight.row, highlight.row, "ace_active-line"); + } else if (highlight) { + session.$highlightLineMarker.start.row = highlight.row; + session.$highlightLineMarker.end.row = highlight.row; + session._emit("changeBackMarker"); } }; - this.onSelectionChange = function(e) { var session = this.session; @@ -2126,4 +2122,4 @@ var Editor = function(renderer, session) { exports.Editor = Editor; -}); \ No newline at end of file +}); From 673646da30e6bbc04f2f705272e7f83358084a6f Mon Sep 17 00:00:00 2001 From: cadorn Date: Fri, 19 Oct 2012 08:56:58 -0700 Subject: [PATCH 45/66] set dryice version --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index bd226318..21fa0334 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ "asyncjs": "0.0.x", "jsdom": "0.2.x", "amd-loader": "~0.0.4", - "dryice": "" + "dryice": "0.4.2" }, "mappings": { "ace": "." From d9c64099220444b42f2e1fcfd6fc6aa2486f3ce8 Mon Sep 17 00:00:00 2001 From: cadorn Date: Fri, 19 Oct 2012 09:58:22 -0700 Subject: [PATCH 46/66] error out properly if post install throws error --- install.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/install.js b/install.js index 730fc12c..fcb1fb7d 100644 --- a/install.js +++ b/install.js @@ -61,8 +61,9 @@ try { suffix: "", name: "ace" }); -} catch (e) { - console.log("--- Ace Build error ---"); - console.log(e); - process.exit(0); + +} catch (err) { + console.error("--- Ace Build error ---"); + console.error(err.stack); + process.exit(1); } \ No newline at end of file From 4fabcca2af1f951123a17c366cce8f1e4863cf9d Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 27 Oct 2012 00:47:57 +0400 Subject: [PATCH 47/66] use latest dryice version compatible with node 0.6 --- Makefile.dryice.js | 5 ++++- package.json | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/Makefile.dryice.js b/Makefile.dryice.js index 3109f84f..4f56c016 100755 --- a/Makefile.dryice.js +++ b/Makefile.dryice.js @@ -30,8 +30,11 @@ * ***** END LICENSE BLOCK ***** */ var fs = require("fs"); +var path = require("path"); if (!fs.existsSync) - fs.existsSync = require("path").existsSync; + fs.existsSync = path.existsSync; +else + path.existsSync = fs.existsSync; var copy = require('dryice').copy; var ACE_HOME = __dirname; diff --git a/package.json b/package.json index 21fa0334..eff404d8 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ "asyncjs": "0.0.x", "jsdom": "0.2.x", "amd-loader": "~0.0.4", - "dryice": "0.4.2" + "dryice": "0.4.7" }, "mappings": { "ace": "." From 9472d497a326632fadd00afe34a52cbfc8cb44fa Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 27 Oct 2012 17:34:40 +0400 Subject: [PATCH 48/66] add basePath config --- lib/ace/config.js | 17 ++++++---- lib/ace/config_test.js | 71 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 82 insertions(+), 6 deletions(-) create mode 100644 lib/ace/config_test.js diff --git a/lib/ace/config.js b/lib/ace/config.js index cf8151cb..5a1b0e47 100644 --- a/lib/ace/config.js +++ b/lib/ace/config.js @@ -39,9 +39,10 @@ var global = (function() { var options = { packaged: false, - workerPath: "", - modePath: "", - themePath: "", + workerPath: null, + modePath: null, + themePath: null, + basePath: "", suffix: ".js", $moduleUrls: {} }; @@ -74,7 +75,12 @@ exports.moduleUrl = function(name, component) { if (!base && parts.length > 1) base = parts[parts.length - 2]; - return this.get(component + "Path") + "/" + component + "-" + base + this.get("suffix"); + var path = options[component + "Path"]; + if (path == null) + path = options.basePath; + if (path && path.slice(-1) != "/") + path += "/"; + return path + component + "-" + base + this.get("suffix"); }; exports.setModuleUrl = function(name, subst) { @@ -95,9 +101,8 @@ exports.init = function() { var script = scripts[i]; var src = script.src || script.getAttribute("src"); - if (!src) { + if (!src) continue; - } var attributes = script.attributes; for (var j=0, l=attributes.length; j < l; j++) { diff --git a/lib/ace/config_test.js b/lib/ace/config_test.js new file mode 100644 index 00000000..efb3f2dd --- /dev/null +++ b/lib/ace/config_test.js @@ -0,0 +1,71 @@ +/* ***** BEGIN LICENSE BLOCK ***** + * Distributed under the BSD license: + * + * Copyright (c) 2010, Ajax.org B.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of Ajax.org B.V. nor the + * names of its contributors may be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * ***** END LICENSE BLOCK ***** */ + +if (typeof process !== "undefined") { + require("amd-loader"); +} + +define(function(require, exports, module) { +"use strict"; + +var config = require("ace/config"); +var assert = require("./test/assertions"); + +module.exports = { + + "test path resolution" : function() { + config.set("packaged", "true"); + var url = config.moduleUrl("kr_theme", "theme"); + assert.equal(url, "theme-kr.js"); + + config.set("basePath", "a/b"); + url = config.moduleUrl("m/theme", "theme"); + assert.equal(url, "a/b/theme-m.js"); + + url = config.moduleUrl("m/theme", "ext"); + assert.equal(url, "a/b/ext-theme.js"); + + config.set("workerPath", "c/"); + url = config.moduleUrl("foo/1", "worker"); + assert.equal(url, "c/worker-1.js"); + + config.setModuleUrl("foo/1", "a/b1.js"); + url = config.moduleUrl("foo/1", "theme"); + assert.equal(url, "a/b1.js"); + + assert.equal(); + } +}; + +}); + +if (typeof module !== "undefined" && module === require.main) { + require("asyncjs").test.testcase(module.exports).exec() +} From 0a88689f1b9dc6c09beb9c8154579cbba33ebcfa Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 27 Oct 2012 17:36:40 +0400 Subject: [PATCH 49/66] fix workers on ace.ajax.org --- doc/site/js/main.js | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/site/js/main.js b/doc/site/js/main.js index 49f91f5e..efa7ba2b 100644 --- a/doc/site/js/main.js +++ b/doc/site/js/main.js @@ -2,6 +2,7 @@ var editor; var embedded_editor; $(function() { hljs.initHighlighting(); + ace.config.set("workerPath", "build/src-min"); editor = ace.edit("ace_editor_demo"); embedded_editor = ace.edit("embedded_ace_code"); editor.getSession().setMode("ace/mode/javascript"); From b50d0cde96ab995be2dfc9bfd9c970b82d6862f4 Mon Sep 17 00:00:00 2001 From: nightwing Date: Sat, 27 Oct 2012 17:43:00 +0400 Subject: [PATCH 50/66] fix test --- lib/ace/config_test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/config_test.js b/lib/ace/config_test.js index efb3f2dd..9d0c4697 100644 --- a/lib/ace/config_test.js +++ b/lib/ace/config_test.js @@ -35,7 +35,7 @@ if (typeof process !== "undefined") { define(function(require, exports, module) { "use strict"; -var config = require("ace/config"); +var config = require("./config"); var assert = require("./test/assertions"); module.exports = { From e3ad71b4e157ac828aa6c43975c42049839eaf1e Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Mon, 22 Oct 2012 18:37:23 +0200 Subject: [PATCH 51/66] modifiy numbers with keyboard --- lib/ace/commands/default_commands.js | 10 ++++ lib/ace/editor.js | 87 +++++++++++++++++++++++++++- 2 files changed, 96 insertions(+), 1 deletion(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index 9da2dd1d..458d5582 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -331,6 +331,16 @@ exports.commands = [{ bindKey: bindKey("Ctrl-/", "Command-/"), exec: function(editor) { editor.toggleCommentLines(); }, multiSelectAction: "forEach" +}, { + name: "modifyNumber+1", + bindKey: bindKey("Ctrl-Shift-Up", "Ctrl-Command-Up"), + exec: function(editor) { editor.modifyNumber(1); }, + multiSelectAction: "forEach" +}, { + name: "modifyNumber-1", + bindKey: bindKey("Ctrl-Shift-Down", "Ctrl-Command-Down"), + exec: function(editor) { editor.modifyNumber(-1); }, + multiSelectAction: "forEach" }, { name: "replace", bindKey: bindKey("Ctrl-R", "Command-Option-F"), diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 937e0e73..190e0d86 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1312,6 +1312,91 @@ var Editor = function(renderer, session) { this.session.getMode().toggleCommentLines(state, this.session, rows.first, rows.last); }; + /** + * Editor.getNumberAt() + * + * Works like getTokenAt just that it returns a number + **/ + this.getNumberAt = function( row, column ) { + var _numberRx = /[\-]?[0-9]+(?:\.[0-9]+)?/g + _numberRx.lastIndex = 0 + + var s = this.session.getLine(row) + while(_numberRx.lastIndex < column - 1 ){ + var m = _numberRx.exec(s) + if(m.index <= column && m.index+m[0].length >= column){ + var number = { + value: m[0], + start: m.index, + end: m.index+m[0].length + + } + return number + } + } + return null; + }; + /** + * Editor.modifyNumber() + * + * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Ctrl+Cmd+Up/Down (Mac) Ctrl+Shift+Up/Down (Win) + **/ + this.modifyNumber = function( amount ) { + var row = this.selection.getCursor().row; + var column = this.selection.getCursor().column; + + //get the char before the cursor + var charRange = new Range(0,0,0,0); + charRange.start.row = row; + charRange.end.row = row; + charRange.start.column = column-1; + charRange.end.column = column; + + var c = this.session.getTextRange(charRange); + //if the char is a digit + if( !isNaN(parseFloat(c)) && isFinite(c) ) { + //get the whole number the digit is part of + var nr = this.getNumberAt(row, column); + //if number found + if( nr ) { + var fp = nr.value.indexOf(".") >= 0 ? nr.start + nr.value.indexOf(".") + 1 : nr.end; + var decimals = nr.start + nr.value.length - fp; + + var t = parseFloat(nr.value); + t *= Math.pow(10, decimals); + + + if( fp !== nr.end && column < fp){ + amount *= Math.pow(10, nr.end - column - 1); + } else { + amount *= Math.pow(10, nr.end - column); + } + + t += amount; + t /= Math.pow(10, decimals); + var nnr = t.toFixed(decimals); + + //update number + var replaceRange = new Range(0, 0, 0, 0); + replaceRange.start.row = row; + replaceRange.end.row = row; + replaceRange.start.column = nr.start; + replaceRange.end.column = nr.end; + this.session.replace(replaceRange, nnr ); + + var cursor = column; + var offset = nnr.length - nr.value.length; + + + cursor = Math.max(nr.start +1, cursor + offset); + console.log(offset, nr.value.length, nnr.length) + //reposition the cursor + this.moveCursorTo(row, cursor ); + + } + } + }; + /** related to: EditSession.remove * Editor.removeLines() * @@ -2126,4 +2211,4 @@ var Editor = function(renderer, session) { exports.Editor = Editor; -}); \ No newline at end of file +}); From 9c3e6c5cce7c29070d6c630150863ba2e6a343ed Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Mon, 22 Oct 2012 18:42:05 +0200 Subject: [PATCH 52/66] reformat the code --- lib/ace/editor.js | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 190e0d86..5c34e33d 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1341,7 +1341,7 @@ var Editor = function(renderer, session) { * * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Ctrl+Cmd+Up/Down (Mac) Ctrl+Shift+Up/Down (Win) **/ - this.modifyNumber = function( amount ) { + this.modifyNumber = function(amount) { var row = this.selection.getCursor().row; var column = this.selection.getCursor().column; @@ -1354,11 +1354,11 @@ var Editor = function(renderer, session) { var c = this.session.getTextRange(charRange); //if the char is a digit - if( !isNaN(parseFloat(c)) && isFinite(c) ) { + if(!isNaN(parseFloat(c)) && isFinite(c)) { //get the whole number the digit is part of var nr = this.getNumberAt(row, column); //if number found - if( nr ) { + if(nr) { var fp = nr.value.indexOf(".") >= 0 ? nr.start + nr.value.indexOf(".") + 1 : nr.end; var decimals = nr.start + nr.value.length - fp; @@ -1366,7 +1366,7 @@ var Editor = function(renderer, session) { t *= Math.pow(10, decimals); - if( fp !== nr.end && column < fp){ + if(fp !== nr.end && column < fp){ amount *= Math.pow(10, nr.end - column - 1); } else { amount *= Math.pow(10, nr.end - column); @@ -1382,16 +1382,10 @@ var Editor = function(renderer, session) { replaceRange.end.row = row; replaceRange.start.column = nr.start; replaceRange.end.column = nr.end; - this.session.replace(replaceRange, nnr ); + this.session.replace(replaceRange, nnr); - var cursor = column; - var offset = nnr.length - nr.value.length; - - - cursor = Math.max(nr.start +1, cursor + offset); - console.log(offset, nr.value.length, nnr.length) //reposition the cursor - this.moveCursorTo(row, cursor ); + this.moveCursorTo(row, Math.max(nr.start +1, column + nnr.length - nr.value.length)); } } From 82c07a5f68da4b1bfb59f7ebddfd6a07b8eea598 Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Tue, 23 Oct 2012 10:49:52 +0200 Subject: [PATCH 53/66] update keyboard shortcut for modifyNumber --- lib/ace/commands/default_commands.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index 458d5582..b833f0ca 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -333,12 +333,12 @@ exports.commands = [{ multiSelectAction: "forEach" }, { name: "modifyNumber+1", - bindKey: bindKey("Ctrl-Shift-Up", "Ctrl-Command-Up"), + bindKey: bindKey("Alt-Shift-Up", "Alt-Shift-Up"), exec: function(editor) { editor.modifyNumber(1); }, multiSelectAction: "forEach" }, { name: "modifyNumber-1", - bindKey: bindKey("Ctrl-Shift-Down", "Ctrl-Command-Down"), + bindKey: bindKey("Alt-Shift-Down", "Alt-Shift-Down"), exec: function(editor) { editor.modifyNumber(-1); }, multiSelectAction: "forEach" }, { From 66f46cc6ef8a05ae84d4eb7964eaca9b91efe5e8 Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Tue, 23 Oct 2012 10:54:27 +0200 Subject: [PATCH 54/66] update description of modifyNumber --- lib/ace/editor.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 5c34e33d..1ac6e2c2 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1339,7 +1339,8 @@ var Editor = function(renderer, session) { /** * Editor.modifyNumber() * - * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Ctrl+Cmd+Up/Down (Mac) Ctrl+Shift+Up/Down (Win) + * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Ctrl+Cmd+Up/Down (Mac) Ctrl+Shift+Up/Down (Win). + * This will update the whole number the digit is part of. **/ this.modifyNumber = function(amount) { var row = this.selection.getCursor().row; From 073ee0cbf6e85b7d98e29f41ea697e6396f9b936 Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Tue, 23 Oct 2012 10:55:19 +0200 Subject: [PATCH 55/66] update description of modifyNumber --- lib/ace/editor.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 1ac6e2c2..318844a3 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1339,7 +1339,7 @@ var Editor = function(renderer, session) { /** * Editor.modifyNumber() * - * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Ctrl+Cmd+Up/Down (Mac) Ctrl+Shift+Up/Down (Win). + * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Alt+Shift+Up/Down. * This will update the whole number the digit is part of. **/ this.modifyNumber = function(amount) { From 048c88cf5e31a466a3f9d86544511e93b22f9d64 Mon Sep 17 00:00:00 2001 From: Vlad Zinculescu Date: Tue, 23 Oct 2012 12:17:25 +0200 Subject: [PATCH 56/66] update keybinding for modifyNumber on windows --- lib/ace/commands/default_commands.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index b833f0ca..ec85f61c 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -333,12 +333,12 @@ exports.commands = [{ multiSelectAction: "forEach" }, { name: "modifyNumber+1", - bindKey: bindKey("Alt-Shift-Up", "Alt-Shift-Up"), + bindKey: bindKey("Ctrl-Shift-Up", "Alt-Shift-Up"), exec: function(editor) { editor.modifyNumber(1); }, multiSelectAction: "forEach" }, { name: "modifyNumber-1", - bindKey: bindKey("Alt-Shift-Down", "Alt-Shift-Down"), + bindKey: bindKey("Ctrl-Shift-Down", "Alt-Shift-Down"), exec: function(editor) { editor.modifyNumber(-1); }, multiSelectAction: "forEach" }, { From 43c74f415fe875f4675889bbadda2d93444bdb7c Mon Sep 17 00:00:00 2001 From: Garen Torikian Date: Tue, 23 Oct 2012 11:00:13 -0700 Subject: [PATCH 57/66] Add tenth place, fix doc comments --- lib/ace/commands/default_commands.js | 10 ++++++++++ lib/ace/editor.js | 10 +++++----- 2 files changed, 15 insertions(+), 5 deletions(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index ec85f61c..f7c96538 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -341,6 +341,16 @@ exports.commands = [{ bindKey: bindKey("Ctrl-Shift-Down", "Alt-Shift-Down"), exec: function(editor) { editor.modifyNumber(-1); }, multiSelectAction: "forEach" +}, { + name: "modifyNumber+10", + bindKey: bindKey("Ctrl-Alt-Shift-Up", "Alt-Command-Shift-Up"), + exec: function(editor) { editor.modifyNumber(10); }, + multiSelectAction: "forEach" +}, { + name: "modifyNumber-10", + bindKey: bindKey("Ctrl-Alt-Shift-Down", "Alt-Command-Shift-Down"), + exec: function(editor) { editor.modifyNumber(-10); }, + multiSelectAction: "forEach" }, { name: "replace", bindKey: bindKey("Ctrl-R", "Command-Option-F"), diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 318844a3..85fb5a18 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1304,7 +1304,7 @@ var Editor = function(renderer, session) { /** * Editor.toggleCommentLines() * - * Given the currently selected range, this function either comments all lines or uncomments all lines (depending on whether it's commented or not). + * Given the currently selected range, this function either comments all the lines, or uncomments all of them. **/ this.toggleCommentLines = function() { var state = this.session.getState(this.getCursorPosition().row); @@ -1313,9 +1313,9 @@ var Editor = function(renderer, session) { }; /** - * Editor.getNumberAt() + * Editor.getNumberAt() -> Number * - * Works like getTokenAt just that it returns a number + * Works like [[Editor.getTokenAt]], excepts it returns a number. **/ this.getNumberAt = function( row, column ) { var _numberRx = /[\-]?[0-9]+(?:\.[0-9]+)?/g @@ -1339,8 +1339,8 @@ var Editor = function(renderer, session) { /** * Editor.modifyNumber() * - * If the character before the cursor is a number, you can increase/descrease it's value with 1 by pressing Alt+Shift+Up/Down. - * This will update the whole number the digit is part of. + * If the character before the cursor is a number, you can increase/or decrease its value by one (by pressing Ctrl+Shift+Up/Down), or + * 10 (by pressing Ctrl+Alt+Shift+Up/Down). **/ this.modifyNumber = function(amount) { var row = this.selection.getCursor().row; From 23f7fc465859783a928d407abcfec4d56a7472e6 Mon Sep 17 00:00:00 2001 From: Garen Torikian Date: Tue, 23 Oct 2012 11:42:22 -0700 Subject: [PATCH 58/66] Remove +10, change command name --- lib/ace/commands/default_commands.js | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/lib/ace/commands/default_commands.js b/lib/ace/commands/default_commands.js index f7c96538..8c33fc42 100644 --- a/lib/ace/commands/default_commands.js +++ b/lib/ace/commands/default_commands.js @@ -332,25 +332,15 @@ exports.commands = [{ exec: function(editor) { editor.toggleCommentLines(); }, multiSelectAction: "forEach" }, { - name: "modifyNumber+1", + name: "modifyNumberUp", bindKey: bindKey("Ctrl-Shift-Up", "Alt-Shift-Up"), exec: function(editor) { editor.modifyNumber(1); }, multiSelectAction: "forEach" }, { - name: "modifyNumber-1", + name: "modifyNumberDown", bindKey: bindKey("Ctrl-Shift-Down", "Alt-Shift-Down"), exec: function(editor) { editor.modifyNumber(-1); }, multiSelectAction: "forEach" -}, { - name: "modifyNumber+10", - bindKey: bindKey("Ctrl-Alt-Shift-Up", "Alt-Command-Shift-Up"), - exec: function(editor) { editor.modifyNumber(10); }, - multiSelectAction: "forEach" -}, { - name: "modifyNumber-10", - bindKey: bindKey("Ctrl-Alt-Shift-Down", "Alt-Command-Shift-Down"), - exec: function(editor) { editor.modifyNumber(-10); }, - multiSelectAction: "forEach" }, { name: "replace", bindKey: bindKey("Ctrl-R", "Command-Option-F"), From aca8b9a73b5b74e1b588f9bc52343026f43512a1 Mon Sep 17 00:00:00 2001 From: Garen Torikian Date: Tue, 23 Oct 2012 11:46:36 -0700 Subject: [PATCH 59/66] Fix doc comment --- lib/ace/editor.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 85fb5a18..1551473c 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1337,10 +1337,10 @@ var Editor = function(renderer, session) { return null; }; /** - * Editor.modifyNumber() - * - * If the character before the cursor is a number, you can increase/or decrease its value by one (by pressing Ctrl+Shift+Up/Down), or - * 10 (by pressing Ctrl+Alt+Shift+Up/Down). + * Editor.modifyNumber(amount) + * - amount (Number): The value to change the numeral by (can be negative to decrease value) + * + * If the character before the cursor is a number, this functions changes its value by `amount`. **/ this.modifyNumber = function(amount) { var row = this.selection.getCursor().row; From 961b6cecb6ce6e4d55bb402ef82fb2b1bd7ccab9 Mon Sep 17 00:00:00 2001 From: nightwing Date: Tue, 23 Oct 2012 23:07:36 +0400 Subject: [PATCH 60/66] small cleanup --- lib/ace/editor.js | 28 ++++++++++------------------ 1 file changed, 10 insertions(+), 18 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 1551473c..1ab72848 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -1315,7 +1315,7 @@ var Editor = function(renderer, session) { /** * Editor.getNumberAt() -> Number * - * Works like [[Editor.getTokenAt]], excepts it returns a number. + * Works like [[Editor.getTokenAt]], except it returns a number. **/ this.getNumberAt = function( row, column ) { var _numberRx = /[\-]?[0-9]+(?:\.[0-9]+)?/g @@ -1346,20 +1346,16 @@ var Editor = function(renderer, session) { var row = this.selection.getCursor().row; var column = this.selection.getCursor().column; - //get the char before the cursor - var charRange = new Range(0,0,0,0); - charRange.start.row = row; - charRange.end.row = row; - charRange.start.column = column-1; - charRange.end.column = column; + // get the char before the cursor + var charRange = new Range(row, column-1, row, column); var c = this.session.getTextRange(charRange); - //if the char is a digit - if(!isNaN(parseFloat(c)) && isFinite(c)) { - //get the whole number the digit is part of + // if the char is a digit + if (!isNaN(parseFloat(c)) && isFinite(c)) { + // get the whole number the digit is part of var nr = this.getNumberAt(row, column); - //if number found - if(nr) { + // if number found + if (nr) { var fp = nr.value.indexOf(".") >= 0 ? nr.start + nr.value.indexOf(".") + 1 : nr.end; var decimals = nr.start + nr.value.length - fp; @@ -1378,18 +1374,14 @@ var Editor = function(renderer, session) { var nnr = t.toFixed(decimals); //update number - var replaceRange = new Range(0, 0, 0, 0); - replaceRange.start.row = row; - replaceRange.end.row = row; - replaceRange.start.column = nr.start; - replaceRange.end.column = nr.end; + var replaceRange = new Range(row, nr.start, row, nr.end); this.session.replace(replaceRange, nnr); //reposition the cursor this.moveCursorTo(row, Math.max(nr.start +1, column + nnr.length - nr.value.length)); } - } + } }; /** related to: EditSession.remove From fb401dc2988af417b7052abad8b0095c412503c1 Mon Sep 17 00:00:00 2001 From: nightwing Date: Mon, 29 Oct 2012 10:17:07 +0400 Subject: [PATCH 61/66] update require.js --- demo/kitchen-sink/require.js | 1037 +++++++++++++++++----------------- tool/update_deps.js | 4 + 2 files changed, 519 insertions(+), 522 deletions(-) diff --git a/demo/kitchen-sink/require.js b/demo/kitchen-sink/require.js index d016e1da..39dbad8e 100644 --- a/demo/kitchen-sink/require.js +++ b/demo/kitchen-sink/require.js @@ -1,21 +1,25 @@ /** vim: et:ts=4:sw=4:sts=4 - * @license RequireJS 2.0.1 Copyright (c) 2010-2012, The Dojo Foundation All Rights Reserved. + * @license RequireJS 2.1.1 Copyright (c) 2010-2012, The Dojo Foundation All Rights Reserved. * Available via the MIT or new BSD license. * see: http://github.com/jrburke/requirejs for details */ -/*jslint regexp: true, nomen: true */ +//Not using strict: uneven strict support in browsers, #392, and causes +//problems with requirejs.exec()/transpiler plugins that may not be strict. +/*jslint regexp: true, nomen: true, sloppy: true */ /*global window, navigator, document, importScripts, jQuery, setTimeout, opera */ var requirejs, require, define; (function (global) { - 'use strict'; - - var version = '2.0.1', + var req, s, head, baseElement, dataMain, src, + interactiveScript, currentlyAddingScript, mainScript, subPath, + version = '2.1.1', commentRegExp = /(\/\*([\s\S]*?)\*\/|([^:]|^)\/\/(.*)$)/mg, - cjsRequireRegExp = /require\s*\(\s*["']([^'"\s]+)["']\s*\)/g, + cjsRequireRegExp = /[^.]\s*require\s*\(\s*["']([^'"\s]+)["']\s*\)/g, jsSuffixRegExp = /\.js$/, currDirRegExp = /^\.\//, - ostring = Object.prototype.toString, + op = Object.prototype, + ostring = op.toString, + hasOwn = op.hasOwnProperty, ap = Array.prototype, aps = ap.slice, apsp = ap.splice, @@ -33,9 +37,7 @@ var requirejs, require, define; contexts = {}, cfg = {}, globalDefQueue = [], - useInteractive = false, - req, s, head, baseElement, dataMain, src, - interactiveScript, currentlyAddingScript, mainScript, subPath; + useInteractive = false; function isFunction(it) { return ostring.call(it) === '[object Function]'; @@ -53,7 +55,7 @@ var requirejs, require, define; if (ary) { var i; for (i = 0; i < ary.length; i += 1) { - if (func(ary[i], i, ary)) { + if (ary[i] && func(ary[i], i, ary)) { break; } } @@ -68,7 +70,7 @@ var requirejs, require, define; if (ary) { var i; for (i = ary.length - 1; i > -1; i -= 1) { - if (func(ary[i], i, ary)) { + if (ary[i] && func(ary[i], i, ary)) { break; } } @@ -76,7 +78,7 @@ var requirejs, require, define; } function hasProp(obj, prop) { - return obj.hasOwnProperty(prop); + return hasOwn.call(obj, prop); } /** @@ -98,18 +100,23 @@ var requirejs, require, define; /** * Simple function to mix in properties from source into target, * but only if target does not already have a property of the same name. - * This is not robust in IE for transferring methods that match - * Object.prototype names, but the uses of mixin here seem unlikely to - * trigger a problem related to that. */ - function mixin(target, source, force) { + function mixin(target, source, force, deepStringMixin) { if (source) { eachProp(source, function (value, prop) { if (force || !hasProp(target, prop)) { - target[prop] = value; + if (deepStringMixin && typeof value !== 'string') { + if (!target[prop]) { + target[prop] = {}; + } + mixin(target[prop], value, force, deepStringMixin); + } else { + target[prop] = value; + } } }); } + return target; } //Similar to Function.prototype.bind, but the 'this' object is specified @@ -137,32 +144,6 @@ var requirejs, require, define; return g; } - function makeContextModuleFunc(func, relMap, enableBuildCallback) { - return function () { - //A version of a require function that passes a moduleName - //value for items that may need to - //look up paths relative to the moduleName - var args = aps.call(arguments, 0), lastArg; - if (enableBuildCallback && - isFunction((lastArg = args[args.length - 1]))) { - lastArg.__requireJsBuild = true; - } - args.push(relMap); - return func.apply(null, args); - }; - } - - function addRequireMethods(req, context, relMap) { - each([ - ['toUrl'], - ['undef'], - ['defined', 'requireDefined'], - ['specified', 'requireSpecified'] - ], function (item) { - req[item[0]] = makeContextModuleFunc(context[item[1] || item[0]], relMap); - }); - } - /** * Constructs an error with a pointer to an URL with more information. * @param {String} id the error ID that maps to an ID on a web page. @@ -204,28 +185,24 @@ var requirejs, require, define; } function newContext(contextName) { - var config = { + var inCheckLoaded, Module, context, handlers, + checkLoadedTimeoutId, + config = { waitSeconds: 7, baseUrl: './', paths: {}, pkgs: {}, - shim: {} + shim: {}, + map: {}, + config: {} }, registry = {}, undefEvents = {}, defQueue = [], defined = {}, - urlMap = {}, urlFetched = {}, requireCounter = 1, - unnormalizedCounter = 1, - //Used to track the order in which modules - //should be executed, by the order they - //load. Important for consistent cycle resolution - //behavior. - waitAry = [], - inCheckLoaded, Module, context, handlers, - checkLoadedTimeoutId; + unnormalizedCounter = 1; /** * Trims the . and .. from an array of path segments. @@ -238,7 +215,7 @@ var requirejs, require, define; */ function trimDots(ary) { var i, part; - for (i = 0; ary[i]; i+= 1) { + for (i = 0; ary[i]; i += 1) { part = ary[i]; if (part === '.') { ary.splice(i, 1); @@ -271,11 +248,12 @@ var requirejs, require, define; * @returns {String} normalized name */ function normalize(name, baseName, applyMap) { - var baseParts = baseName && baseName.split('/'), + var pkgName, pkgConfig, mapValue, nameParts, i, j, nameSegment, + foundMap, foundI, foundStarMap, starI, + baseParts = baseName && baseName.split('/'), + normalizedBaseParts = baseParts, map = config.map, - starMap = map && map['*'], - pkgName, pkgConfig, mapValue, nameParts, i, j, nameSegment, - foundMap; + starMap = map && map['*']; //Adjust any relative paths. if (name && name.charAt(0) === '.') { @@ -286,17 +264,17 @@ var requirejs, require, define; if (config.pkgs[baseName]) { //If the baseName is a package name, then just treat it as one //name to concat the name with. - baseParts = [baseName]; + normalizedBaseParts = baseParts = [baseName]; } else { //Convert baseName to array, and lop off the last part, //so that . matches that 'directory' and not name of the baseName's //module. For instance, baseName of 'one/two/three', maps to //'one/two/three.js', but we want the directory, 'one/two' for //this normalization. - baseParts = baseParts.slice(0, baseParts.length - 1); + normalizedBaseParts = baseParts.slice(0, baseParts.length - 1); } - name = baseParts.concat(name.split('/')); + name = normalizedBaseParts.concat(name.split('/')); trimDots(name); //Some use of packages may use a . path to reference the @@ -326,28 +304,41 @@ var requirejs, require, define; for (j = baseParts.length; j > 0; j -= 1) { mapValue = map[baseParts.slice(0, j).join('/')]; - //baseName segment has config, find if it has one for + //baseName segment has config, find if it has one for //this name. if (mapValue) { mapValue = mapValue[nameSegment]; if (mapValue) { //Match, update name to the new value. foundMap = mapValue; + foundI = i; break; } } } } - if (!foundMap && starMap && starMap[nameSegment]) { - foundMap = starMap[nameSegment]; - } - if (foundMap) { - nameParts.splice(0, i, foundMap); - name = nameParts.join('/'); break; } + + //Check for a star map match, but just hold on to it, + //if there is a shorter segment match later in a matching + //config, then favor over this star map. + if (!foundStarMap && starMap && starMap[nameSegment]) { + foundStarMap = starMap[nameSegment]; + starI = i; + } + } + + if (!foundMap && foundStarMap) { + foundMap = foundStarMap; + foundI = starI; + } + + if (foundMap) { + nameParts.splice(0, foundI, foundMap); + name = nameParts.join('/'); } } @@ -358,7 +349,7 @@ var requirejs, require, define; if (isBrowser) { each(scripts(), function (scriptNode) { if (scriptNode.getAttribute('data-requiremodule') === name && - scriptNode.getAttribute('data-requirecontext') === context.contextName) { + scriptNode.getAttribute('data-requirecontext') === context.contextName) { scriptNode.parentNode.removeChild(scriptNode); return true; } @@ -373,12 +364,25 @@ var requirejs, require, define; //Pop off the first array value, since it failed, and //retry pathConfig.shift(); - context.undef(id); + context.require.undef(id); context.require([id]); return true; } } + //Turns a plugin!resource to [plugin, resource] + //with the plugin being undefined if the name + //did not have a plugin prefix. + function splitPrefix(name) { + var prefix, + index = name ? name.indexOf('!') : -1; + if (index > -1) { + prefix = name.substring(0, index); + name = name.substring(index + 1, name.length); + } + return [prefix, name]; + } + /** * Creates a module mapping that includes plugin prefix, module * name, and path. If parentModuleMap is provided it will @@ -395,13 +399,12 @@ var requirejs, require, define; * @returns {Object} */ function makeModuleMap(name, parentModuleMap, isNormalized, applyMap) { - var index = name ? name.indexOf('!') : -1, + var url, pluginModule, suffix, nameParts, prefix = null, parentName = parentModuleMap ? parentModuleMap.name : null, originalName = name, isDefine = true, - normalizedName = '', - url, pluginModule, suffix; + normalizedName = ''; //If no name, then it means it is a require call, generate an //internal name. @@ -410,10 +413,9 @@ var requirejs, require, define; name = '_@r' + (requireCounter += 1); } - if (index !== -1) { - prefix = name.substring(0, index); - name = name.substring(index + 1, name.length); - } + nameParts = splitPrefix(name); + prefix = nameParts[0]; + name = nameParts[1]; if (prefix) { prefix = normalize(prefix, parentName, applyMap); @@ -435,22 +437,15 @@ var requirejs, require, define; //A regular module. normalizedName = normalize(name, parentName, applyMap); - url = urlMap[normalizedName]; - if (!url) { - //Calculate url for the module, if it has a name. - //Use name here since nameToUrl also calls normalize, - //and for relative names that are outside the baseUrl - //this causes havoc. Was thinking of just removing - //parentModuleMap to avoid extra normalization, but - //normalize() still does a dot removal because of - //issue #142, so just pass in name here and redo - //the normalization. Paths outside baseUrl are just - //messy to support. - url = context.nameToUrl(name, null, parentModuleMap); + //Normalized name may be a plugin ID due to map config + //application in normalize. The map config values must + //already be normalized, so do not need to redo that part. + nameParts = splitPrefix(normalizedName); + prefix = nameParts[0]; + normalizedName = nameParts[1]; + isNormalized = true; - //Store the URL mapping for later. - urlMap[normalizedName] = url; - } + url = context.nameToUrl(normalizedName); } } @@ -470,8 +465,8 @@ var requirejs, require, define; originalName: originalName, isDefine: isDefine, id: (prefix ? - prefix + '!' + normalizedName : - normalizedName) + suffix + prefix + '!' + normalizedName : + normalizedName) + suffix }; } @@ -491,7 +486,7 @@ var requirejs, require, define; mod = registry[id]; if (hasProp(defined, id) && - (!mod || mod.defineEmitComplete)) { + (!mod || mod.defineEmitComplete)) { if (name === 'defined') { fn(defined[id]); } @@ -541,163 +536,82 @@ var requirejs, require, define; } } - /** - * Helper function that creates a require function object to give to - * modules that ask for it as a dependency. It needs to be specific - * per module because of the implication of path mappings that may - * need to be relative to the module name. - */ - function makeRequire(mod, enableBuildCallback, altRequire) { - var relMap = mod && mod.map, - modRequire = makeContextModuleFunc(altRequire || context.require, - relMap, - enableBuildCallback); - - addRequireMethods(modRequire, context, relMap); - modRequire.isBrowser = isBrowser; - - return modRequire; - } - handlers = { 'require': function (mod) { - return makeRequire(mod); + if (mod.require) { + return mod.require; + } else { + return (mod.require = context.makeRequire(mod.map)); + } }, 'exports': function (mod) { mod.usingExports = true; if (mod.map.isDefine) { - return (mod.exports = defined[mod.map.id] = {}); + if (mod.exports) { + return mod.exports; + } else { + return (mod.exports = defined[mod.map.id] = {}); + } } }, 'module': function (mod) { - return (mod.module = { - id: mod.map.id, - uri: mod.map.url, - config: function () { - return (config.config && config.config[mod.map.id]) || {}; - }, - exports: defined[mod.map.id] - }); + if (mod.module) { + return mod.module; + } else { + return (mod.module = { + id: mod.map.id, + uri: mod.map.url, + config: function () { + return (config.config && config.config[mod.map.id]) || {}; + }, + exports: defined[mod.map.id] + }); + } } }; - function removeWaiting(id) { + function cleanRegistry(id) { //Clean up machinery used for waiting modules. delete registry[id]; - - each(waitAry, function (mod, i) { - if (mod.map.id === id) { - waitAry.splice(i, 1); - if (!mod.defined) { - context.waitCount -= 1; - } - return true; - } - }); } - function findCycle(mod, traced) { - var id = mod.map.id, - depArray = mod.depMaps, - foundModule; + function breakCycle(mod, traced, processed) { + var id = mod.map.id; - //Do not bother with unitialized modules or not yet enabled - //modules. - if (!mod.inited) { - return; - } + if (mod.error) { + mod.emit('error', mod.error); + } else { + traced[id] = true; + each(mod.depMaps, function (depMap, i) { + var depId = depMap.id, + dep = registry[depId]; - //Found the cycle. - if (traced[id]) { - return mod; - } - - traced[id] = true; - - //Trace through the dependencies. - each(depArray, function (depMap) { - var depId = depMap.id, - depMod = registry[depId]; - - if (!depMod) { - return; - } - - if (!depMod.inited || !depMod.enabled) { - //Dependency is not inited, so this cannot - //be used to determine a cycle. - foundModule = null; - delete traced[id]; - return true; - } - - return (foundModule = findCycle(depMod, traced)); - }); - - return foundModule; - } - - function forceExec(mod, traced, uninited) { - var id = mod.map.id, - depArray = mod.depMaps; - - if (!mod.inited || !mod.map.isDefine) { - return; - } - - if (traced[id]) { - return defined[id]; - } - - traced[id] = mod; - - each(depArray, function(depMap) { - var depId = depMap.id, - depMod = registry[depId], - value; - - if (handlers[depId]) { - return; - } - - if (depMod) { - if (!depMod.inited || !depMod.enabled) { - //Dependency is not inited, - //so this module cannot be - //given a forced value yet. - uninited[id] = true; - return; + //Only force things that have not completed + //being defined, so still in the registry, + //and only if it has not been matched up + //in the module already. + if (dep && !mod.depMatched[i] && !processed[depId]) { + if (traced[depId]) { + mod.defineDep(i, defined[depId]); + mod.check(); //pass false? + } else { + breakCycle(dep, traced, processed); + } } - - //Get the value for the current dependency - value = forceExec(depMod, traced, uninited); - - //Even with forcing it may not be done, - //in particular if the module is waiting - //on a plugin resource. - if (!uninited[depId]) { - mod.defineDepById(depId, value); - } - } - }); - - mod.check(true); - - return defined[id]; - } - - function modCheck(mod) { - mod.check(); + }); + processed[id] = true; + } } function checkLoaded() { - var waitInterval = config.waitSeconds * 1000, + var map, modId, err, usingPathFallback, + waitInterval = config.waitSeconds * 1000, //It is possible to disable the wait interval by using waitSeconds of 0. expired = waitInterval && (context.startTime + waitInterval) < new Date().getTime(), noLoads = [], + reqCalls = [], stillLoading = false, - needCycleCheck = true, - map, modId, err, usingPathFallback; + needCycleCheck = true; //Do not bother if this call was a result of a cycle break. if (inCheckLoaded) { @@ -716,6 +630,10 @@ var requirejs, require, define; return; } + if (!map.isDefine) { + reqCalls.push(mod); + } + if (!mod.error) { //If the module should be executed, and it has not //been inited and time is up, remember it. @@ -750,31 +668,9 @@ var requirejs, require, define; //Not expired, check for a cycle. if (needCycleCheck) { - - each(waitAry, function (mod) { - if (mod.defined) { - return; - } - - var cycleMod = findCycle(mod, {}), - traced = {}; - - if (cycleMod) { - forceExec(cycleMod, traced, {}); - - //traced modules may have been - //removed from the registry, but - //their listeners still need to - //be called. - eachProp(traced, modCheck); - } + each(reqCalls, function (mod) { + breakCycle(mod, {}, {}); }); - - //Now that dependencies have - //been satisfied, trigger the - //completion check that then - //notifies listeners. - eachProp(registry, modCheck); } //If still waiting on loads, and the waiting load is something @@ -811,7 +707,7 @@ var requirejs, require, define; }; Module.prototype = { - init: function(depMaps, factory, errback, options) { + init: function (depMaps, factory, errback, options) { options = options || {}; //Do not do more inits if already done. Can happen if there @@ -834,33 +730,14 @@ var requirejs, require, define; }); } - each(depMaps, bind(this, function (depMap, i) { - if (typeof depMap === 'string') { - depMap = makeModuleMap(depMap, - (this.map.isDefine ? this.map : this.map.parentMap), - false, - true); - this.depMaps.push(depMap); - } + //Do a copy of the dependency array, so that + //source inputs are not modified. For example + //"shim" deps are passed in here directly, and + //doing a direct modification of the depMaps array + //would affect that config. + this.depMaps = depMaps && depMaps.slice(0); - var handler = handlers[depMap.id]; - - if (handler) { - this.depExports[i] = handler(this); - return; - } - - this.depCount += 1; - - on(depMap, 'defined', bind(this, function (depExports) { - this.defineDep(i, depExports); - this.check(); - })); - - if (errback) { - on(depMap, 'error', errback); - } - })); + this.errback = errback; //Indicate this module has be initialized this.inited = true; @@ -880,20 +757,6 @@ var requirejs, require, define; } }, - defineDepById: function (id, depExports) { - var i; - - //Find the index for this dependency. - each(this.depMaps, function (map, index) { - if (map.id === id) { - i = index; - return true; - } - }); - - return this.defineDep(i, depExports); - }, - defineDep: function (i, depExports) { //Because of cycles, defined callback for a given //export can be called more than once. @@ -916,19 +779,19 @@ var requirejs, require, define; //If the manager is for a plugin managed resource, //ask the plugin to load it now. - if (map.prefix) { - this.callPlugin(); - } else if (this.shim) { - makeRequire(this, true)(this.shim.deps || [], bind(this, function () { - this.load(); + if (this.shim) { + context.makeRequire(this.map, { + enableBuildCallback: true + })(this.shim.deps || [], bind(this, function () { + return map.prefix ? this.callPlugin() : this.load(); })); } else { //Regular dependency. - this.load(); + return map.prefix ? this.callPlugin() : this.load(); } }, - load: function() { + load: function () { var url = this.map.url; //Regular dependency. @@ -940,20 +803,18 @@ var requirejs, require, define; /** * Checks is the module is ready to define itself, and if so, - * define it. If the silent argument is true, then it will just - * define, but not notify listeners, and not ask for a context-wide - * check of all loaded modules. That is useful for cycle breaking. + * define it. */ - check: function (silent) { - if (!this.enabled) { + check: function () { + if (!this.enabled || this.enabling) { return; } - var id = this.map.id, + var err, cjsModule, + id = this.map.id, depExports = this.depExports, exports = this.exports, - factory = this.factory, - err, cjsModule; + factory = this.factory; if (!this.inited) { this.fetch(); @@ -986,9 +847,9 @@ var requirejs, require, define; //favor a non-undefined return value over exports use. cjsModule = this.module; if (cjsModule && - cjsModule.exports !== undefined && - //Make sure it is not already the exports value - cjsModule.exports !== this.exports) { + cjsModule.exports !== undefined && + //Make sure it is not already the exports value + cjsModule.exports !== this.exports) { exports = cjsModule.exports; } else if (exports === undefined && this.usingExports) { //exports already set the defined value. @@ -1022,11 +883,6 @@ var requirejs, require, define; delete registry[id]; this.defined = true; - context.waitCount -= 1; - if (context.waitCount === 0) { - //Clear the wait array used for cycles. - waitAry = []; - } } //Finished the define stage. Allow calling check again @@ -1034,25 +890,33 @@ var requirejs, require, define; //cycle. this.defining = false; - if (!silent) { - if (this.defined && !this.defineEmitted) { - this.defineEmitted = true; - this.emit('defined', this.exports); - this.defineEmitComplete = true; - } + if (this.defined && !this.defineEmitted) { + this.defineEmitted = true; + this.emit('defined', this.exports); + this.defineEmitComplete = true; } + } }, - callPlugin: function() { + callPlugin: function () { var map = this.map, id = map.id, - pluginMap = makeModuleMap(map.prefix, null, false, true); + //Map already normalized the prefix. + pluginMap = makeModuleMap(map.prefix); + + //Mark this as a dependency for this plugin, so it + //can be traced for cycles. + this.depMaps.push(pluginMap); on(pluginMap, 'defined', bind(this, function (plugin) { - var name = this.map.name, + var load, normalizedMap, normalizedMod, + name = this.map.name, parentName = this.map.parentMap ? this.map.parentMap.name : null, - load, normalizedMap, normalizedMod; + localRequire = context.makeRequire(map.parentMap, { + enableBuildCallback: true, + skipMap: true + }); //If current map is not normalized, wait for that //normalized name to load instead of continuing. @@ -1064,16 +928,24 @@ var requirejs, require, define; }) || ''; } - normalizedMap = makeModuleMap(map.prefix + '!' + name); + //prefix and name should already be normalized, no need + //for applying map config again either. + normalizedMap = makeModuleMap(map.prefix + '!' + name, + this.map.parentMap); on(normalizedMap, - 'defined', bind(this, function (value) { - this.init([], function () { return value; }, null, { - enabled: true, - ignore: true - }); - })); + 'defined', bind(this, function (value) { + this.init([], function () { return value; }, null, { + enabled: true, + ignore: true + }); + })); + normalizedMod = registry[normalizedMap.id]; if (normalizedMod) { + //Mark this as a dependency for this plugin, so it + //can be traced for cycles. + this.depMaps.push(normalizedMap); + if (this.events.error) { normalizedMod.on('error', bind(this, function (err) { this.emit('error', err); @@ -1100,7 +972,7 @@ var requirejs, require, define; //since they will never be resolved otherwise now. eachProp(registry, function (mod) { if (mod.map.id.indexOf(id + '_unnormalized') === 0) { - removeWaiting(mod.map.id); + cleanRegistry(mod.map.id); } }); @@ -1109,9 +981,19 @@ var requirejs, require, define; //Allow plugins to load other code without having to know the //context or how to 'complete' the load. - load.fromText = function (moduleName, text) { + load.fromText = bind(this, function (text, textAlt) { /*jslint evil: true */ - var hasInteractive = useInteractive; + var moduleName = map.name, + moduleMap = makeModuleMap(moduleName), + hasInteractive = useInteractive; + + //As of 2.1.0, support just passing the text, to reinforce + //fromText only being called once per resource. Still + //support old style of passing moduleName but discard + //that moduleName in favor of the internal ref. + if (textAlt) { + text = textAlt; + } //Turn off interactive script matching for IE for any define //calls in the text, then turn it back on at the end. @@ -1119,22 +1001,37 @@ var requirejs, require, define; useInteractive = false; } - req.exec(text); + //Prime the system by creating a module instance for + //it. + getModule(moduleMap); + + try { + req.exec(text); + } catch (e) { + throw new Error('fromText eval for ' + moduleName + + ' failed: ' + e); + } if (hasInteractive) { useInteractive = true; } + //Mark this as a dependency for the plugin + //resource + this.depMaps.push(moduleMap); + //Support anonymous modules. context.completeLoad(moduleName); - }; + + //Bind the value of that module to the value for this + //resource ID. + localRequire([moduleName], load); + }); //Use parentName here since the plugin's name is not reliable, //could be some weird string with no path that actually wants to //reference the parentName's path. - plugin.load(map.name, makeRequire(map.parentMap, true, function (deps, cb) { - return context.require(deps, cb); - }), load, config); + plugin.load(map.name, localRequire, load, config); })); context.enable(pluginMap, this); @@ -1144,21 +1041,52 @@ var requirejs, require, define; enable: function () { this.enabled = true; - if (!this.waitPushed) { - waitAry.push(this); - context.waitCount += 1; - this.waitPushed = true; - } + //Set flag mentioning that the module is enabling, + //so that immediate calls to the defined callbacks + //for dependencies do not trigger inadvertent load + //with the depCount still being zero. + this.enabling = true; //Enable each dependency - each(this.depMaps, bind(this, function (map) { - var id = map.id, - mod = registry[id]; + each(this.depMaps, bind(this, function (depMap, i) { + var id, mod, handler; + + if (typeof depMap === 'string') { + //Dependency needs to be converted to a depMap + //and wired up to this module. + depMap = makeModuleMap(depMap, + (this.map.isDefine ? this.map : this.map.parentMap), + false, + !this.skipMap); + this.depMaps[i] = depMap; + + handler = handlers[depMap.id]; + + if (handler) { + this.depExports[i] = handler(this); + return; + } + + this.depCount += 1; + + on(depMap, 'defined', bind(this, function (depExports) { + this.defineDep(i, depExports); + this.check(); + })); + + if (this.errback) { + on(depMap, 'error', this.errback); + } + } + + id = depMap.id; + mod = registry[id]; + //Skip special modules like 'require', 'exports', 'module' //Also, don't call enable if it is already enabled, //important in circular dependency cases. if (!handlers[id] && mod && !mod.enabled) { - context.enable(map, this); + context.enable(depMap, this); } })); @@ -1171,10 +1099,12 @@ var requirejs, require, define; } })); + this.enabling = false; + this.check(); }, - on: function(name, cb) { + on: function (name, cb) { var cbs = this.events[name]; if (!cbs) { cbs = this.events[name] = []; @@ -1189,7 +1119,7 @@ var requirejs, require, define; if (name === 'error') { //Now that the error handler was triggered, remove //the listeners, since this broken Module instance - //can stay around for a while in the registry/waitAry. + //can stay around for a while in the registry. delete this.events[name]; } } @@ -1236,17 +1166,35 @@ var requirejs, require, define; }; } - return (context = { + function intakeDefines() { + var args; + + //Any defined modules in the global queue, intake them now. + takeGlobalQueue(); + + //Make sure any remaining defQueue items get properly processed. + while (defQueue.length) { + args = defQueue.shift(); + if (args[0] === null) { + return onError(makeError('mismatch', 'Mismatched anonymous define() module: ' + args[args.length - 1])); + } else { + //args are id, deps, factory. Should be normalized by the + //define() function. + callGetModule(args); + } + } + } + + context = { config: config, contextName: contextName, registry: registry, defined: defined, - urlMap: urlMap, urlFetched: urlFetched, - waitCount: 0, defQueue: defQueue, Module: Module, makeModuleMap: makeModuleMap, + nextTick: req.nextTick, /** * Set a configuration for the context. @@ -1262,24 +1210,25 @@ var requirejs, require, define; //Save off the paths and packages since they require special processing, //they are additive. - var paths = config.paths, - pkgs = config.pkgs, + var pkgs = config.pkgs, shim = config.shim, - map = config.map || {}; + objs = { + paths: true, + config: true, + map: true + }; - //Mix in the config values, favoring the new values over - //existing ones in context.config. - mixin(config, cfg, true); - - //Merge paths. - mixin(paths, cfg.paths, true); - config.paths = paths; - - //Merge map - if (cfg.map) { - mixin(map, cfg.map, true); - config.map = map; - } + eachProp(cfg, function (value, prop) { + if (objs[prop]) { + if (prop === 'map') { + mixin(config[prop], value, true, true); + } else { + mixin(config[prop], value, true); + } + } else { + config[prop] = value; + } + }); //Merge shim if (cfg.shim) { @@ -1290,8 +1239,8 @@ var requirejs, require, define; deps: value }; } - if (value.exports && !value.exports.__buildReady) { - value.exports = context.makeShimExports(value.exports); + if (value.exports && !value.exportsFn) { + value.exportsFn = context.makeShimExports(value); } shim[id] = value; }); @@ -1326,6 +1275,18 @@ var requirejs, require, define; config.pkgs = pkgs; } + //If there are any "waiting to execute" modules in the registry, + //update the maps for them, since their info, like URLs to load, + //may have changed. + eachProp(registry, function (mod, id) { + //If module already has init called, since it is too + //late to modify them, and ignore unnormalized ones + //since they are transient. + if (!mod.inited && !mod.map.unnormalized) { + mod.map = makeModuleMap(id); + } + }); + //If a deps array or a config callback is specified, then call //require with those args. This is useful when require is defined as a //config object before require.js is loaded. @@ -1334,122 +1295,144 @@ var requirejs, require, define; } }, - makeShimExports: function (exports) { - var func; - if (typeof exports === 'string') { - func = function () { - return getGlobal(exports); - }; - //Save the exports for use in nodefine checking. - func.exports = exports; - return func; - } else { - return function () { - return exports.apply(global, arguments); - }; + makeShimExports: function (value) { + function fn() { + var ret; + if (value.init) { + ret = value.init.apply(global, arguments); + } + return ret || getGlobal(value.exports); } + return fn; }, - requireDefined: function (id, relMap) { - return hasProp(defined, makeModuleMap(id, relMap, false, true).id); - }, + makeRequire: function (relMap, options) { + options = options || {}; - requireSpecified: function (id, relMap) { - id = makeModuleMap(id, relMap, false, true).id; - return hasProp(defined, id) || hasProp(registry, id); - }, + function localRequire(deps, callback, errback) { + var id, map, requireMod; - require: function (deps, callback, errback, relMap) { - var moduleName, id, map, requireMod, args; - if (typeof deps === 'string') { - if (isFunction(callback)) { - //Invalid call - return onError(makeError('requireargs', 'Invalid require call'), errback); + if (options.enableBuildCallback && callback && isFunction(callback)) { + callback.__requireJsBuild = true; } - //Synchronous access to one module. If require.get is - //available (as in the Node adapter), prefer that. - //In this case deps is the moduleName and callback is - //the relMap - if (req.get) { - return req.get(context, deps, callback); + if (typeof deps === 'string') { + if (isFunction(callback)) { + //Invalid call + return onError(makeError('requireargs', 'Invalid require call'), errback); + } + + //If require|exports|module are requested, get the + //value for them from the special handlers. Caveat: + //this only works while module is being defined. + if (relMap && handlers[deps]) { + return handlers[deps](registry[relMap.id]); + } + + //Synchronous access to one module. If require.get is + //available (as in the Node adapter), prefer that. + if (req.get) { + return req.get(context, deps, relMap); + } + + //Normalize module name, if it contains . or .. + map = makeModuleMap(deps, relMap, false, true); + id = map.id; + + if (!hasProp(defined, id)) { + return onError(makeError('notloaded', 'Module name "' + + id + + '" has not been loaded yet for context: ' + + contextName + + (relMap ? '' : '. Use require([])'))); + } + return defined[id]; } - //Just return the module wanted. In this scenario, the - //second arg (if passed) is just the relMap. - moduleName = deps; - relMap = callback; + //Grab defines waiting in the global queue. + intakeDefines(); - //Normalize module name, if it contains . or .. - map = makeModuleMap(moduleName, relMap, false, true); - id = map.id; + //Mark all the dependencies as needing to be loaded. + context.nextTick(function () { + //Some defines could have been added since the + //require call, collect them. + intakeDefines(); - if (!hasProp(defined, id)) { - return onError(makeError('notloaded', 'Module name "' + - id + - '" has not been loaded yet for context: ' + - contextName)); + requireMod = getModule(makeModuleMap(null, relMap)); + + //Store if map config should be applied to this require + //call for dependencies. + requireMod.skipMap = options.skipMap; + + requireMod.init(deps, callback, errback, { + enabled: true + }); + + checkLoaded(); + }); + + return localRequire; + } + + mixin(localRequire, { + isBrowser: isBrowser, + + /** + * Converts a module name + .extension into an URL path. + * *Requires* the use of a module name. It does not support using + * plain URLs like nameToUrl. + */ + toUrl: function (moduleNamePlusExt) { + var index = moduleNamePlusExt.lastIndexOf('.'), + ext = null; + + if (index !== -1) { + ext = moduleNamePlusExt.substring(index, moduleNamePlusExt.length); + moduleNamePlusExt = moduleNamePlusExt.substring(0, index); + } + + return context.nameToUrl(normalize(moduleNamePlusExt, + relMap && relMap.id, true), ext); + }, + + defined: function (id) { + return hasProp(defined, makeModuleMap(id, relMap, false, true).id); + }, + + specified: function (id) { + id = makeModuleMap(id, relMap, false, true).id; + return hasProp(defined, id) || hasProp(registry, id); } - return defined[id]; - } - - //Callback require. Normalize args. if callback or errback is - //not a function, it means it is a relMap. Test errback first. - if (errback && !isFunction(errback)) { - relMap = errback; - errback = undefined; - } - if (callback && !isFunction(callback)) { - relMap = callback; - callback = undefined; - } - - //Any defined modules in the global queue, intake them now. - takeGlobalQueue(); - - //Make sure any remaining defQueue items get properly processed. - while (defQueue.length) { - args = defQueue.shift(); - if (args[0] === null) { - return onError(makeError('mismatch', 'Mismatched anonymous define() module: ' + args[args.length - 1])); - } else { - //args are id, deps, factory. Should be normalized by the - //define() function. - callGetModule(args); - } - } - - //Mark all the dependencies as needing to be loaded. - requireMod = getModule(makeModuleMap(null, relMap)); - - requireMod.init(deps, callback, errback, { - enabled: true }); - checkLoaded(); + //Only allow undef on top level require calls + if (!relMap) { + localRequire.undef = function (id) { + //Bind any waiting define() calls to this context, + //fix for #408 + takeGlobalQueue(); - return context.require; - }, + var map = makeModuleMap(id, relMap, true), + mod = registry[id]; - undef: function (id) { - var map = makeModuleMap(id, null, true), - mod = registry[id]; + delete defined[id]; + delete urlFetched[map.url]; + delete undefEvents[id]; - delete defined[id]; - delete urlMap[id]; - delete urlFetched[map.url]; - delete undefEvents[id]; + if (mod) { + //Hold on to listeners in case the + //module will be attempted to be reloaded + //using a different config. + if (mod.events.defined) { + undefEvents[id] = mod.events; + } - if (mod) { - //Hold on to listeners in case the - //module will be attempted to be reloaded - //using a different config. - if (mod.events.defined) { - undefEvents[id] = mod.events; - } - - removeWaiting(id); + cleanRegistry(id); + } + }; } + + return localRequire; }, /** @@ -1471,9 +1454,9 @@ var requirejs, require, define; * @param {String} moduleName the name of the module to potentially complete. */ completeLoad: function (moduleName) { - var shim = config.shim[moduleName] || {}, - shExports = shim.exports && shim.exports.exports, - found, args, mod; + var found, args, mod, + shim = config.shim[moduleName] || {}, + shExports = shim.exports; takeGlobalQueue(); @@ -1500,9 +1483,7 @@ var requirejs, require, define; //of those calls/init calls changes the registry. mod = registry[moduleName]; - if (!found && - !defined[moduleName] && - mod && !mod.inited) { + if (!found && !defined[moduleName] && mod && !mod.inited) { if (config.enforceDefine && (!shExports || !getGlobal(shExports))) { if (hasPathFallback(moduleName)) { return; @@ -1515,41 +1496,24 @@ var requirejs, require, define; } else { //A script that does not call define(), so just simulate //the call for it. - callGetModule([moduleName, (shim.deps || []), shim.exports]); + callGetModule([moduleName, (shim.deps || []), shim.exportsFn]); } } checkLoaded(); }, - /** - * Converts a module name + .extension into an URL path. - * *Requires* the use of a module name. It does not support using - * plain URLs like nameToUrl. - */ - toUrl: function (moduleNamePlusExt, relModuleMap) { - var index = moduleNamePlusExt.lastIndexOf('.'), - ext = null; - - if (index !== -1) { - ext = moduleNamePlusExt.substring(index, moduleNamePlusExt.length); - moduleNamePlusExt = moduleNamePlusExt.substring(0, index); - } - - return context.nameToUrl(moduleNamePlusExt, ext, relModuleMap); - }, - /** * Converts a module name to a file path. Supports cases where * moduleName may actually be just an URL. + * Note that it **does not** call normalize on the moduleName, + * it is assumed to have already been normalized. This is an + * internal API, not a public one. Use toUrl for the public API. */ - nameToUrl: function (moduleName, ext, relModuleMap) { + nameToUrl: function (moduleName, ext) { var paths, pkgs, pkg, pkgPath, syms, i, parentModule, url, parentPath; - //Normalize module name if have a base relative module name to work from. - moduleName = normalize(moduleName, relModuleMap && relModuleMap.id, true); - //If a colon is in the URL, it indicates a protocol is used and it is just //an URL to a file, or if it starts with a slash, contains a query arg (i.e. ?) //or ends with .js, then assume the user meant to use an url and not a module id. @@ -1594,7 +1558,8 @@ var requirejs, require, define; } //Join the path parts together, then figure out if baseUrl is needed. - url = syms.join('/') + (ext || '.js'); + url = syms.join('/'); + url += (ext || (/\?/.test(url) ? '' : '.js')); url = (url.charAt(0) === '/' || url.match(/^[\w\+\.\-]+:/) ? '' : config.baseUrl) + url; } @@ -1631,7 +1596,7 @@ var requirejs, require, define; //all old browsers will be supported, but this one was easy enough //to support and still makes sense. if (evt.type === 'load' || - (readyRegExp.test((evt.currentTarget || evt.srcElement).readyState))) { + (readyRegExp.test((evt.currentTarget || evt.srcElement).readyState))) { //Reset interactive script so a script node is not held onto for //to long. interactiveScript = null; @@ -1651,7 +1616,10 @@ var requirejs, require, define; return onError(makeError('scripterror', 'Script error', evt, [data.id])); } } - }); + }; + + context.require = context.makeRequire(); + return context; } /** @@ -1671,8 +1639,8 @@ var requirejs, require, define; req = requirejs = function (deps, callback, errback, optional) { //Find the right context, use default - var contextName = defContextName, - context, config; + var context, config, + contextName = defContextName; // Determine if have config object in the call. if (!isArray(deps) && typeof deps !== 'string') { @@ -1712,6 +1680,16 @@ var requirejs, require, define; return req(config); }; + /** + * Execute something after the current tick + * of the event loop. Override for other envs + * that have a better solution than setTimeout. + * @param {Function} fn function to execute later. + */ + req.nextTick = typeof setTimeout !== 'undefined' ? function (fn) { + setTimeout(fn, 4); + } : function (fn) { fn(); }; + /** * Export require as a global, but only if it does not already exist. */ @@ -1732,9 +1710,21 @@ var requirejs, require, define; //Create default context. req({}); - //Exports some context-sensitive methods on global require, using - //default context if no context specified. - addRequireMethods(req, contexts[defContextName]); + //Exports some context-sensitive methods on global require. + each([ + 'toUrl', + 'undef', + 'defined', + 'specified' + ], function (prop) { + //Reference from contexts instead of early binding to default context, + //so that during builds, the latest instance of the default context + //with its config gets used. + req[prop] = function () { + var ctx = contexts[defContextName]; + return ctx.require[prop].apply(ctx, arguments); + }; + }); if (isBrowser) { head = s.head = document.getElementsByTagName('head')[0]; @@ -1771,10 +1761,11 @@ var requirejs, require, define; if (isBrowser) { //In the browser so use a script tag node = config.xhtml ? - document.createElementNS('http://www.w3.org/1999/xhtml', 'html:script') : - document.createElement('script'); + document.createElementNS('http://www.w3.org/1999/xhtml', 'html:script') : + document.createElement('script'); node.type = config.scriptType || 'text/javascript'; node.charset = 'utf-8'; + node.async = true; node.setAttribute('data-requirecontext', context.contextName); node.setAttribute('data-requiremodule', moduleName); @@ -1788,15 +1779,15 @@ var requirejs, require, define; //UNFORTUNATELY Opera implements attachEvent but does not follow the script //script execution mode. if (node.attachEvent && - //Check if node.attachEvent is artificially added by custom script or - //natively supported by browser - //read https://github.com/jrburke/requirejs/issues/187 - //if we can NOT find [native code] then it must NOT natively supported. - //in IE8, node.attachEvent does not have toString() - //Note the test for "[native code" with no closing brace, see: - //https://github.com/jrburke/requirejs/issues/273 - !(node.attachEvent.toString && node.attachEvent.toString().indexOf('[native code') < 0) && - !isOpera) { + //Check if node.attachEvent is artificially added by custom script or + //natively supported by browser + //read https://github.com/jrburke/requirejs/issues/187 + //if we can NOT find [native code] then it must NOT natively supported. + //in IE8, node.attachEvent does not have toString() + //Note the test for "[native code" with no closing brace, see: + //https://github.com/jrburke/requirejs/issues/273 + !(node.attachEvent.toString && node.attachEvent.toString().indexOf('[native code') < 0) && + !isOpera) { //Probably IE. IE (at least 6-8) do not fire //script onload right after executing the script, so //we cannot tie the anonymous define call to a name. @@ -1877,6 +1868,7 @@ var requirejs, require, define; //baseUrl, if it is not already set. dataMain = script.getAttribute('data-main'); if (dataMain) { + //Set final baseUrl if there is not already an explicit one. if (!cfg.baseUrl) { //Pull off the directory of data-main for use as the //baseUrl. @@ -1884,13 +1876,14 @@ var requirejs, require, define; mainScript = src.pop(); subPath = src.length ? src.join('/') + '/' : './'; - //Set final config. cfg.baseUrl = subPath; - //Strip off any trailing .js since dataMain is now - //like a module name. - dataMain = mainScript.replace(jsSuffixRegExp, ''); + dataMain = mainScript; } + //Strip off any trailing .js since dataMain is now + //like a module name. + dataMain = dataMain.replace(jsSuffixRegExp, ''); + //Put the data-main script in the files to load. cfg.deps = cfg.deps ? cfg.deps.concat(dataMain) : [dataMain]; @@ -1909,7 +1902,7 @@ var requirejs, require, define; define = function (name, deps, callback) { var node, context; - //Allow for anonymous functions + //Allow for anonymous modules if (typeof name !== 'string') { //Adjust args appropriately callback = deps; diff --git a/tool/update_deps.js b/tool/update_deps.js index 91630a50..6d74040c 100644 --- a/tool/update_deps.js +++ b/tool/update_deps.js @@ -19,6 +19,10 @@ var deps = [{ path: "mode/css/csslint.js", url: "https://raw.github.com/stubbornella/csslint/master/release/csslint-node.js", needsFixup: true +}, { + path: "../../demo/kitchen-sink/require.js", + url: "https://raw.github.com/jrburke/requirejs/master/require.js", + needsFixup: false }] var download = function(href, callback) { From 9d82f0d406a9ef14f444635328b796790fc8b06e Mon Sep 17 00:00:00 2001 From: DanyaPostfactum Date: Mon, 29 Oct 2012 17:11:06 +1100 Subject: [PATCH 62/66] Fix contextual menu in Chrome (Windows) --- lib/ace/keyboard/textinput.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 7204c022..44632ef3 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -298,7 +298,7 @@ var TextInput = function(parentNode, host) { host.renderer.$keepTextAreaAtCursor = null; // on windows context menu is opened after mouseup - if (useragent.isWin && (useragent.isGecko || useragent.isIE)) + if (useragent.isWin) event.capture(host.container, function(e) { text.style.left = e.clientX - 2 + "px"; text.style.top = e.clientY - 2 + "px"; From 4c9f8cf0bd7405bc55410a056a7bcbcd8a9fcb89 Mon Sep 17 00:00:00 2001 From: nightwing Date: Mon, 29 Oct 2012 11:51:41 +0400 Subject: [PATCH 63/66] ie8 fixes --- lib/ace/virtual_renderer.js | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/lib/ace/virtual_renderer.js b/lib/ace/virtual_renderer.js index 757db95c..5f14bc14 100644 --- a/lib/ace/virtual_renderer.js +++ b/lib/ace/virtual_renderer.js @@ -164,8 +164,8 @@ var VirtualRenderer = function(container, theme) { ); this.$loop.schedule(this.CHANGE_FULL); - this.setPadding(4); this.updateCharacterSize(); + this.setPadding(4); }; (function() { @@ -509,13 +509,11 @@ var VirtualRenderer = function(container, theme) { }; this.$updatePrintMargin = function() { - var containerEl; - if (!this.$showPrintMargin && !this.$printMarginEl) return; if (!this.$printMarginEl) { - containerEl = dom.createElement("div"); + var containerEl = dom.createElement("div"); containerEl.className = "ace_layer ace_print-margin-layer"; this.$printMarginEl = dom.createElement("div"); this.$printMarginEl.className = "ace_print-margin"; From 66836adbc35d7b5a857fae0e009ac14912a43a93 Mon Sep 17 00:00:00 2001 From: nightwing Date: Mon, 29 Oct 2012 12:14:04 +0400 Subject: [PATCH 64/66] fix getVersion for install -c --- install.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/install.js b/install.js index 730fc12c..53e8c454 100644 --- a/install.js +++ b/install.js @@ -42,6 +42,10 @@ function getVersion(path) { return fs.readFileSync(path + "/.git-ref", "utf8"); if (fs.existsSync(path + "/.git/ORIG_HEAD")) return fs.readFileSync(path + "/.git/ORIG_HEAD", "utf8"); + if (fs.existsSync(path + "/.sourcemint/source.json")) { + var json = fs.readFileSync(path + "/.sourcemint/source.json", "utf8"); + return JSON.parse(json).url.split("/").pop(); + } } if (process.argv.indexOf("-c") > 0) try { From aa0c0d5fa79bf8d45cc5fe53d094be8c0954168b Mon Sep 17 00:00:00 2001 From: nightwing Date: Wed, 31 Oct 2012 17:37:02 +0400 Subject: [PATCH 65/66] Revert "Merge branch 'textinput' into master" This reverts commit 8d9f0e28eb6dffa52f63974534f94d505597d06f, reversing changes made to 5538d1654a0740b3ba1c9bd744c4c3afc5e22312. --- lib/ace/editor.js | 5 - lib/ace/keyboard/textinput.js | 336 +++++++++++++++------------------- 2 files changed, 151 insertions(+), 190 deletions(-) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 65d31201..9f9aee0c 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -652,11 +652,6 @@ var Editor = function(renderer, session) { this.insert(text); }; - - this.execCommand = function(command, args) { - this.commands.exec(command, this, args); - }; - /** * Editor.insert(text) * - text (String): The new text to add diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index f2c632df..44632ef3 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -48,98 +48,75 @@ var TextInput = function(parentNode, host) { text.setAttribute("x-palm-disable-auto-cap", true); text.wrap = "off"; - text.autocorrect = "off"; - text.autocapitalize = "off"; text.spellcheck = false; text.style.top = "-2em"; parentNode.insertBefore(text, parentNode.firstChild); - var PLACEHOLDER = useragent.isIE || useragent.isOpera ? "\x01\x01" : "\x00\x00"; - - resetValue(); - + var PLACEHOLDER = useragent.isIE ? "\x01" : "\x00"; + reset(true); if (isFocused()) host.onFocus(); - // Somehow fixes problem with firing onpropertychange on first typed char - if (useragent.isOldIE) { - resetSelection(); - resetValue(); - setTimeout(resetSelection); - } - - var cut = false + var inCompostion = false; var copied = false; var pasted = false; - - var inCompostion = false; - - var isSelectionEmpty = true; - var tempStyle = ''; - function resetValue() { - text.value = PLACEHOLDER; - //http://code.google.com/p/chromium/issues/detail?id=76516 - if (useragent.isWebKit) - setTimeout(function(){ + function reset(full) { + try { + if (full) { text.value = PLACEHOLDER; - resetSelection(); - }); + text.selectionStart = 0; + text.selectionEnd = 1; + } else + text.select(); + } catch (e) {} + } + + function sendText(valueToSend) { + if (!copied) { + var value = valueToSend || text.value; + if (value) { + if (value.length > 1) { + if (value.charAt(0) == PLACEHOLDER) + value = value.substr(1); + else if (value.charAt(value.length - 1) == PLACEHOLDER) + value = value.slice(0, -1); + } + + if (value && value != PLACEHOLDER) { + if (pasted) + host.onPaste(value); + else + host.onTextInput(value); + } + } + } + + copied = false; + pasted = false; + + // Safari doesn't fire copy events if no text is selected + reset(true); + } + + var onTextInput = function(e) { + if (!inCompostion) + sendText(e.data); + setTimeout(function () { + if (!inCompostion) + reset(true); + }, 0); }; - function resetSelection() { - var selectionStart = isSelectionEmpty ? 2 : 1; - var selectionEnd = 2; - - if (text.setSelectionRange) { - text.setSelectionRange(selectionStart, selectionEnd); - } - // IE8 does not support setSelectionRange - else if (text.createTextRange) { - var range = text.createTextRange(); - range.collapse(true); - range.moveEnd('character', selectionEnd); - range.moveStart('character', selectionStart); - range.select(); - } - }; - - var onSelect = function(e) { - if (cut) { - cut = false; - return; - } - if (copied) { - copied = false; - return; - } - if (text.selectionStart === 0 && text.selectionEnd === text.value.length) { - host.selectAll(); - resetSelection(); - } - }; - - var onInput = function(e) { - if (inCompostion) - return; - - if (pasted) { - var data = text.value; - resetValue(); - if (data) - host.onPaste(data); - pasted = false; - return; - } - - var data = text.value.substring(isSelectionEmpty ? 2 : 1); - resetValue(); - if (data) - host.onTextInput(data); - else - host.execCommand("del", {source: "ace"}); + var onPropertyChange = function(e) { + setTimeout(function() { + if (!inCompostion) + if(text.value != "") { + sendText(); + } + }, 0); }; var onCompositionStart = function(e) { @@ -158,111 +135,37 @@ var TextInput = function(parentNode, host) { host.onCompositionEnd(); }; - var onCut = function(e) { - var data = host.getCopyText(); - if (!data) { - event.preventDefault(e); - return; - } - - var clipboardData = e.clipboardData || window.clipboardData; - - if (clipboardData) { - // Safari 5 has clipboardData object, but does not handle setData() - var supported = clipboardData.setData("Text", data); - if (supported) { - host.onCut(); - event.preventDefault(e); - } - } - - if (!supported) { - cut = true; - text.value = data; - text.select(); - setTimeout(function(){ host.onCut() }); - } - }; - var onCopy = function(e) { - var data = host.getCopyText(); - if (!data) { - event.preventDefault(e); - return; - } - - var clipboardData = e.clipboardData || window.clipboardData; - - if (clipboardData) { - // Safari 5 has clipboardData object, but does not handle setData() - var supported = clipboardData.setData("Text", data); - if (supported) { - host.onCopy(); - event.preventDefault(e); - } - } - if (!supported) { - copied = true; - text.value = data; - text.select(); - setTimeout(function(){ host.onCopy() }); - } - - + copied = true; + var copyText = host.getCopyText(); + if(copyText) + text.value = copyText; + else + e.preventDefault(); + reset(); + setTimeout(function () { + sendText(); + }, 0); }; - var onPaste = function(e) { - var clipboardData = e.clipboardData || window.clipboardData; - - if (clipboardData) { - var data = clipboardData.getData("Text"); - if (data) - host.onPaste(data); - event.preventDefault(e); - } - else { - text.value = ""; - pasted = true; - } + var onCut = function(e) { + copied = true; + var copyText = host.getCopyText(); + if(copyText) { + text.value = copyText; + host.onCut(); + } else + e.preventDefault(); + reset(); + setTimeout(function () { + sendText(); + }, 0); }; event.addCommandKeyListener(text, host.onCommandKey.bind(host)); - - event.addListener(text, "select", onSelect); - - event.addListener(text, "input", onInput); - - event.addListener(text, "cut", onCut); - event.addListener(text, "copy", onCopy); - event.addListener(text, "paste", onPaste); - - - // Opera has no clipboard events - if (!('oncut' in text) || !('oncopy' in text) || !('onpaste' in text)){ - event.addListener(parentNode, "keydown", function(e) { - if ((useragent.isMac && !e.metaKey) || !e.ctrlKey) - return; - - switch (e.keyCode) { - case 67: - onCopy(e); - break; - case 86: - onPaste(e); - break; - case 88: - onCut(e); - break; - } - }); - } - + event.addListener(text, "input", onTextInput); + if (useragent.isOldIE) { - event.addListener(text, "propertychange", function(e){ - if (text.value != "" && text.value != PLACEHOLDER) - onInput(e); - }); - var keytable = { 13:1, 27:1 }; event.addListener(text, "keyup", function (e) { if (inCompostion && (!text.value || keytable[e.keyCode])) @@ -272,6 +175,70 @@ var TextInput = function(parentNode, host) { } inCompostion ? onCompositionUpdate() : onCompositionStart(); }); + + event.addListener(text, "propertychange", function() { + if (text.value != PLACEHOLDER) + setTimeout(sendText, 0); + }); + } + + event.addListener(text, "paste", function(e) { + // Mark that the next input text comes from past. + pasted = true; + // Some browsers support the event.clipboardData API. Use this to get + // the pasted content which increases speed if pasting a lot of lines. + if (e.clipboardData && e.clipboardData.getData) { + sendText(e.clipboardData.getData("text/plain")); + e.preventDefault(); + } + else { + // If a browser doesn't support any of the things above, use the regular + // method to detect the pasted input. + onPropertyChange(); + } + }); + + if ("onbeforecopy" in text && typeof clipboardData !== "undefined") { + event.addListener(text, "beforecopy", function(e) { + if (tempStyle) + return; // without this text is copied when contextmenu is shown + var copyText = host.getCopyText(); + if (copyText) + clipboardData.setData("Text", copyText); + else + e.preventDefault(); + }); + event.addListener(parentNode, "keydown", function(e) { + if (e.ctrlKey && e.keyCode == 88) { + var copyText = host.getCopyText(); + if (copyText) { + clipboardData.setData("Text", copyText); + host.onCut(); + } + event.preventDefault(e); + } + }); + event.addListener(text, "cut", onCut); // for ie9 context menu + } + else if (useragent.isOpera && !("KeyboardEvent" in window)) { + event.addListener(parentNode, "keydown", function(e) { + if ((useragent.isMac && !e.metaKey) || !e.ctrlKey) + return; + + if ((e.keyCode == 88 || e.keyCode == 67)) { + var copyText = host.getCopyText(); + if (copyText) { + text.value = copyText; + text.select(); + if (e.keyCode == 88) + host.onCut(); + } + } + }); + } + else { + event.addListener(text, "copy", onCopy); + event.addListener(text, "cut", onCut); } event.addListener(text, "compositionstart", onCompositionStart); @@ -289,10 +256,11 @@ var TextInput = function(parentNode, host) { event.addListener(text, "focus", function() { host.onFocus(); - resetSelection(); + reset(); }); this.focus = function() { + reset(); text.focus(); }; @@ -318,6 +286,11 @@ var TextInput = function(parentNode, host) { (useragent.isIE ? "background:rgba(0, 0, 0, 0.03); opacity:0.1;" : "") + //"background:rgba(250, 0, 0, 0.3); opacity:1;" + "left:" + (e.clientX - 2) + "px; top:" + (e.clientY - 2) + "px;"; + if (host.selection.isEmpty()) + text.value = ""; + else + reset(true); + if (e.type != "mousedown") return; @@ -338,6 +311,7 @@ var TextInput = function(parentNode, host) { text.style.cssText = tempStyle; tempStyle = ''; } + sendText(); if (host.renderer.$keepTextAreaAtCursor == null) { host.renderer.$keepTextAreaAtCursor = true; host.renderer.$moveTextAreaToCursor(); @@ -350,16 +324,8 @@ var TextInput = function(parentNode, host) { if (!useragent.isGecko) event.addListener(text, "contextmenu", function(e) { host.textInput.onContextMenu(e); - onContextMenuClose(); + onContextMenuClose() }); - - - host.addEventListener('changeSelection', function(){ - if (host.selection.isEmpty() != isSelectionEmpty) { - isSelectionEmpty = !isSelectionEmpty; - resetSelection(); - } - }); }; exports.TextInput = TextInput; From 4b372b67ad96f04021acb9d6a30a3a51a5334bc1 Mon Sep 17 00:00:00 2001 From: nightwing Date: Wed, 31 Oct 2012 17:39:48 +0400 Subject: [PATCH 66/66] keep execCommand --- lib/ace/editor.js | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 9f9aee0c..65d31201 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -652,6 +652,11 @@ var Editor = function(renderer, session) { this.insert(text); }; + + this.execCommand = function(command, args) { + this.commands.exec(command, this, args); + }; + /** * Editor.insert(text) * - text (String): The new text to add