codemirror-rails 4.7 → 4.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/codemirror/rails/version.rb +2 -2
- data/vendor/assets/javascripts/codemirror.js +229 -137
- data/vendor/assets/javascripts/codemirror/addons/edit/closebrackets.js +1 -1
- data/vendor/assets/javascripts/codemirror/addons/hint/javascript-hint.js +9 -9
- data/vendor/assets/javascripts/codemirror/addons/hint/xml-hint.js +9 -1
- data/vendor/assets/javascripts/codemirror/addons/mode/loadmode.js +19 -16
- data/vendor/assets/javascripts/codemirror/addons/mode/overlay.js +3 -3
- data/vendor/assets/javascripts/codemirror/keymaps/emacs.js +19 -28
- data/vendor/assets/javascripts/codemirror/keymaps/sublime.js +14 -15
- data/vendor/assets/javascripts/codemirror/keymaps/vim.js +694 -752
- data/vendor/assets/javascripts/codemirror/modes/clike.js +15 -0
- data/vendor/assets/javascripts/codemirror/modes/css.js +1 -1
- data/vendor/assets/javascripts/codemirror/modes/dockerfile.js +80 -0
- data/vendor/assets/javascripts/codemirror/modes/gfm.js +2 -1
- data/vendor/assets/javascripts/codemirror/modes/htmlmixed.js +2 -2
- data/vendor/assets/javascripts/codemirror/modes/idl.js +290 -0
- data/vendor/assets/javascripts/codemirror/modes/markdown.js +62 -55
- data/vendor/assets/javascripts/codemirror/modes/sparql.js +19 -5
- data/vendor/assets/javascripts/codemirror/modes/sql.js +0 -2
- data/vendor/assets/javascripts/codemirror/modes/stex.js +184 -193
- data/vendor/assets/javascripts/codemirror/modes/yaml.js +6 -1
- data/vendor/assets/stylesheets/codemirror.css +11 -2
- data/vendor/assets/stylesheets/codemirror/themes/3024-day.css +1 -1
- data/vendor/assets/stylesheets/codemirror/themes/solarized.css +0 -5
- metadata +3 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0d7ed536cdd6c54bf26a2267fc6cf13ed09e4624
|
4
|
+
data.tar.gz: 62813e43c76250a3ff56dc69e5d4123a1d42217f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 3317a5d5a1f262e96ee51ce496be3108871e07f081140d3c35636beba654d2dc665a10004384f6cb49a7d6feca12a5aea7c634675cb905819226d32ed8798b79
|
7
|
+
data.tar.gz: f48c7e94303a13be7f6ef197dc5346ed5c113c829fcf9b8be8e858511b989c641bf7957082514f86df44e32140d8ee5c296118ff2e29f6703b6ce886f8ca608c
|
@@ -86,7 +86,8 @@
|
|
86
86
|
suppressEdits: false, // used to disable editing during key handlers when in readOnly mode
|
87
87
|
pasteIncoming: false, cutIncoming: false, // help recognize paste/cut edits in readInput
|
88
88
|
draggingText: false,
|
89
|
-
highlight: new Delayed() // stores highlight worker timeout
|
89
|
+
highlight: new Delayed(), // stores highlight worker timeout
|
90
|
+
keySeq: null // Unfinished key sequence
|
90
91
|
};
|
91
92
|
|
92
93
|
// Override magic textarea content restore that IE sometimes does
|
@@ -184,8 +185,10 @@
|
|
184
185
|
// Need to set a minimum width to see the scrollbar on IE7 (but must not set it on IE8).
|
185
186
|
if (ie && ie_version < 8) d.scrollbarH.style.minHeight = d.scrollbarV.style.minWidth = "18px";
|
186
187
|
|
187
|
-
if (place
|
188
|
-
|
188
|
+
if (place) {
|
189
|
+
if (place.appendChild) place.appendChild(d.wrapper);
|
190
|
+
else place(d.wrapper);
|
191
|
+
}
|
189
192
|
|
190
193
|
// Current rendered range (may be bigger than the view window).
|
191
194
|
d.viewFrom = d.viewTo = doc.first;
|
@@ -196,7 +199,7 @@
|
|
196
199
|
d.externalMeasured = null;
|
197
200
|
// Empty space (in pixels) above the view
|
198
201
|
d.viewOffset = 0;
|
199
|
-
d.
|
202
|
+
d.lastWrapHeight = d.lastWrapWidth = 0;
|
200
203
|
d.updateLineNumbers = null;
|
201
204
|
|
202
205
|
// Used to only resize the line number gutter when necessary (when
|
@@ -301,12 +304,6 @@
|
|
301
304
|
});
|
302
305
|
}
|
303
306
|
|
304
|
-
function keyMapChanged(cm) {
|
305
|
-
var map = keyMap[cm.options.keyMap], style = map.style;
|
306
|
-
cm.display.wrapper.className = cm.display.wrapper.className.replace(/\s*cm-keymap-\S+/g, "") +
|
307
|
-
(style ? " cm-keymap-" + style : "");
|
308
|
-
}
|
309
|
-
|
310
307
|
function themeChanged(cm) {
|
311
308
|
cm.display.wrapper.className = cm.display.wrapper.className.replace(/\s*cm-s-\S+/g, "") +
|
312
309
|
cm.options.theme.replace(/(^|\s)\s*/g, " cm-s-");
|
@@ -551,6 +548,7 @@
|
|
551
548
|
this.visible = visibleLines(display, cm.doc, viewport);
|
552
549
|
this.editorIsHidden = !display.wrapper.offsetWidth;
|
553
550
|
this.wrapperHeight = display.wrapper.clientHeight;
|
551
|
+
this.wrapperWidth = display.wrapper.clientWidth;
|
554
552
|
this.oldViewFrom = display.viewFrom; this.oldViewTo = display.viewTo;
|
555
553
|
this.oldScrollerWidth = display.scroller.clientWidth;
|
556
554
|
this.force = force;
|
@@ -591,7 +589,7 @@
|
|
591
589
|
}
|
592
590
|
|
593
591
|
var different = from != display.viewFrom || to != display.viewTo ||
|
594
|
-
display.
|
592
|
+
display.lastWrapHeight != update.wrapperHeight || display.lastWrapWidth != update.wrapperWidth;
|
595
593
|
adjustView(cm, from, to);
|
596
594
|
|
597
595
|
display.viewOffset = heightAtLine(getLine(cm.doc, display.viewFrom));
|
@@ -619,7 +617,8 @@
|
|
619
617
|
removeChildren(display.selectionDiv);
|
620
618
|
|
621
619
|
if (different) {
|
622
|
-
display.
|
620
|
+
display.lastWrapHeight = update.wrapperHeight;
|
621
|
+
display.lastWrapWidth = update.wrapperWidth;
|
623
622
|
startWorker(cm, 400);
|
624
623
|
}
|
625
624
|
|
@@ -868,9 +867,12 @@
|
|
868
867
|
if (cm.options.lineNumbers || markers) {
|
869
868
|
var wrap = ensureLineWrapped(lineView);
|
870
869
|
var gutterWrap = lineView.gutter =
|
871
|
-
wrap.insertBefore(elt("div", null, "CodeMirror-gutter-wrapper", "
|
872
|
-
(cm.options.fixedGutter ? dims.fixedPos : -dims.gutterTotalWidth) +
|
870
|
+
wrap.insertBefore(elt("div", null, "CodeMirror-gutter-wrapper", "left: " +
|
871
|
+
(cm.options.fixedGutter ? dims.fixedPos : -dims.gutterTotalWidth) +
|
872
|
+
"px; width: " + dims.gutterTotalWidth + "px"),
|
873
873
|
lineView.text);
|
874
|
+
if (lineView.line.gutterClass)
|
875
|
+
gutterWrap.className += " " + lineView.line.gutterClass;
|
874
876
|
if (cm.options.lineNumbers && (!markers || !markers["CodeMirror-linenumbers"]))
|
875
877
|
lineView.lineNumber = gutterWrap.appendChild(
|
876
878
|
elt("div", lineNumberFor(cm.options, lineN),
|
@@ -2397,7 +2399,7 @@
|
|
2397
2399
|
// possible when it is clear that nothing happened. hasSelection
|
2398
2400
|
// will be the case when there is a lot of text in the textarea,
|
2399
2401
|
// in which case reading its value would be expensive.
|
2400
|
-
if (!cm.state.focused || (hasSelection(input) && !prevInput) || isReadOnly(cm) || cm.options.disableInput)
|
2402
|
+
if (!cm.state.focused || (hasSelection(input) && !prevInput) || isReadOnly(cm) || cm.options.disableInput || cm.state.keySeq)
|
2401
2403
|
return false;
|
2402
2404
|
// See paste handler for more on the fakedLastChar kludge
|
2403
2405
|
if (cm.state.pasteIncoming && cm.state.fakedLastChar) {
|
@@ -2652,8 +2654,10 @@
|
|
2652
2654
|
|
2653
2655
|
// Called when the window resizes
|
2654
2656
|
function onResize(cm) {
|
2655
|
-
// Might be a text scaling operation, clear size caches.
|
2656
2657
|
var d = cm.display;
|
2658
|
+
if (d.lastWrapHeight == d.wrapper.clientHeight && d.lastWrapWidth == d.wrapper.clientWidth)
|
2659
|
+
return;
|
2660
|
+
// Might be a text scaling operation, clear size caches.
|
2657
2661
|
d.cachedCharWidth = d.cachedTextHeight = d.cachedPaddingH = null;
|
2658
2662
|
cm.setSize();
|
2659
2663
|
}
|
@@ -3167,62 +3171,70 @@
|
|
3167
3171
|
return done;
|
3168
3172
|
}
|
3169
3173
|
|
3170
|
-
|
3171
|
-
|
3172
|
-
|
3173
|
-
|
3174
|
-
|
3175
|
-
return
|
3174
|
+
function lookupKeyForEditor(cm, name, handle) {
|
3175
|
+
for (var i = 0; i < cm.state.keyMaps.length; i++) {
|
3176
|
+
var result = lookupKey(name, cm.state.keyMaps[i], handle);
|
3177
|
+
if (result) return result;
|
3178
|
+
}
|
3179
|
+
return (cm.options.extraKeys && lookupKey(name, cm.options.extraKeys, handle))
|
3180
|
+
|| lookupKey(name, cm.options.keyMap, handle);
|
3181
|
+
}
|
3182
|
+
|
3183
|
+
var stopSeq = new Delayed;
|
3184
|
+
function dispatchKey(cm, name, e, handle) {
|
3185
|
+
var seq = cm.state.keySeq;
|
3186
|
+
if (seq) {
|
3187
|
+
if (isModifierKey(name)) return "handled";
|
3188
|
+
stopSeq.set(50, function() {
|
3189
|
+
if (cm.state.keySeq == seq) {
|
3190
|
+
cm.state.keySeq = null;
|
3191
|
+
resetInput(cm);
|
3192
|
+
}
|
3193
|
+
});
|
3194
|
+
name = seq + " " + name;
|
3195
|
+
}
|
3196
|
+
var result = lookupKeyForEditor(cm, name, handle);
|
3197
|
+
|
3198
|
+
if (result == "multi")
|
3199
|
+
cm.state.keySeq = name;
|
3200
|
+
if (result == "handled")
|
3201
|
+
signalLater(cm, "keyHandled", cm, name, e);
|
3202
|
+
|
3203
|
+
if (result == "handled" || result == "multi") {
|
3204
|
+
e_preventDefault(e);
|
3205
|
+
restartBlink(cm);
|
3206
|
+
}
|
3207
|
+
|
3208
|
+
if (seq && !result && /\'$/.test(name)) {
|
3209
|
+
e_preventDefault(e);
|
3210
|
+
return true;
|
3211
|
+
}
|
3212
|
+
return !!result;
|
3176
3213
|
}
|
3177
3214
|
|
3178
|
-
var maybeTransition;
|
3179
3215
|
// Handle a key from the keydown event.
|
3180
3216
|
function handleKeyBinding(cm, e) {
|
3181
|
-
|
3182
|
-
var startMap = getKeyMap(cm.options.keyMap), next = startMap.auto;
|
3183
|
-
clearTimeout(maybeTransition);
|
3184
|
-
if (next && !isModifierKey(e)) maybeTransition = setTimeout(function() {
|
3185
|
-
if (getKeyMap(cm.options.keyMap) == startMap) {
|
3186
|
-
cm.options.keyMap = (next.call ? next.call(null, cm) : next);
|
3187
|
-
keyMapChanged(cm);
|
3188
|
-
}
|
3189
|
-
}, 50);
|
3190
|
-
|
3191
|
-
var name = keyName(e, true), handled = false;
|
3217
|
+
var name = keyName(e, true);
|
3192
3218
|
if (!name) return false;
|
3193
|
-
var keymaps = allKeyMaps(cm);
|
3194
3219
|
|
3195
|
-
if (e.shiftKey) {
|
3220
|
+
if (e.shiftKey && !cm.state.keySeq) {
|
3196
3221
|
// First try to resolve full name (including 'Shift-'). Failing
|
3197
3222
|
// that, see if there is a cursor-motion command (starting with
|
3198
3223
|
// 'go') bound to the keyname without 'Shift-'.
|
3199
|
-
|
3200
|
-
|
3201
|
-
|
3202
|
-
|
3203
|
-
|
3224
|
+
return dispatchKey(cm, "Shift-" + name, e, function(b) {return doHandleBinding(cm, b, true);})
|
3225
|
+
|| dispatchKey(cm, name, e, function(b) {
|
3226
|
+
if (typeof b == "string" ? /^go[A-Z]/.test(b) : b.motion)
|
3227
|
+
return doHandleBinding(cm, b);
|
3228
|
+
});
|
3204
3229
|
} else {
|
3205
|
-
|
3230
|
+
return dispatchKey(cm, name, e, function(b) { return doHandleBinding(cm, b); });
|
3206
3231
|
}
|
3207
|
-
|
3208
|
-
if (handled) {
|
3209
|
-
e_preventDefault(e);
|
3210
|
-
restartBlink(cm);
|
3211
|
-
signalLater(cm, "keyHandled", cm, name, e);
|
3212
|
-
}
|
3213
|
-
return handled;
|
3214
3232
|
}
|
3215
3233
|
|
3216
3234
|
// Handle a key from the keypress event
|
3217
3235
|
function handleCharBinding(cm, e, ch) {
|
3218
|
-
|
3219
|
-
|
3220
|
-
if (handled) {
|
3221
|
-
e_preventDefault(e);
|
3222
|
-
restartBlink(cm);
|
3223
|
-
signalLater(cm, "keyHandled", cm, "'" + ch + "'", e);
|
3224
|
-
}
|
3225
|
-
return handled;
|
3236
|
+
return dispatchKey(cm, "'" + ch + "'", e,
|
3237
|
+
function(b) { return doHandleBinding(cm, b, true); });
|
3226
3238
|
}
|
3227
3239
|
|
3228
3240
|
var lastStoppedKey = null;
|
@@ -3701,6 +3713,8 @@
|
|
3701
3713
|
// If an editor sits on the top or bottom of the window, partially
|
3702
3714
|
// scrolled out of view, this ensures that the cursor is visible.
|
3703
3715
|
function maybeScrollWindow(cm, coords) {
|
3716
|
+
if (signalDOMEvent(cm, "scrollCursorIntoView")) return;
|
3717
|
+
|
3704
3718
|
var display = cm.display, box = display.sizer.getBoundingClientRect(), doScroll = null;
|
3705
3719
|
if (coords.top + box.top < 0) doScroll = true;
|
3706
3720
|
else if (coords.bottom + box.top > (window.innerHeight || document.documentElement.clientHeight)) doScroll = false;
|
@@ -4024,12 +4038,12 @@
|
|
4024
4038
|
getDoc: function() {return this.doc;},
|
4025
4039
|
|
4026
4040
|
addKeyMap: function(map, bottom) {
|
4027
|
-
this.state.keyMaps[bottom ? "push" : "unshift"](map);
|
4041
|
+
this.state.keyMaps[bottom ? "push" : "unshift"](getKeyMap(map));
|
4028
4042
|
},
|
4029
4043
|
removeKeyMap: function(map) {
|
4030
4044
|
var maps = this.state.keyMaps;
|
4031
4045
|
for (var i = 0; i < maps.length; ++i)
|
4032
|
-
if (maps[i] == map ||
|
4046
|
+
if (maps[i] == map || maps[i].name == map) {
|
4033
4047
|
maps.splice(i, 1);
|
4034
4048
|
return true;
|
4035
4049
|
}
|
@@ -4086,20 +4100,11 @@
|
|
4086
4100
|
// Fetch the parser token for a given character. Useful for hacks
|
4087
4101
|
// that want to inspect the mode state (say, for completion).
|
4088
4102
|
getTokenAt: function(pos, precise) {
|
4089
|
-
|
4090
|
-
|
4091
|
-
|
4092
|
-
|
4093
|
-
|
4094
|
-
while (stream.pos < pos.ch && !stream.eol()) {
|
4095
|
-
stream.start = stream.pos;
|
4096
|
-
var style = readToken(mode, stream, state);
|
4097
|
-
}
|
4098
|
-
return {start: stream.start,
|
4099
|
-
end: stream.pos,
|
4100
|
-
string: stream.current(),
|
4101
|
-
type: style || null,
|
4102
|
-
state: state};
|
4103
|
+
return takeToken(this, pos, precise);
|
4104
|
+
},
|
4105
|
+
|
4106
|
+
getLineTokens: function(line, precise) {
|
4107
|
+
return takeToken(this, Pos(line), precise, true);
|
4103
4108
|
},
|
4104
4109
|
|
4105
4110
|
getTokenTypeAt: function(pos) {
|
@@ -4502,7 +4507,12 @@
|
|
4502
4507
|
themeChanged(cm);
|
4503
4508
|
guttersChanged(cm);
|
4504
4509
|
}, true);
|
4505
|
-
option("keyMap", "default",
|
4510
|
+
option("keyMap", "default", function(cm, val, old) {
|
4511
|
+
var next = getKeyMap(val);
|
4512
|
+
var prev = old != CodeMirror.Init && getKeyMap(old);
|
4513
|
+
if (prev && prev.detach) prev.detach(cm, next);
|
4514
|
+
if (next.attach) next.attach(cm, prev || null);
|
4515
|
+
});
|
4506
4516
|
option("extraKeys", null);
|
4507
4517
|
|
4508
4518
|
option("lineWrapping", false, wrappingChanged, true);
|
@@ -4847,9 +4857,11 @@
|
|
4847
4857
|
toggleOverwrite: function(cm) {cm.toggleOverwrite();}
|
4848
4858
|
};
|
4849
4859
|
|
4860
|
+
|
4850
4861
|
// STANDARD KEYMAPS
|
4851
4862
|
|
4852
4863
|
var keyMap = CodeMirror.keyMap = {};
|
4864
|
+
|
4853
4865
|
keyMap.basic = {
|
4854
4866
|
"Left": "goCharLeft", "Right": "goCharRight", "Up": "goLineUp", "Down": "goLineDown",
|
4855
4867
|
"End": "goLineEnd", "Home": "goLineStartSmart", "PageUp": "goPageUp", "PageDown": "goPageDown",
|
@@ -4871,6 +4883,13 @@
|
|
4871
4883
|
"Ctrl-U": "undoSelection", "Shift-Ctrl-U": "redoSelection", "Alt-U": "redoSelection",
|
4872
4884
|
fallthrough: "basic"
|
4873
4885
|
};
|
4886
|
+
// Very basic readline/emacs-style bindings, which are standard on Mac.
|
4887
|
+
keyMap.emacsy = {
|
4888
|
+
"Ctrl-F": "goCharRight", "Ctrl-B": "goCharLeft", "Ctrl-P": "goLineUp", "Ctrl-N": "goLineDown",
|
4889
|
+
"Alt-F": "goWordRight", "Alt-B": "goWordLeft", "Ctrl-A": "goLineStart", "Ctrl-E": "goLineEnd",
|
4890
|
+
"Ctrl-V": "goPageDown", "Shift-Ctrl-V": "goPageUp", "Ctrl-D": "delCharAfter", "Ctrl-H": "delCharBefore",
|
4891
|
+
"Alt-D": "delWordAfter", "Alt-Backspace": "delWordBefore", "Ctrl-K": "killLine", "Ctrl-T": "transposeChars"
|
4892
|
+
};
|
4874
4893
|
keyMap.macDefault = {
|
4875
4894
|
"Cmd-A": "selectAll", "Cmd-D": "deleteLine", "Cmd-Z": "undo", "Shift-Cmd-Z": "redo", "Cmd-Y": "redo",
|
4876
4895
|
"Cmd-Home": "goDocStart", "Cmd-Up": "goDocStart", "Cmd-End": "goDocEnd", "Cmd-Down": "goDocEnd", "Alt-Left": "goGroupLeft",
|
@@ -4881,70 +4900,100 @@
|
|
4881
4900
|
"Cmd-U": "undoSelection", "Shift-Cmd-U": "redoSelection", "Ctrl-Up": "goDocStart", "Ctrl-Down": "goDocEnd",
|
4882
4901
|
fallthrough: ["basic", "emacsy"]
|
4883
4902
|
};
|
4884
|
-
// Very basic readline/emacs-style bindings, which are standard on Mac.
|
4885
|
-
keyMap.emacsy = {
|
4886
|
-
"Ctrl-F": "goCharRight", "Ctrl-B": "goCharLeft", "Ctrl-P": "goLineUp", "Ctrl-N": "goLineDown",
|
4887
|
-
"Alt-F": "goWordRight", "Alt-B": "goWordLeft", "Ctrl-A": "goLineStart", "Ctrl-E": "goLineEnd",
|
4888
|
-
"Ctrl-V": "goPageDown", "Shift-Ctrl-V": "goPageUp", "Ctrl-D": "delCharAfter", "Ctrl-H": "delCharBefore",
|
4889
|
-
"Alt-D": "delWordAfter", "Alt-Backspace": "delWordBefore", "Ctrl-K": "killLine", "Ctrl-T": "transposeChars"
|
4890
|
-
};
|
4891
4903
|
keyMap["default"] = mac ? keyMap.macDefault : keyMap.pcDefault;
|
4892
4904
|
|
4893
4905
|
// KEYMAP DISPATCH
|
4894
4906
|
|
4895
|
-
function
|
4896
|
-
|
4897
|
-
|
4898
|
-
|
4899
|
-
|
4900
|
-
|
4901
|
-
|
4902
|
-
|
4903
|
-
|
4904
|
-
|
4905
|
-
|
4906
|
-
|
4907
|
-
|
4908
|
-
|
4909
|
-
|
4910
|
-
|
4911
|
-
|
4912
|
-
|
4913
|
-
|
4914
|
-
|
4915
|
-
|
4916
|
-
|
4917
|
-
|
4918
|
-
|
4907
|
+
function normalizeKeyName(name) {
|
4908
|
+
var parts = name.split(/-(?!$)/), name = parts[parts.length - 1];
|
4909
|
+
var alt, ctrl, shift, cmd;
|
4910
|
+
for (var i = 0; i < parts.length - 1; i++) {
|
4911
|
+
var mod = parts[i];
|
4912
|
+
if (/^(cmd|meta|m)$/i.test(mod)) cmd = true;
|
4913
|
+
else if (/^a(lt)?$/i.test(mod)) alt = true;
|
4914
|
+
else if (/^(c|ctrl|control)$/i.test(mod)) ctrl = true;
|
4915
|
+
else if (/^s(hift)$/i.test(mod)) shift = true;
|
4916
|
+
else throw new Error("Unrecognized modifier name: " + mod);
|
4917
|
+
}
|
4918
|
+
if (alt) name = "Alt-" + name;
|
4919
|
+
if (ctrl) name = "Ctrl-" + name;
|
4920
|
+
if (cmd) name = "Cmd-" + name;
|
4921
|
+
if (shift) name = "Shift-" + name;
|
4922
|
+
return name;
|
4923
|
+
}
|
4924
|
+
|
4925
|
+
// This is a kludge to keep keymaps mostly working as raw objects
|
4926
|
+
// (backwards compatibility) while at the same time support features
|
4927
|
+
// like normalization and multi-stroke key bindings. It compiles a
|
4928
|
+
// new normalized keymap, and then updates the old object to reflect
|
4929
|
+
// this.
|
4930
|
+
CodeMirror.normalizeKeyMap = function(keymap) {
|
4931
|
+
var copy = {};
|
4932
|
+
for (var keyname in keymap) if (keymap.hasOwnProperty(keyname)) {
|
4933
|
+
var value = keymap[keyname];
|
4934
|
+
if (/^(name|fallthrough|(de|at)tach)$/.test(keyname)) continue;
|
4935
|
+
if (value == "...") { delete keymap[keyname]; continue; }
|
4936
|
+
|
4937
|
+
var keys = map(keyname.split(" "), normalizeKeyName);
|
4938
|
+
for (var i = 0; i < keys.length; i++) {
|
4939
|
+
var val, name;
|
4940
|
+
if (i == keys.length - 1) {
|
4941
|
+
name = keyname;
|
4942
|
+
val = value;
|
4943
|
+
} else {
|
4944
|
+
name = keys.slice(0, i + 1).join(" ");
|
4945
|
+
val = "...";
|
4946
|
+
}
|
4947
|
+
var prev = copy[name];
|
4948
|
+
if (!prev) copy[name] = val;
|
4949
|
+
else if (prev != val) throw new Error("Inconsistent bindings for " + name);
|
4919
4950
|
}
|
4920
|
-
|
4951
|
+
delete keymap[keyname];
|
4921
4952
|
}
|
4953
|
+
for (var prop in copy) keymap[prop] = copy[prop];
|
4954
|
+
return keymap;
|
4955
|
+
};
|
4922
4956
|
|
4923
|
-
|
4924
|
-
|
4925
|
-
|
4957
|
+
var lookupKey = CodeMirror.lookupKey = function(key, map, handle) {
|
4958
|
+
map = getKeyMap(map);
|
4959
|
+
var found = map.call ? map.call(key) : map[key];
|
4960
|
+
if (found === false) return "nothing";
|
4961
|
+
if (found === "...") return "multi";
|
4962
|
+
if (found != null && handle(found)) return "handled";
|
4963
|
+
|
4964
|
+
if (map.fallthrough) {
|
4965
|
+
if (Object.prototype.toString.call(map.fallthrough) != "[object Array]")
|
4966
|
+
return lookupKey(key, map.fallthrough, handle);
|
4967
|
+
for (var i = 0; i < map.fallthrough.length; i++) {
|
4968
|
+
var result = lookupKey(key, map.fallthrough[i], handle);
|
4969
|
+
if (result) return result;
|
4970
|
+
}
|
4926
4971
|
}
|
4927
4972
|
};
|
4928
4973
|
|
4929
4974
|
// Modifier key presses don't count as 'real' key presses for the
|
4930
4975
|
// purpose of keymap fallthrough.
|
4931
|
-
var isModifierKey = CodeMirror.isModifierKey = function(
|
4932
|
-
var name = keyNames[
|
4976
|
+
var isModifierKey = CodeMirror.isModifierKey = function(value) {
|
4977
|
+
var name = typeof value == "string" ? value : keyNames[value.keyCode];
|
4933
4978
|
return name == "Ctrl" || name == "Alt" || name == "Shift" || name == "Mod";
|
4934
4979
|
};
|
4935
4980
|
|
4936
4981
|
// Look up the name of a key as indicated by an event object.
|
4937
4982
|
var keyName = CodeMirror.keyName = function(event, noShift) {
|
4938
4983
|
if (presto && event.keyCode == 34 && event["char"]) return false;
|
4939
|
-
var
|
4984
|
+
var base = keyNames[event.keyCode], name = base;
|
4940
4985
|
if (name == null || event.altGraphKey) return false;
|
4941
|
-
if (event.altKey) name = "Alt-" + name;
|
4942
|
-
if (flipCtrlCmd ? event.metaKey : event.ctrlKey) name = "Ctrl-" + name;
|
4943
|
-
if (flipCtrlCmd ? event.ctrlKey : event.metaKey) name = "Cmd-" + name;
|
4944
|
-
if (!noShift && event.shiftKey) name = "Shift-" + name;
|
4986
|
+
if (event.altKey && base != "Alt") name = "Alt-" + name;
|
4987
|
+
if ((flipCtrlCmd ? event.metaKey : event.ctrlKey) && base != "Ctrl") name = "Ctrl-" + name;
|
4988
|
+
if ((flipCtrlCmd ? event.ctrlKey : event.metaKey) && base != "Cmd") name = "Cmd-" + name;
|
4989
|
+
if (!noShift && event.shiftKey && base != "Shift") name = "Shift-" + name;
|
4945
4990
|
return name;
|
4946
4991
|
};
|
4947
4992
|
|
4993
|
+
function getKeyMap(val) {
|
4994
|
+
return typeof val == "string" ? keyMap[val] : val;
|
4995
|
+
}
|
4996
|
+
|
4948
4997
|
// FROMTEXTAREA
|
4949
4998
|
|
4950
4999
|
CodeMirror.fromTextArea = function(textarea, options) {
|
@@ -5794,20 +5843,44 @@
|
|
5794
5843
|
if (inner.mode.blankLine) return inner.mode.blankLine(inner.state);
|
5795
5844
|
}
|
5796
5845
|
|
5797
|
-
function readToken(mode, stream, state) {
|
5846
|
+
function readToken(mode, stream, state, inner) {
|
5798
5847
|
for (var i = 0; i < 10; i++) {
|
5848
|
+
if (inner) inner[0] = CodeMirror.innerMode(mode, state).mode;
|
5799
5849
|
var style = mode.token(stream, state);
|
5800
5850
|
if (stream.pos > stream.start) return style;
|
5801
5851
|
}
|
5802
5852
|
throw new Error("Mode " + mode.name + " failed to advance stream.");
|
5803
5853
|
}
|
5804
5854
|
|
5855
|
+
// Utility for getTokenAt and getLineTokens
|
5856
|
+
function takeToken(cm, pos, precise, asArray) {
|
5857
|
+
function getObj(copy) {
|
5858
|
+
return {start: stream.start, end: stream.pos,
|
5859
|
+
string: stream.current(),
|
5860
|
+
type: style || null,
|
5861
|
+
state: copy ? copyState(doc.mode, state) : state};
|
5862
|
+
}
|
5863
|
+
|
5864
|
+
var doc = cm.doc, mode = doc.mode, style;
|
5865
|
+
pos = clipPos(doc, pos);
|
5866
|
+
var line = getLine(doc, pos.line), state = getStateBefore(cm, pos.line, precise);
|
5867
|
+
var stream = new StringStream(line.text, cm.options.tabSize), tokens;
|
5868
|
+
if (asArray) tokens = [];
|
5869
|
+
while ((asArray || stream.pos < pos.ch) && !stream.eol()) {
|
5870
|
+
stream.start = stream.pos;
|
5871
|
+
style = readToken(mode, stream, state);
|
5872
|
+
if (asArray) tokens.push(getObj(true));
|
5873
|
+
}
|
5874
|
+
return asArray ? tokens : getObj();
|
5875
|
+
}
|
5876
|
+
|
5805
5877
|
// Run the given mode's parser over a line, calling f for each token.
|
5806
5878
|
function runMode(cm, text, mode, state, f, lineClasses, forceToEnd) {
|
5807
5879
|
var flattenSpans = mode.flattenSpans;
|
5808
5880
|
if (flattenSpans == null) flattenSpans = cm.options.flattenSpans;
|
5809
5881
|
var curStart = 0, curStyle = null;
|
5810
5882
|
var stream = new StringStream(text, cm.options.tabSize), style;
|
5883
|
+
var inner = cm.options.addModeClass && [null];
|
5811
5884
|
if (text == "") extractLineClasses(callBlankLine(mode, state), lineClasses);
|
5812
5885
|
while (!stream.eol()) {
|
5813
5886
|
if (stream.pos > cm.options.maxHighlightLength) {
|
@@ -5816,10 +5889,10 @@
|
|
5816
5889
|
stream.pos = text.length;
|
5817
5890
|
style = null;
|
5818
5891
|
} else {
|
5819
|
-
style = extractLineClasses(readToken(mode, stream, state), lineClasses);
|
5892
|
+
style = extractLineClasses(readToken(mode, stream, state, inner), lineClasses);
|
5820
5893
|
}
|
5821
|
-
if (
|
5822
|
-
var mName =
|
5894
|
+
if (inner) {
|
5895
|
+
var mName = inner[0].name;
|
5823
5896
|
if (mName) style = "m-" + (style ? mName + " " + style : mName);
|
5824
5897
|
}
|
5825
5898
|
if (!flattenSpans || curStyle != style) {
|
@@ -5878,12 +5951,13 @@
|
|
5878
5951
|
return {styles: st, classes: lineClasses.bgClass || lineClasses.textClass ? lineClasses : null};
|
5879
5952
|
}
|
5880
5953
|
|
5881
|
-
function getLineStyles(cm, line) {
|
5954
|
+
function getLineStyles(cm, line, updateFrontier) {
|
5882
5955
|
if (!line.styles || line.styles[0] != cm.state.modeGen) {
|
5883
5956
|
var result = highlightLine(cm, line, line.stateAfter = getStateBefore(cm, lineNo(line)));
|
5884
5957
|
line.styles = result.styles;
|
5885
5958
|
if (result.classes) line.styleClasses = result.classes;
|
5886
5959
|
else if (line.styleClasses) line.styleClasses = null;
|
5960
|
+
if (updateFrontier === cm.doc.frontier) cm.doc.frontier++;
|
5887
5961
|
}
|
5888
5962
|
return line.styles;
|
5889
5963
|
}
|
@@ -5938,7 +6012,8 @@
|
|
5938
6012
|
if (hasBadBidiRects(cm.display.measure) && (order = getOrder(line)))
|
5939
6013
|
builder.addToken = buildTokenBadBidi(builder.addToken, order);
|
5940
6014
|
builder.map = [];
|
5941
|
-
|
6015
|
+
var allowFrontierUpdate = lineView != cm.display.externalMeasured && lineNo(line);
|
6016
|
+
insertLineContent(line, builder, getLineStyles(cm, line, allowFrontierUpdate));
|
5942
6017
|
if (line.styleClasses) {
|
5943
6018
|
if (line.styleClasses.bgClass)
|
5944
6019
|
builder.bgClass = joinClasses(line.styleClasses.bgClass, builder.bgClass || "");
|
@@ -5960,9 +6035,14 @@
|
|
5960
6035
|
}
|
5961
6036
|
}
|
5962
6037
|
|
6038
|
+
// See issue #2901
|
6039
|
+
if (webkit && /\bcm-tab\b/.test(builder.content.lastChild.className))
|
6040
|
+
builder.content.className = "cm-tab-wrap-hack";
|
6041
|
+
|
5963
6042
|
signal(cm, "renderLine", cm, lineView.line, builder.pre);
|
5964
6043
|
if (builder.pre.className)
|
5965
6044
|
builder.textClass = joinClasses(builder.pre.className, builder.textClass || "");
|
6045
|
+
|
5966
6046
|
return builder;
|
5967
6047
|
}
|
5968
6048
|
|
@@ -6531,22 +6611,26 @@
|
|
6531
6611
|
},
|
6532
6612
|
|
6533
6613
|
addLineClass: docMethodOp(function(handle, where, cls) {
|
6534
|
-
return changeLine(this, handle, "class", function(line) {
|
6535
|
-
var prop = where == "text" ? "textClass"
|
6614
|
+
return changeLine(this, handle, where == "gutter" ? "gutter" : "class", function(line) {
|
6615
|
+
var prop = where == "text" ? "textClass"
|
6616
|
+
: where == "background" ? "bgClass"
|
6617
|
+
: where == "gutter" ? "gutterClass" : "wrapClass";
|
6536
6618
|
if (!line[prop]) line[prop] = cls;
|
6537
|
-
else if (
|
6619
|
+
else if (classTest(cls).test(line[prop])) return false;
|
6538
6620
|
else line[prop] += " " + cls;
|
6539
6621
|
return true;
|
6540
6622
|
});
|
6541
6623
|
}),
|
6542
6624
|
removeLineClass: docMethodOp(function(handle, where, cls) {
|
6543
6625
|
return changeLine(this, handle, "class", function(line) {
|
6544
|
-
var prop = where == "text" ? "textClass"
|
6626
|
+
var prop = where == "text" ? "textClass"
|
6627
|
+
: where == "background" ? "bgClass"
|
6628
|
+
: where == "gutter" ? "gutterClass" : "wrapClass";
|
6545
6629
|
var cur = line[prop];
|
6546
6630
|
if (!cur) return false;
|
6547
6631
|
else if (cls == null) line[prop] = null;
|
6548
6632
|
else {
|
6549
|
-
var found = cur.match(
|
6633
|
+
var found = cur.match(classTest(cls));
|
6550
6634
|
if (!found) return false;
|
6551
6635
|
var end = found.index + found[0].length;
|
6552
6636
|
line[prop] = cur.slice(0, found.index) + (!found.index || end == cur.length ? "" : " ") + cur.slice(end) || null;
|
@@ -7165,6 +7249,8 @@
|
|
7165
7249
|
// registering a (non-DOM) handler on the editor for the event name,
|
7166
7250
|
// and preventDefault-ing the event in that handler.
|
7167
7251
|
function signalDOMEvent(cm, e, override) {
|
7252
|
+
if (typeof e == "string")
|
7253
|
+
e = {type: e, preventDefault: function() { this.defaultPrevented = true; }};
|
7168
7254
|
signal(cm, override || e.type, cm, e);
|
7169
7255
|
return e_defaultPrevented(e) || e.codemirrorIgnore;
|
7170
7256
|
}
|
@@ -7338,7 +7424,8 @@
|
|
7338
7424
|
};
|
7339
7425
|
else range = function(node, start, end) {
|
7340
7426
|
var r = document.body.createTextRange();
|
7341
|
-
r.moveToElementText(node.parentNode);
|
7427
|
+
try { r.moveToElementText(node.parentNode); }
|
7428
|
+
catch(e) { return r; }
|
7342
7429
|
r.collapse(true);
|
7343
7430
|
r.moveEnd("character", end);
|
7344
7431
|
r.moveStart("character", start);
|
@@ -7370,14 +7457,19 @@
|
|
7370
7457
|
catch(e) { return document.body; }
|
7371
7458
|
};
|
7372
7459
|
|
7373
|
-
function classTest(cls) { return new RegExp("
|
7374
|
-
|
7375
|
-
var
|
7376
|
-
|
7377
|
-
|
7378
|
-
|
7379
|
-
|
7380
|
-
|
7460
|
+
function classTest(cls) { return new RegExp("(^|\\s)" + cls + "(?:$|\\s)\\s*"); }
|
7461
|
+
var rmClass = CodeMirror.rmClass = function(node, cls) {
|
7462
|
+
var current = node.className;
|
7463
|
+
var match = classTest(cls).exec(current);
|
7464
|
+
if (match) {
|
7465
|
+
var after = current.slice(match.index + match[0].length);
|
7466
|
+
node.className = current.slice(0, match.index) + (after ? match[1] + after : "");
|
7467
|
+
}
|
7468
|
+
};
|
7469
|
+
var addClass = CodeMirror.addClass = function(node, cls) {
|
7470
|
+
var current = node.className;
|
7471
|
+
if (!classTest(cls).test(current)) node.className += (current ? " " : "") + cls;
|
7472
|
+
};
|
7381
7473
|
function joinClasses(a, b) {
|
7382
7474
|
var as = a.split(" ");
|
7383
7475
|
for (var i = 0; i < as.length; i++)
|
@@ -7824,7 +7916,7 @@
|
|
7824
7916
|
|
7825
7917
|
// THE END
|
7826
7918
|
|
7827
|
-
CodeMirror.version = "4.
|
7919
|
+
CodeMirror.version = "4.8.0";
|
7828
7920
|
|
7829
7921
|
return CodeMirror;
|
7830
7922
|
});
|