| @@ -1,7 +1,7 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: https://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| // This is CodeMirror (https://codemirror.net), a code editor | |||
| // This is CodeMirror (https://codemirror.net/5), a code editor | |||
| // implemented in JavaScript on top of the browser's DOM. | |||
| // | |||
| // You can find some technical background for some of the code below | |||
| @@ -26,7 +26,8 @@ | |||
| var ie_version = ie && (ie_upto10 ? document.documentMode || 6 : +(edge || ie_11up)[1]); | |||
| var webkit = !edge && /WebKit\//.test(userAgent); | |||
| var qtwebkit = webkit && /Qt\/\d+\.\d+/.test(userAgent); | |||
| var chrome = !edge && /Chrome\//.test(userAgent); | |||
| var chrome = !edge && /Chrome\/(\d+)/.exec(userAgent); | |||
| var chrome_version = chrome && +chrome[1]; | |||
| var presto = /Opera\//.test(userAgent); | |||
| var safari = /Apple Computer/.test(navigator.vendor); | |||
| var mac_geMountainLion = /Mac OS X 1\d\D([8-9]|\d\d)\D/.test(userAgent); | |||
| @@ -111,15 +112,15 @@ | |||
| } while (child = child.parentNode) | |||
| } | |||
| function activeElt() { | |||
| function activeElt(doc) { | |||
| // IE and Edge may throw an "Unspecified Error" when accessing document.activeElement. | |||
| // IE < 10 will throw when accessed while the page is loading or in an iframe. | |||
| // IE > 9 and Edge will throw when accessed in an iframe if document.body is unavailable. | |||
| var activeElement; | |||
| try { | |||
| activeElement = document.activeElement; | |||
| activeElement = doc.activeElement; | |||
| } catch(e) { | |||
| activeElement = document.body || null; | |||
| activeElement = doc.body || null; | |||
| } | |||
| while (activeElement && activeElement.shadowRoot && activeElement.shadowRoot.activeElement) | |||
| { activeElement = activeElement.shadowRoot.activeElement; } | |||
| @@ -143,6 +144,10 @@ | |||
| else if (ie) // Suppress mysterious IE10 errors | |||
| { selectInput = function(node) { try { node.select(); } catch(_e) {} }; } | |||
| function doc(cm) { return cm.display.wrapper.ownerDocument } | |||
| function win(cm) { return doc(cm).defaultView } | |||
| function bind(f) { | |||
| var args = Array.prototype.slice.call(arguments, 1); | |||
| return function(){return f.apply(null, args)} | |||
| @@ -1543,7 +1548,7 @@ | |||
| var toCmp = cmp(found.to, to) || extraRight(sp.marker) - extraRight(marker); | |||
| if (fromCmp >= 0 && toCmp <= 0 || fromCmp <= 0 && toCmp >= 0) { continue } | |||
| if (fromCmp <= 0 && (sp.marker.inclusiveRight && marker.inclusiveLeft ? cmp(found.to, from) >= 0 : cmp(found.to, from) > 0) || | |||
| FROMCmp >= 0 && (sp.marker.inclusiveRight && marker.inclusiveLeft ? cmp(found.from, to) <= 0 : cmp(found.from, to) < 0)) | |||
| fromCmp >= 0 && (sp.marker.inclusiveRight && marker.inclusiveLeft ? cmp(found.from, to) <= 0 : cmp(found.from, to) < 0)) | |||
| { return true } | |||
| } } | |||
| } | |||
| @@ -2572,16 +2577,16 @@ | |||
| cm.display.lineNumChars = null; | |||
| } | |||
| function pageScrollX() { | |||
| function pageScrollX(doc) { | |||
| // Work around https://bugs.chromium.org/p/chromium/issues/detail?id=489206 | |||
| // which causes page_Offset and bounding client rects to use | |||
| // different reference viewports and invalidate our calculations. | |||
| if (chrome && android) { return -(document.body.getBoundingClientRect().left - parseInt(getComputedStyle(document.body).marginLeft)) } | |||
| return window.pageXOffset || (document.documentElement || document.body).scrollLeft | |||
| if (chrome && android) { return -(doc.body.getBoundingClientRect().left - parseInt(getComputedStyle(doc.body).marginLeft)) } | |||
| return doc.defaultView.pageXOffset || (doc.documentElement || doc.body).scrollLeft | |||
| } | |||
| function pageScrollY() { | |||
| if (chrome && android) { return -(document.body.getBoundingClientRect().top - parseInt(getComputedStyle(document.body).marginTop)) } | |||
| return window.pageYOffset || (document.documentElement || document.body).scrollTop | |||
| function pageScrollY(doc) { | |||
| if (chrome && android) { return -(doc.body.getBoundingClientRect().top - parseInt(getComputedStyle(doc.body).marginTop)) } | |||
| return doc.defaultView.pageYOffset || (doc.documentElement || doc.body).scrollTop | |||
| } | |||
| function widgetTopHeight(lineObj) { | |||
| @@ -2609,8 +2614,8 @@ | |||
| else { yOff -= cm.display.viewOffset; } | |||
| if (context == "page" || context == "window") { | |||
| var lOff = cm.display.lineSpace.getBoundingClientRect(); | |||
| yOff += lOff.top + (context == "window" ? 0 : pageScrollY()); | |||
| var xOff = lOff.left + (context == "window" ? 0 : pageScrollX()); | |||
| yOff += lOff.top + (context == "window" ? 0 : pageScrollY(doc(cm))); | |||
| var xOff = lOff.left + (context == "window" ? 0 : pageScrollX(doc(cm))); | |||
| rect.left += xOff; rect.right += xOff; | |||
| } | |||
| rect.top += yOff; rect.bottom += yOff; | |||
| @@ -2624,8 +2629,8 @@ | |||
| var left = coords.left, top = coords.top; | |||
| // First move into "page" coordinate system | |||
| if (context == "page") { | |||
| left -= pageScrollX(); | |||
| top -= pageScrollY(); | |||
| left -= pageScrollX(doc(cm)); | |||
| top -= pageScrollY(doc(cm)); | |||
| } else if (context == "local" || !context) { | |||
| var localBox = cm.display.sizer.getBoundingClientRect(); | |||
| left += localBox.left; | |||
| @@ -3423,10 +3428,10 @@ | |||
| if (viewport && viewport.ensure) { | |||
| var ensureFrom = viewport.ensure.from.line, ensureTo = viewport.ensure.to.line; | |||
| if (ensureFrom < from) { | |||
| FROM = ensureFrom; | |||
| from = ensureFrom; | |||
| to = lineAtHeight(doc, heightAtLine(getLine(doc, ensureFrom)) + display.wrapper.clientHeight); | |||
| } else if (Math.min(ensureTo, doc.lastLine()) >= to) { | |||
| FROM = lineAtHeight(doc, heightAtLine(getLine(doc, ensureTo)) - display.wrapper.clientHeight); | |||
| from = lineAtHeight(doc, heightAtLine(getLine(doc, ensureTo)) - display.wrapper.clientHeight); | |||
| to = ensureTo; | |||
| } | |||
| } | |||
| @@ -3441,8 +3446,9 @@ | |||
| if (signalDOMEvent(cm, "scrollCursorIntoView")) { return } | |||
| var display = cm.display, box = display.sizer.getBoundingClientRect(), doScroll = null; | |||
| var doc = display.wrapper.ownerDocument; | |||
| if (rect.top + box.top < 0) { doScroll = true; } | |||
| else if (rect.bottom + box.top > (window.innerHeight || document.documentElement.clientHeight)) { doScroll = false; } | |||
| else if (rect.bottom + box.top > (doc.defaultView.innerHeight || doc.documentElement.clientHeight)) { doScroll = false; } | |||
| if (doScroll != null && !phantom) { | |||
| var scrollNode = elt("div", "\u200b", null, ("position: absolute;\n top: " + (rect.top - display.viewOffset - paddingTop(cm.display)) + "px;\n height: " + (rect.bottom - rect.top + scrollGap(cm) + display.barHeight) + "px;\n left: " + (rect.left) + "px; width: " + (Math.max(2, rect.right - rect.left)) + "px;")); | |||
| cm.display.lineSpace.appendChild(scrollNode); | |||
| @@ -3696,13 +3702,13 @@ | |||
| NativeScrollbars.prototype.zeroWidthHack = function () { | |||
| var w = mac && !mac_geMountainLion ? "12px" : "18px"; | |||
| this.horiz.style.height = this.vert.style.width = w; | |||
| this.horiz.style.pointerEvents = this.vert.style.pointerEvents = "none"; | |||
| this.horiz.style.visibility = this.vert.style.visibility = "hidden"; | |||
| this.disableHoriz = new Delayed; | |||
| this.disableVert = new Delayed; | |||
| }; | |||
| NativeScrollbars.prototype.enableZeroWidthBar = function (bar, delay, type) { | |||
| bar.style.pointerEvents = "auto"; | |||
| bar.style.visibility = ""; | |||
| function maybeDisable() { | |||
| // To find out whether the scrollbar is still visible, we | |||
| // check whether the element under the pixel in the bottom | |||
| @@ -3713,7 +3719,7 @@ | |||
| var box = bar.getBoundingClientRect(); | |||
| var elt = type == "vert" ? document.elementFromPoint(box.right - 1, (box.top + box.bottom) / 2) | |||
| : document.elementFromPoint((box.right + box.left) / 2, box.bottom - 1); | |||
| if (elt != bar) { bar.style.pointerEvents = "none"; } | |||
| if (elt != bar) { bar.style.visibility = "hidden"; } | |||
| else { delay.set(1000, maybeDisable); } | |||
| } | |||
| delay.set(1000, maybeDisable); | |||
| @@ -3894,7 +3900,7 @@ | |||
| cm.display.maxLineChanged = false; | |||
| } | |||
| var takeFocus = op.focus && op.focus == activeElt(); | |||
| var takeFocus = op.focus && op.focus == activeElt(doc(cm)); | |||
| if (op.preparedSelection) | |||
| { cm.display.input.showSelection(op.preparedSelection, takeFocus); } | |||
| if (op.updatedDisplay || op.startHeight != cm.doc.height) | |||
| @@ -4071,11 +4077,11 @@ | |||
| function selectionSnapshot(cm) { | |||
| if (cm.hasFocus()) { return null } | |||
| var active = activeElt(); | |||
| var active = activeElt(doc(cm)); | |||
| if (!active || !contains(cm.display.lineDiv, active)) { return null } | |||
| var result = {activeElt: active}; | |||
| if (window.getSelection) { | |||
| var sel = window.getSelection(); | |||
| var sel = win(cm).getSelection(); | |||
| if (sel.anchorNode && sel.extend && contains(cm.display.lineDiv, sel.anchorNode)) { | |||
| result.anchorNode = sel.anchorNode; | |||
| result.anchorOffset = sel.anchorOffset; | |||
| @@ -4087,11 +4093,12 @@ | |||
| } | |||
| function restoreSelection(snapshot) { | |||
| if (!snapshot || !snapshot.activeElt || snapshot.activeElt == activeElt()) { return } | |||
| if (!snapshot || !snapshot.activeElt || snapshot.activeElt == activeElt(snapshot.activeElt.ownerDocument)) { return } | |||
| snapshot.activeElt.focus(); | |||
| if (!/^(INPUT|TEXTAREA)$/.test(snapshot.activeElt.nodeName) && | |||
| snapshot.anchorNode && contains(document.body, snapshot.anchorNode) && contains(document.body, snapshot.focusNode)) { | |||
| var sel = window.getSelection(), range = document.createRange(); | |||
| var doc = snapshot.activeElt.ownerDocument; | |||
| var sel = doc.defaultView.getSelection(), range = doc.createRange(); | |||
| range.setEnd(snapshot.anchorNode, snapshot.anchorOffset); | |||
| range.collapse(false); | |||
| sel.removeAllRanges(); | |||
| @@ -4130,7 +4137,7 @@ | |||
| if (display.viewFrom < from && from - display.viewFrom < 20) { from = Math.max(doc.first, display.viewFrom); } | |||
| if (display.viewTo > to && display.viewTo - to < 20) { to = Math.min(end, display.viewTo); } | |||
| if (sawCollapsedSpans) { | |||
| FROM = visualLineNo(cm.doc, from); | |||
| from = visualLineNo(cm.doc, from); | |||
| to = visualLineEndNo(cm.doc, to); | |||
| } | |||
| @@ -4408,6 +4415,8 @@ | |||
| d.scroller.setAttribute("tabIndex", "-1"); | |||
| // The element in which the editor lives. | |||
| d.wrapper = elt("div", [d.scrollbarFiller, d.gutterFiller, d.scroller], "CodeMirror"); | |||
| // See #6982. FIXME remove when this has been fixed for a while in Chrome | |||
| if (chrome && chrome_version >= 105) { d.wrapper.style.clipPath = "inset(0px)"; } | |||
| // This attribute is respected by automatic translation systems such as Google Translate, | |||
| // and may also be respected by tools used by human translators. | |||
| @@ -4509,6 +4518,17 @@ | |||
| } | |||
| function onScrollWheel(cm, e) { | |||
| // On Chrome 102, viewport updates somehow stop wheel-based | |||
| // scrolling. Turning off pointer events during the scroll seems | |||
| // to avoid the issue. | |||
| if (chrome && chrome_version == 102) { | |||
| if (cm.display.chromeScrollHack == null) { cm.display.sizer.style.pointerEvents = "none"; } | |||
| else { clearTimeout(cm.display.chromeScrollHack); } | |||
| cm.display.chromeScrollHack = setTimeout(function () { | |||
| cm.display.chromeScrollHack = null; | |||
| cm.display.sizer.style.pointerEvents = ""; | |||
| }, 100); | |||
| } | |||
| var delta = wheelEventDelta(e), dx = delta.x, dy = delta.y; | |||
| var pixelsPerUnit = wheelPixelsPerUnit; | |||
| if (e.deltaMode === 0) { | |||
| @@ -5192,7 +5212,7 @@ | |||
| var range = sel.ranges[i]; | |||
| var old = sel.ranges.length == doc.sel.ranges.length && doc.sel.ranges[i]; | |||
| var newAnchor = skipAtomic(doc, range.anchor, old && old.anchor, bias, mayClear); | |||
| var newHead = skipAtomic(doc, range.head, old && old.head, bias, mayClear); | |||
| var newHead = range.head == range.anchor ? newAnchor : skipAtomic(doc, range.head, old && old.head, bias, mayClear); | |||
| if (out || newAnchor != range.anchor || newHead != range.head) { | |||
| if (!out) { out = sel.ranges.slice(0, i); } | |||
| out[i] = new Range(newAnchor, newHead); | |||
| @@ -5276,7 +5296,7 @@ | |||
| function filterChange(doc, change, update) { | |||
| var obj = { | |||
| canceled: false, | |||
| FROM: change.from, | |||
| from: change.from, | |||
| to: change.to, | |||
| text: change.text, | |||
| origin: change.origin, | |||
| @@ -5515,7 +5535,7 @@ | |||
| var changesHandler = hasHandler(cm, "changes"), changeHandler = hasHandler(cm, "change"); | |||
| if (changeHandler || changesHandler) { | |||
| var obj = { | |||
| FROM: from, to: to, | |||
| from: from, to: to, | |||
| text: change.text, | |||
| removed: change.removed, | |||
| origin: change.origin | |||
| @@ -5911,7 +5931,7 @@ | |||
| var line = this.lines[i]; | |||
| var span = getMarkedSpanFor(line.markedSpans, this); | |||
| if (span.from != null) { | |||
| FROM = Pos(lineObj ? line : lineNo(line), span.from); | |||
| from = Pos(lineObj ? line : lineNo(line), span.from); | |||
| if (side == -1) { return from } | |||
| } | |||
| if (span.to != null) { | |||
| @@ -5989,7 +6009,7 @@ | |||
| } | |||
| if (marker.collapsed) { | |||
| if (conflictingCollapsedRange(doc, from.line, from, to, marker) || | |||
| FROM.line != to.line && conflictingCollapsedRange(doc, to.line, from, to, marker)) | |||
| from.line != to.line && conflictingCollapsedRange(doc, to.line, from, to, marker)) | |||
| { throw new Error("Inserting collapsed marker partially overlapping an existing one") } | |||
| seeCollapsedSpans(); | |||
| } | |||
| @@ -6169,7 +6189,7 @@ | |||
| setSelection(this, simpleSelection(top), sel_dontScroll); | |||
| }), | |||
| replaceRange: function(code, from, to, origin) { | |||
| FROM = clipPos(this, from); | |||
| from = clipPos(this, from); | |||
| to = to ? clipPos(this, to) : from; | |||
| replaceRange(this, code, from, to, origin); | |||
| }, | |||
| @@ -6413,7 +6433,7 @@ | |||
| return markers | |||
| }, | |||
| findMarks: function(from, to, filter) { | |||
| FROM = clipPos(this, from); to = clipPos(this, to); | |||
| from = clipPos(this, from); to = clipPos(this, to); | |||
| var found = [], lineNo = from.line; | |||
| this.iter(from.line, to.line + 1, function (line) { | |||
| var spans = line.markedSpans; | |||
| @@ -6997,11 +7017,11 @@ | |||
| } | |||
| }); }, | |||
| deleteLine: function (cm) { return deleteNearSelection(cm, function (range) { return ({ | |||
| FROM: Pos(range.from().line, 0), | |||
| from: Pos(range.from().line, 0), | |||
| to: clipPos(cm.doc, Pos(range.to().line + 1, 0)) | |||
| }); }); }, | |||
| delLineLeft: function (cm) { return deleteNearSelection(cm, function (range) { return ({ | |||
| FROM: Pos(range.from().line, 0), to: range.from() | |||
| from: Pos(range.from().line, 0), to: range.from() | |||
| }); }); }, | |||
| delWrappedLineLeft: function (cm) { return deleteNearSelection(cm, function (range) { | |||
| var top = cm.charCoords(range.head, "div").top + 5; | |||
| @@ -7244,7 +7264,7 @@ | |||
| function onKeyDown(e) { | |||
| var cm = this; | |||
| if (e.target && e.target != cm.display.input.getField()) { return } | |||
| cm.curOp.focus = activeElt(); | |||
| cm.curOp.focus = activeElt(doc(cm)); | |||
| if (signalDOMEvent(cm, e)) { return } | |||
| // IE does strange things with escape. | |||
| if (ie && ie_version < 11 && e.keyCode == 27) { e.returnValue = false; } | |||
| @@ -7351,7 +7371,7 @@ | |||
| } | |||
| if (clickInGutter(cm, e)) { return } | |||
| var pos = posFromMouse(cm, e), button = e_button(e), repeat = pos ? clickRepeat(pos, button) : "single"; | |||
| window.focus(); | |||
| win(cm).focus(); | |||
| // #3261: make sure, that we're not starting a second selection | |||
| if (button == 1 && cm.state.selectingText) | |||
| @@ -7406,7 +7426,7 @@ | |||
| function leftButtonDown(cm, pos, repeat, event) { | |||
| if (ie) { setTimeout(bind(ensureFocus, cm), 0); } | |||
| else { cm.curOp.focus = activeElt(); } | |||
| else { cm.curOp.focus = activeElt(doc(cm)); } | |||
| var behavior = configureMouse(cm, repeat, event); | |||
| @@ -7476,19 +7496,19 @@ | |||
| // Normal selection, as opposed to text dragging. | |||
| function leftButtonSelect(cm, event, start, behavior) { | |||
| if (ie) { delayBlurEvent(cm); } | |||
| var display = cm.display, doc = cm.doc; | |||
| var display = cm.display, doc$1 = cm.doc; | |||
| e_preventDefault(event); | |||
| var ourRange, ourIndex, startSel = doc.sel, ranges = startSel.ranges; | |||
| var ourRange, ourIndex, startSel = doc$1.sel, ranges = startSel.ranges; | |||
| if (behavior.addNew && !behavior.extend) { | |||
| ourIndex = doc.sel.contains(start); | |||
| ourIndex = doc$1.sel.contains(start); | |||
| if (ourIndex > -1) | |||
| { ourRange = ranges[ourIndex]; } | |||
| else | |||
| { ourRange = new Range(start, start); } | |||
| } else { | |||
| ourRange = doc.sel.primary(); | |||
| ourIndex = doc.sel.primIndex; | |||
| ourRange = doc$1.sel.primary(); | |||
| ourIndex = doc$1.sel.primIndex; | |||
| } | |||
| if (behavior.unit == "rectangle") { | |||
| @@ -7505,18 +7525,18 @@ | |||
| if (!behavior.addNew) { | |||
| ourIndex = 0; | |||
| setSelection(doc, new Selection([ourRange], 0), sel_mouse); | |||
| startSel = doc.sel; | |||
| setSelection(doc$1, new Selection([ourRange], 0), sel_mouse); | |||
| startSel = doc$1.sel; | |||
| } else if (ourIndex == -1) { | |||
| ourIndex = ranges.length; | |||
| setSelection(doc, normalizeSelection(cm, ranges.concat([ourRange]), ourIndex), | |||
| setSelection(doc$1, normalizeSelection(cm, ranges.concat([ourRange]), ourIndex), | |||
| {scroll: false, origin: "*mouse"}); | |||
| } else if (ranges.length > 1 && ranges[ourIndex].empty() && behavior.unit == "char" && !behavior.extend) { | |||
| setSelection(doc, normalizeSelection(cm, ranges.slice(0, ourIndex).concat(ranges.slice(ourIndex + 1)), 0), | |||
| setSelection(doc$1, normalizeSelection(cm, ranges.slice(0, ourIndex).concat(ranges.slice(ourIndex + 1)), 0), | |||
| {scroll: false, origin: "*mouse"}); | |||
| startSel = doc.sel; | |||
| startSel = doc$1.sel; | |||
| } else { | |||
| replaceOneSelection(doc, ourIndex, ourRange, sel_mouse); | |||
| replaceOneSelection(doc$1, ourIndex, ourRange, sel_mouse); | |||
| } | |||
| var lastPos = start; | |||
| @@ -7526,19 +7546,19 @@ | |||
| if (behavior.unit == "rectangle") { | |||
| var ranges = [], tabSize = cm.options.tabSize; | |||
| var startCol = countColumn(getLine(doc, start.line).text, start.ch, tabSize); | |||
| var posCol = countColumn(getLine(doc, pos.line).text, pos.ch, tabSize); | |||
| var startCol = countColumn(getLine(doc$1, start.line).text, start.ch, tabSize); | |||
| var posCol = countColumn(getLine(doc$1, pos.line).text, pos.ch, tabSize); | |||
| var left = Math.min(startCol, posCol), right = Math.max(startCol, posCol); | |||
| for (var line = Math.min(start.line, pos.line), end = Math.min(cm.lastLine(), Math.max(start.line, pos.line)); | |||
| line <= end; line++) { | |||
| var text = getLine(doc, line).text, leftPos = findColumn(text, left, tabSize); | |||
| var text = getLine(doc$1, line).text, leftPos = findColumn(text, left, tabSize); | |||
| if (left == right) | |||
| { ranges.push(new Range(Pos(line, leftPos), Pos(line, leftPos))); } | |||
| else if (text.length > leftPos) | |||
| { ranges.push(new Range(Pos(line, leftPos), Pos(line, findColumn(text, right, tabSize)))); } | |||
| } | |||
| if (!ranges.length) { ranges.push(new Range(start, start)); } | |||
| setSelection(doc, normalizeSelection(cm, startSel.ranges.slice(0, ourIndex).concat(ranges), ourIndex), | |||
| setSelection(doc$1, normalizeSelection(cm, startSel.ranges.slice(0, ourIndex).concat(ranges), ourIndex), | |||
| {origin: "*mouse", scroll: false}); | |||
| cm.scrollIntoView(pos); | |||
| } else { | |||
| @@ -7553,8 +7573,8 @@ | |||
| anchor = maxPos(oldRange.to(), range.head); | |||
| } | |||
| var ranges$1 = startSel.ranges.slice(0); | |||
| ranges$1[ourIndex] = bidiSimplify(cm, new Range(clipPos(doc, anchor), head)); | |||
| setSelection(doc, normalizeSelection(cm, ranges$1, ourIndex), sel_mouse); | |||
| ranges$1[ourIndex] = bidiSimplify(cm, new Range(clipPos(doc$1, anchor), head)); | |||
| setSelection(doc$1, normalizeSelection(cm, ranges$1, ourIndex), sel_mouse); | |||
| } | |||
| } | |||
| @@ -7570,9 +7590,9 @@ | |||
| var cur = posFromMouse(cm, e, true, behavior.unit == "rectangle"); | |||
| if (!cur) { return } | |||
| if (cmp(cur, lastPos) != 0) { | |||
| cm.curOp.focus = activeElt(); | |||
| cm.curOp.focus = activeElt(doc(cm)); | |||
| extendTo(cur); | |||
| var visible = visibleLines(display, doc); | |||
| var visible = visibleLines(display, doc$1); | |||
| if (cur.line >= visible.to || cur.line < visible.from) | |||
| { setTimeout(operation(cm, function () {if (counter == curCount) { extend(e); }}), 150); } | |||
| } else { | |||
| @@ -7597,7 +7617,7 @@ | |||
| } | |||
| off(display.wrapper.ownerDocument, "mousemove", move); | |||
| off(display.wrapper.ownerDocument, "mouseup", up); | |||
| doc.history.lastSelOrigin = null; | |||
| doc$1.history.lastSelOrigin = null; | |||
| } | |||
| var move = operation(cm, function (e) { | |||
| @@ -7754,7 +7774,7 @@ | |||
| for (var i = newBreaks.length - 1; i >= 0; i--) | |||
| { replaceRange(cm.doc, val, newBreaks[i], Pos(newBreaks[i].line, newBreaks[i].ch + val.length)); } | |||
| }); | |||
| option("specialChars", /[\u0000-\u001f\u007f-\u009f\u00ad\u061c\u200b\u200e\u200f\u2028\u2029\ufeff\ufff9-\ufffc]/g, function (cm, val, old) { | |||
| option("specialChars", /[\u0000-\u001f\u007f-\u009f\u00ad\u061c\u200b\u200e\u200f\u2028\u2029\u202d\u202e\u2066\u2067\u2069\ufeff\ufff9-\ufffc]/g, function (cm, val, old) { | |||
| cm.state.specialChars = new RegExp(val.source + (val.test("\t") ? "" : "|\t"), "g"); | |||
| if (old != Init) { cm.refresh(); } | |||
| }); | |||
| @@ -8197,7 +8217,7 @@ | |||
| var pasted = e.clipboardData && e.clipboardData.getData("Text"); | |||
| if (pasted) { | |||
| e.preventDefault(); | |||
| if (!cm.isReadOnly() && !cm.options.disableInput) | |||
| if (!cm.isReadOnly() && !cm.options.disableInput && cm.hasFocus()) | |||
| { runInOp(cm, function () { return applyTextInput(cm, pasted, 0, null, "paste"); }); } | |||
| return true | |||
| } | |||
| @@ -8274,7 +8294,7 @@ | |||
| CodeMirror.prototype = { | |||
| constructor: CodeMirror, | |||
| focus: function(){window.focus(); this.display.input.focus();}, | |||
| focus: function(){win(this).focus(); this.display.input.focus();}, | |||
| setOption: function(option, value) { | |||
| var options = this.options, old = options[option]; | |||
| @@ -8598,7 +8618,7 @@ | |||
| signal(this, "overwriteToggle", this, this.state.overwrite); | |||
| }, | |||
| hasFocus: function() { return this.display.input.getField() == activeElt() }, | |||
| hasFocus: function() { return this.display.input.getField() == activeElt(doc(this)) }, | |||
| isReadOnly: function() { return !!(this.options.readOnly || this.doc.cantEdit) }, | |||
| scrollTo: methodOp(function (x, y) { scrollToCoords(this, x, y); }), | |||
| @@ -8779,7 +8799,7 @@ | |||
| function findPosV(cm, pos, dir, unit) { | |||
| var doc = cm.doc, x = pos.left, y; | |||
| if (unit == "page") { | |||
| var pageSize = Math.min(cm.display.wrapper.clientHeight, window.innerHeight || document.documentElement.clientHeight); | |||
| var pageSize = Math.min(cm.display.wrapper.clientHeight, win(cm).innerHeight || doc(cm).documentElement.clientHeight); | |||
| var moveAmount = Math.max(pageSize - .5 * textHeight(cm.display), 3); | |||
| y = (dir > 0 ? pos.bottom : pos.top) + dir * moveAmount; | |||
| @@ -8879,7 +8899,7 @@ | |||
| var kludge = hiddenTextarea(), te = kludge.firstChild; | |||
| cm.display.lineSpace.insertBefore(kludge, cm.display.lineSpace.firstChild); | |||
| te.value = lastCopied.text.join("\n"); | |||
| var hadFocus = activeElt(); | |||
| var hadFocus = activeElt(div.ownerDocument); | |||
| selectInput(te); | |||
| setTimeout(function () { | |||
| cm.display.lineSpace.removeChild(kludge); | |||
| @@ -8902,7 +8922,7 @@ | |||
| ContentEditableInput.prototype.prepareSelection = function () { | |||
| var result = prepareSelection(this.cm, false); | |||
| result.focus = activeElt() == this.div; | |||
| result.focus = activeElt(this.div.ownerDocument) == this.div; | |||
| return result | |||
| }; | |||
| @@ -8998,7 +9018,7 @@ | |||
| ContentEditableInput.prototype.focus = function () { | |||
| if (this.cm.options.readOnly != "nocursor") { | |||
| if (!this.selectionInEditor() || activeElt() != this.div) | |||
| if (!this.selectionInEditor() || activeElt(this.div.ownerDocument) != this.div) | |||
| { this.showSelection(this.prepareSelection(), true); } | |||
| this.div.focus(); | |||
| } | |||
| @@ -9073,11 +9093,11 @@ | |||
| var fromIndex, fromLine, fromNode; | |||
| if (from.line == display.viewFrom || (fromIndex = findViewIndex(cm, from.line)) == 0) { | |||
| FROMLine = lineNo(display.view[0].line); | |||
| FROMNode = display.view[0].node; | |||
| fromLine = lineNo(display.view[0].line); | |||
| fromNode = display.view[0].node; | |||
| } else { | |||
| FROMLine = lineNo(display.view[fromIndex].line); | |||
| FROMNode = display.view[fromIndex - 1].node.nextSibling; | |||
| fromLine = lineNo(display.view[fromIndex].line); | |||
| fromNode = display.view[fromIndex - 1].node.nextSibling; | |||
| } | |||
| var toIndex = findViewIndex(cm, to.line); | |||
| var toLine, toNode; | |||
| @@ -9254,7 +9274,7 @@ | |||
| for (;;) { | |||
| walk(from); | |||
| if (from == to) { break } | |||
| FROM = from.nextSibling; | |||
| from = from.nextSibling; | |||
| extraLinebreak = false; | |||
| } | |||
| return text | |||
| @@ -9350,6 +9370,7 @@ | |||
| // Used to work around IE issue with selection being forgotten when focus moves away from textarea | |||
| this.hasSelection = false; | |||
| this.composing = null; | |||
| this.resetting = false; | |||
| }; | |||
| TextareaInput.prototype.init = function (display) { | |||
| @@ -9482,8 +9503,9 @@ | |||
| // Reset the input to correspond to the selection (or to be empty, | |||
| // when not typing and nothing is selected) | |||
| TextareaInput.prototype.reset = function (typing) { | |||
| if (this.contextMenuPending || this.composing) { return } | |||
| if (this.contextMenuPending || this.composing && typing) { return } | |||
| var cm = this.cm; | |||
| this.resetting = true; | |||
| if (cm.somethingSelected()) { | |||
| this.prevInput = ""; | |||
| var content = cm.getSelection(); | |||
| @@ -9494,6 +9516,7 @@ | |||
| this.prevInput = this.textarea.value = ""; | |||
| if (ie && ie_version >= 9) { this.hasSelection = null; } | |||
| } | |||
| this.resetting = false; | |||
| }; | |||
| TextareaInput.prototype.getField = function () { return this.textarea }; | |||
| @@ -9501,7 +9524,7 @@ | |||
| TextareaInput.prototype.supportsTouch = function () { return false }; | |||
| TextareaInput.prototype.focus = function () { | |||
| if (this.cm.options.readOnly != "nocursor" && (!mobile || activeElt() != this.textarea)) { | |||
| if (this.cm.options.readOnly != "nocursor" && (!mobile || activeElt(this.textarea.ownerDocument) != this.textarea)) { | |||
| try { this.textarea.focus(); } | |||
| catch (e) {} // IE8 will throw if the textarea is display: none or not in DOM | |||
| } | |||
| @@ -9555,7 +9578,7 @@ | |||
| // possible when it is clear that nothing happened. hasSelection | |||
| // will be the case when there is a lot of text in the textarea, | |||
| // in which case reading its value would be expensive. | |||
| if (this.contextMenuPending || !cm.state.focused || | |||
| if (this.contextMenuPending || this.resetting || !cm.state.focused || | |||
| (hasSelection(input) && !prevInput && !this.composing) || | |||
| cm.isReadOnly() || cm.options.disableInput || cm.state.keySeq) | |||
| { return false } | |||
| @@ -9624,9 +9647,9 @@ | |||
| input.wrapper.style.cssText = "position: static"; | |||
| te.style.cssText = "position: absolute; width: 30px; height: 30px;\n top: " + (e.clientY - wrapperBox.top - 5) + "px; left: " + (e.clientX - wrapperBox.left - 5) + "px;\n z-index: 1000; background: " + (ie ? "rgba(255, 255, 255, .05)" : "transparent") + ";\n outline: none; border-width: 0; outline: none; overflow: hidden; opacity: .05; filter: alpha(opacity=5);"; | |||
| var oldScrollY; | |||
| if (webkit) { oldScrollY = window.scrollY; } // Work around Chrome issue (#2712) | |||
| if (webkit) { oldScrollY = te.ownerDocument.defaultView.scrollY; } // Work around Chrome issue (#2712) | |||
| display.input.focus(); | |||
| if (webkit) { window.scrollTo(null, oldScrollY); } | |||
| if (webkit) { te.ownerDocument.defaultView.scrollTo(null, oldScrollY); } | |||
| display.input.reset(); | |||
| // Adds "Select all" to context menu in FF | |||
| if (!cm.somethingSelected()) { te.value = input.prevInput = " "; } | |||
| @@ -9708,7 +9731,7 @@ | |||
| // Set autofocus to true if this textarea is focused, or if it has | |||
| // autofocus and no other element is focused. | |||
| if (options.autofocus == null) { | |||
| var hasFocus = activeElt(); | |||
| var hasFocus = activeElt(textarea.ownerDocument); | |||
| options.autofocus = hasFocus == textarea || | |||
| textarea.getAttribute("autofocus") != null && hasFocus == document.body; | |||
| } | |||
| @@ -9842,7 +9865,7 @@ | |||
| addLegacyProps(CodeMirror); | |||
| CodeMirror.version = "5.65.3"; | |||
| CodeMirror.version = "5.65.9"; | |||
| return CodeMirror; | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: https://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function(mod) { | |||
| if (typeof exports == "object" && typeof module == "object") // CommonJS | |||
| @@ -0,0 +1,165 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "text/x-c"); | |||
| function MT(name) { test.mode(name, mode, Array.prototype.slice.call(arguments, 1)); } | |||
| MT("indent", | |||
| "[type void] [def foo]([type void*] [variable a], [type int] [variable b]) {", | |||
| " [type int] [variable c] [operator =] [variable b] [operator +]", | |||
| " [number 1];", | |||
| " [keyword return] [operator *][variable a];", | |||
| "}"); | |||
| MT("indent_switch", | |||
| "[keyword switch] ([variable x]) {", | |||
| " [keyword case] [number 10]:", | |||
| " [keyword return] [number 20];", | |||
| " [keyword default]:", | |||
| " [variable printf]([string \"foo %c\"], [variable x]);", | |||
| "}"); | |||
| MT("def", | |||
| "[type void] [def foo]() {}", | |||
| "[keyword struct] [def bar]{}", | |||
| "[keyword enum] [def zot]{}", | |||
| "[keyword union] [def ugh]{}", | |||
| "[type int] [type *][def baz]() {}"); | |||
| MT("def_new_line", | |||
| "::[variable std]::[variable SomeTerribleType][operator <][variable T][operator >]", | |||
| "[def SomeLongMethodNameThatDoesntFitIntoOneLine]([keyword const] [variable MyType][operator &] [variable param]) {}") | |||
| MT("double_block", | |||
| "[keyword for] (;;)", | |||
| " [keyword for] (;;)", | |||
| " [variable x][operator ++];", | |||
| "[keyword return];"); | |||
| MT("preprocessor", | |||
| "[meta #define FOO 3]", | |||
| "[type int] [variable foo];", | |||
| "[meta #define BAR\\]", | |||
| "[meta 4]", | |||
| "[type unsigned] [type int] [variable bar] [operator =] [number 8];", | |||
| "[meta #include <baz> ][comment // comment]") | |||
| MT("c_underscores", | |||
| "[builtin __FOO];", | |||
| "[builtin _Complex];", | |||
| "[builtin __aName];", | |||
| "[variable _aName];"); | |||
| MT("c_types", | |||
| "[type int];", | |||
| "[type long];", | |||
| "[type char];", | |||
| "[type short];", | |||
| "[type double];", | |||
| "[type float];", | |||
| "[type unsigned];", | |||
| "[type signed];", | |||
| "[type void];", | |||
| "[type bool];", | |||
| "[type foo_t];", | |||
| "[variable foo_T];", | |||
| "[variable _t];"); | |||
| var mode_cpp = CodeMirror.getMode({indentUnit: 2}, "text/x-c++src"); | |||
| function MTCPP(name) { test.mode(name, mode_cpp, Array.prototype.slice.call(arguments, 1)); } | |||
| MTCPP("cpp14_literal", | |||
| "[number 10'000];", | |||
| "[number 0b10'000];", | |||
| "[number 0x10'000];", | |||
| "[string '100000'];"); | |||
| MTCPP("ctor_dtor", | |||
| "[def Foo::Foo]() {}", | |||
| "[def Foo::~Foo]() {}"); | |||
| MTCPP("cpp_underscores", | |||
| "[builtin __FOO];", | |||
| "[builtin _Complex];", | |||
| "[builtin __aName];", | |||
| "[variable _aName];"); | |||
| var mode_objc = CodeMirror.getMode({indentUnit: 2}, "text/x-objectivec"); | |||
| function MTOBJC(name) { test.mode(name, mode_objc, Array.prototype.slice.call(arguments, 1)); } | |||
| MTOBJC("objc_underscores", | |||
| "[builtin __FOO];", | |||
| "[builtin _Complex];", | |||
| "[builtin __aName];", | |||
| "[variable _aName];"); | |||
| MTOBJC("objc_interface", | |||
| "[keyword @interface] [def foo] {", | |||
| " [type int] [variable bar];", | |||
| "}", | |||
| "[keyword @property] ([keyword atomic], [keyword nullable]) [variable NSString][operator *] [variable a];", | |||
| "[keyword @property] ([keyword nonatomic], [keyword assign]) [type int] [variable b];", | |||
| "[operator -]([type instancetype])[variable initWithFoo]:([type int])[variable a] " + | |||
| "[builtin NS_DESIGNATED_INITIALIZER];", | |||
| "[keyword @end]"); | |||
| MTOBJC("objc_implementation", | |||
| "[keyword @implementation] [def foo] {", | |||
| " [type int] [variable bar];", | |||
| "}", | |||
| "[keyword @property] ([keyword readwrite]) [type SEL] [variable a];", | |||
| "[operator -]([type instancetype])[variable initWithFoo]:([type int])[variable a] {", | |||
| " [keyword if](([keyword self] [operator =] [[[keyword super] [variable init] ]])) {}", | |||
| " [keyword return] [keyword self];", | |||
| "}", | |||
| "[keyword @end]"); | |||
| MTOBJC("objc_types", | |||
| "[type int];", | |||
| "[type foo_t];", | |||
| "[variable foo_T];", | |||
| "[type id];", | |||
| "[type SEL];", | |||
| "[type instancetype];", | |||
| "[type Class];", | |||
| "[type Protocol];", | |||
| "[type BOOL];" | |||
| ); | |||
| var mode_scala = CodeMirror.getMode({indentUnit: 2}, "text/x-scala"); | |||
| function MTSCALA(name) { test.mode("scala_" + name, mode_scala, Array.prototype.slice.call(arguments, 1)); } | |||
| MTSCALA("nested_comments", | |||
| "[comment /*]", | |||
| "[comment But wait /* this is a nested comment */ for real]", | |||
| "[comment /**** let * me * show * you ****/]", | |||
| "[comment ///// let / me / show / you /////]", | |||
| "[comment */]"); | |||
| var mode_java = CodeMirror.getMode({indentUnit: 2}, "text/x-java"); | |||
| function MTJAVA(name) { test.mode("java_" + name, mode_java, Array.prototype.slice.call(arguments, 1)); } | |||
| MTJAVA("types", | |||
| "[type byte];", | |||
| "[type short];", | |||
| "[type int];", | |||
| "[type long];", | |||
| "[type float];", | |||
| "[type double];", | |||
| "[type boolean];", | |||
| "[type char];", | |||
| "[type void];", | |||
| "[type Boolean];", | |||
| "[type Byte];", | |||
| "[type Character];", | |||
| "[type Double];", | |||
| "[type Float];", | |||
| "[type Integer];", | |||
| "[type Long];", | |||
| "[type Number];", | |||
| "[type Object];", | |||
| "[type Short];", | |||
| "[type String];", | |||
| "[type StringBuffer];", | |||
| "[type StringBuilder];", | |||
| "[type Void];"); | |||
| })(); | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function(mod) { | |||
| if (typeof exports == "object" && typeof module == "object") // CommonJS | |||
| @@ -29,7 +29,8 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| valueKeywords = parserConfig.valueKeywords || {}, | |||
| allowNested = parserConfig.allowNested, | |||
| lineComment = parserConfig.lineComment, | |||
| supportsAtComponent = parserConfig.supportsAtComponent === true; | |||
| supportsAtComponent = parserConfig.supportsAtComponent === true, | |||
| highlightNonStandardPropertyKeywords = config.highlightNonStandardPropertyKeywords !== false; | |||
| var type, override; | |||
| function ret(style, tp) { type = tp; return style; } | |||
| @@ -63,7 +64,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| if (/[\d.]/.test(stream.peek())) { | |||
| stream.eatWhile(/[\w.%]/); | |||
| return ret("number", "unit"); | |||
| } else if (stream.match(/^-[\w\\\-]+/)) { | |||
| } else if (stream.match(/^-[\w\\\-]*/)) { | |||
| stream.eatWhile(/[\w\\\-]/); | |||
| if (stream.match(/^\s*:/, false)) | |||
| return ret("variable-2", "variable-definition"); | |||
| @@ -77,12 +78,11 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| return ret("qualifier", "qualifier"); | |||
| } else if (/[:;{}\[\]\(\)]/.test(ch)) { | |||
| return ret(null, ch); | |||
| } else if ((ch == "u" && stream.match(/rl(-prefix)?\(/)) || | |||
| (ch == "d" && stream.match("omain(")) || | |||
| (ch == "r" && stream.match("egexp("))) { | |||
| stream.backUp(1); | |||
| state.tokenize = tokenParenthesized; | |||
| return ret("property", "word"); | |||
| } else if (stream.match(/^[\w-.]+(?=\()/)) { | |||
| if (/^(url(-prefix)?|domain|regexp)$/i.test(stream.current())) { | |||
| state.tokenize = tokenParenthesized; | |||
| } | |||
| return ret("variable callee", "variable"); | |||
| } else if (/[\w\\\-]/.test(ch)) { | |||
| stream.eatWhile(/[\w\\\-]/); | |||
| return ret("property", "word"); | |||
| @@ -108,7 +108,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| function tokenParenthesized(stream, state) { | |||
| stream.next(); // Must be '(' | |||
| if (!stream.match(/\s*[\"\')]/, false)) | |||
| if (!stream.match(/^\s*[\"\')]/, false)) | |||
| state.tokenize = tokenString(")"); | |||
| else | |||
| state.tokenize = null; | |||
| @@ -162,16 +162,16 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| return pushContext(state, stream, "block"); | |||
| } else if (type == "}" && state.context.prev) { | |||
| return popContext(state); | |||
| } else if (supportsAtComponent && /@component/.test(type)) { | |||
| } else if (supportsAtComponent && /@component/i.test(type)) { | |||
| return pushContext(state, stream, "atComponentBlock"); | |||
| } else if (/^@(-moz-)?document$/.test(type)) { | |||
| } else if (/^@(-moz-)?document$/i.test(type)) { | |||
| return pushContext(state, stream, "documentTypes"); | |||
| } else if (/^@(media|supports|(-moz-)?document|import)$/.test(type)) { | |||
| } else if (/^@(media|supports|(-moz-)?document|import)$/i.test(type)) { | |||
| return pushContext(state, stream, "atBlock"); | |||
| } else if (/^@(font-face|counter-style)/.test(type)) { | |||
| } else if (/^@(font-face|counter-style)/i.test(type)) { | |||
| state.stateArg = type; | |||
| return "restricted_atBlock_before"; | |||
| } else if (/^@(-(moz|ms|o|webkit)-)?keyframes$/.test(type)) { | |||
| } else if (/^@(-(moz|ms|o|webkit)-)?keyframes$/i.test(type)) { | |||
| return "keyframes"; | |||
| } else if (type && type.charAt(0) == "@") { | |||
| return pushContext(state, stream, "at"); | |||
| @@ -198,7 +198,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| override = "property"; | |||
| return "maybeprop"; | |||
| } else if (nonStandardPropertyKeywords.hasOwnProperty(word)) { | |||
| override = "string-2"; | |||
| override = highlightNonStandardPropertyKeywords ? "string-2" : "property"; | |||
| return "maybeprop"; | |||
| } else if (allowNested) { | |||
| override = stream.match(/^\s*:(?:\s|$)/, false) ? "property" : "tag"; | |||
| @@ -228,7 +228,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| if (type == "}" || type == "{") return popAndPass(type, stream, state); | |||
| if (type == "(") return pushContext(state, stream, "parens"); | |||
| if (type == "hash" && !/^#([0-9a-fA-f]{3,4}|[0-9a-fA-f]{6}|[0-9a-fA-f]{8})$/.test(stream.current())) { | |||
| if (type == "hash" && !/^#([0-9a-fA-F]{3,4}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/.test(stream.current())) { | |||
| override += " error"; | |||
| } else if (type == "word") { | |||
| wordAsValue(stream); | |||
| @@ -292,7 +292,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| else if (propertyKeywords.hasOwnProperty(word)) | |||
| override = "property"; | |||
| else if (nonStandardPropertyKeywords.hasOwnProperty(word)) | |||
| override = "string-2"; | |||
| override = highlightNonStandardPropertyKeywords ? "string-2" : "property"; | |||
| else if (valueKeywords.hasOwnProperty(word)) | |||
| override = "atom"; | |||
| else if (colorKeywords.hasOwnProperty(word)) | |||
| @@ -383,7 +383,8 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| style = style[0]; | |||
| } | |||
| override = style; | |||
| state.state = states[state.state](type, stream, state); | |||
| if (type != "comment") | |||
| state.state = states[state.state](type, stream, state); | |||
| return override; | |||
| }, | |||
| @@ -401,7 +402,6 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| ch == "{" && (cx.type == "at" || cx.type == "atBlock")) { | |||
| // Dedent relative to current context. | |||
| indent = Math.max(0, cx.indent - indentUnit); | |||
| cx = cx.prev; | |||
| } | |||
| } | |||
| return indent; | |||
| @@ -410,6 +410,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| electricChars: "}", | |||
| blockCommentStart: "/*", | |||
| blockCommentEnd: "*/", | |||
| blockCommentContinue: " * ", | |||
| lineComment: lineComment, | |||
| fold: "brace" | |||
| }; | |||
| @@ -442,117 +443,151 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "monochrome", "min-monochrome", "max-monochrome", "resolution", | |||
| "min-resolution", "max-resolution", "scan", "grid", "orientation", | |||
| "device-pixel-ratio", "min-device-pixel-ratio", "max-device-pixel-ratio", | |||
| "pointer", "any-pointer", "hover", "any-hover" | |||
| "pointer", "any-pointer", "hover", "any-hover", "prefers-color-scheme", | |||
| "dynamic-range", "video-dynamic-range" | |||
| ], mediaFeatures = keySet(mediaFeatures_); | |||
| var mediaValueKeywords_ = [ | |||
| "landscape", "portrait", "none", "coarse", "fine", "on-demand", "hover", | |||
| "interlace", "progressive" | |||
| "interlace", "progressive", | |||
| "dark", "light", | |||
| "standard", "high" | |||
| ], mediaValueKeywords = keySet(mediaValueKeywords_); | |||
| var propertyKeywords_ = [ | |||
| "align-content", "align-items", "align-self", "alignment-adjust", | |||
| "alignment-baseline", "anchor-point", "animation", "animation-delay", | |||
| "alignment-baseline", "all", "anchor-point", "animation", "animation-delay", | |||
| "animation-direction", "animation-duration", "animation-fill-mode", | |||
| "animation-iteration-count", "animation-name", "animation-play-state", | |||
| "animation-timing-function", "appearance", "azimuth", "backface-visibility", | |||
| "background", "background-attachment", "background-blend-mode", "background-clip", | |||
| "background-color", "background-image", "background-origin", "background-position", | |||
| "background-repeat", "background-size", "baseline-shift", "binding", | |||
| "bleed", "bookmark-label", "bookmark-level", "bookmark-state", | |||
| "bookmark-target", "border", "border-bottom", "border-bottom-color", | |||
| "border-bottom-left-radius", "border-bottom-right-radius", | |||
| "border-bottom-style", "border-bottom-width", "border-collapse", | |||
| "border-color", "border-image", "border-image-outset", | |||
| "animation-timing-function", "appearance", "azimuth", "backdrop-filter", | |||
| "backface-visibility", "background", "background-attachment", | |||
| "background-blend-mode", "background-clip", "background-color", | |||
| "background-image", "background-origin", "background-position", | |||
| "background-position-x", "background-position-y", "background-repeat", | |||
| "background-size", "baseline-shift", "binding", "bleed", "block-size", | |||
| "bookmark-label", "bookmark-level", "bookmark-state", "bookmark-target", | |||
| "border", "border-bottom", "border-bottom-color", "border-bottom-left-radius", | |||
| "border-bottom-right-radius", "border-bottom-style", "border-bottom-width", | |||
| "border-collapse", "border-color", "border-image", "border-image-outset", | |||
| "border-image-repeat", "border-image-slice", "border-image-source", | |||
| "border-image-width", "border-left", "border-left-color", | |||
| "border-left-style", "border-left-width", "border-radius", "border-right", | |||
| "border-right-color", "border-right-style", "border-right-width", | |||
| "border-spacing", "border-style", "border-top", "border-top-color", | |||
| "border-top-left-radius", "border-top-right-radius", "border-top-style", | |||
| "border-top-width", "border-width", "bottom", "box-decoration-break", | |||
| "box-shadow", "box-sizing", "break-after", "break-before", "break-inside", | |||
| "caption-side", "clear", "clip", "color", "color-profile", "column-count", | |||
| "column-fill", "column-gap", "column-rule", "column-rule-color", | |||
| "column-rule-style", "column-rule-width", "column-span", "column-width", | |||
| "columns", "content", "counter-increment", "counter-reset", "crop", "cue", | |||
| "cue-after", "cue-before", "cursor", "direction", "display", | |||
| "dominant-baseline", "drop-initial-after-adjust", | |||
| "drop-initial-after-align", "drop-initial-before-adjust", | |||
| "drop-initial-before-align", "drop-initial-size", "drop-initial-value", | |||
| "elevation", "empty-cells", "fit", "fit-position", "flex", "flex-basis", | |||
| "flex-direction", "flex-flow", "flex-grow", "flex-shrink", "flex-wrap", | |||
| "float", "float-offset", "flow-from", "flow-into", "font", "font-feature-settings", | |||
| "font-family", "font-kerning", "font-language-override", "font-size", "font-size-adjust", | |||
| "font-stretch", "font-style", "font-synthesis", "font-variant", | |||
| "font-variant-alternates", "font-variant-caps", "font-variant-east-asian", | |||
| "font-variant-ligatures", "font-variant-numeric", "font-variant-position", | |||
| "font-weight", "grid", "grid-area", "grid-auto-columns", "grid-auto-flow", | |||
| "grid-auto-rows", "grid-column", "grid-column-end", "grid-column-gap", | |||
| "grid-column-start", "grid-gap", "grid-row", "grid-row-end", "grid-row-gap", | |||
| "grid-row-start", "grid-template", "grid-template-areas", "grid-template-columns", | |||
| "grid-template-rows", "hanging-punctuation", "height", "hyphens", | |||
| "icon", "image-orientation", "image-rendering", "image-resolution", | |||
| "inline-box-align", "justify-content", "left", "letter-spacing", | |||
| "line-break", "line-height", "line-stacking", "line-stacking-ruby", | |||
| "border-image-width", "border-left", "border-left-color", "border-left-style", | |||
| "border-left-width", "border-radius", "border-right", "border-right-color", | |||
| "border-right-style", "border-right-width", "border-spacing", "border-style", | |||
| "border-top", "border-top-color", "border-top-left-radius", | |||
| "border-top-right-radius", "border-top-style", "border-top-width", | |||
| "border-width", "bottom", "box-decoration-break", "box-shadow", "box-sizing", | |||
| "break-after", "break-before", "break-inside", "caption-side", "caret-color", | |||
| "clear", "clip", "color", "color-profile", "column-count", "column-fill", | |||
| "column-gap", "column-rule", "column-rule-color", "column-rule-style", | |||
| "column-rule-width", "column-span", "column-width", "columns", "contain", | |||
| "content", "counter-increment", "counter-reset", "crop", "cue", "cue-after", | |||
| "cue-before", "cursor", "direction", "display", "dominant-baseline", | |||
| "drop-initial-after-adjust", "drop-initial-after-align", | |||
| "drop-initial-before-adjust", "drop-initial-before-align", "drop-initial-size", | |||
| "drop-initial-value", "elevation", "empty-cells", "fit", "fit-content", "fit-position", | |||
| "flex", "flex-basis", "flex-direction", "flex-flow", "flex-grow", | |||
| "flex-shrink", "flex-wrap", "float", "float-offset", "flow-from", "flow-into", | |||
| "font", "font-family", "font-feature-settings", "font-kerning", | |||
| "font-language-override", "font-optical-sizing", "font-size", | |||
| "font-size-adjust", "font-stretch", "font-style", "font-synthesis", | |||
| "font-variant", "font-variant-alternates", "font-variant-caps", | |||
| "font-variant-east-asian", "font-variant-ligatures", "font-variant-numeric", | |||
| "font-variant-position", "font-variation-settings", "font-weight", "gap", | |||
| "grid", "grid-area", "grid-auto-columns", "grid-auto-flow", "grid-auto-rows", | |||
| "grid-column", "grid-column-end", "grid-column-gap", "grid-column-start", | |||
| "grid-gap", "grid-row", "grid-row-end", "grid-row-gap", "grid-row-start", | |||
| "grid-template", "grid-template-areas", "grid-template-columns", | |||
| "grid-template-rows", "hanging-punctuation", "height", "hyphens", "icon", | |||
| "image-orientation", "image-rendering", "image-resolution", "inline-box-align", | |||
| "inset", "inset-block", "inset-block-end", "inset-block-start", "inset-inline", | |||
| "inset-inline-end", "inset-inline-start", "isolation", "justify-content", | |||
| "justify-items", "justify-self", "left", "letter-spacing", "line-break", | |||
| "line-height", "line-height-step", "line-stacking", "line-stacking-ruby", | |||
| "line-stacking-shift", "line-stacking-strategy", "list-style", | |||
| "list-style-image", "list-style-position", "list-style-type", "margin", | |||
| "margin-bottom", "margin-left", "margin-right", "margin-top", | |||
| "marks", "marquee-direction", "marquee-loop", | |||
| "marquee-play-count", "marquee-speed", "marquee-style", "max-height", | |||
| "max-width", "min-height", "min-width", "move-to", "nav-down", "nav-index", | |||
| "nav-left", "nav-right", "nav-up", "object-fit", "object-position", | |||
| "opacity", "order", "orphans", "outline", | |||
| "outline-color", "outline-offset", "outline-style", "outline-width", | |||
| "overflow", "overflow-style", "overflow-wrap", "overflow-x", "overflow-y", | |||
| "padding", "padding-bottom", "padding-left", "padding-right", "padding-top", | |||
| "page", "page-break-after", "page-break-before", "page-break-inside", | |||
| "page-policy", "pause", "pause-after", "pause-before", "perspective", | |||
| "perspective-origin", "pitch", "pitch-range", "play-during", "position", | |||
| "presentation-level", "punctuation-trim", "quotes", "region-break-after", | |||
| "region-break-before", "region-break-inside", "region-fragment", | |||
| "rendering-intent", "resize", "rest", "rest-after", "rest-before", "richness", | |||
| "right", "rotation", "rotation-point", "ruby-align", "ruby-overhang", | |||
| "ruby-position", "ruby-span", "shape-image-threshold", "shape-inside", "shape-margin", | |||
| "shape-outside", "size", "speak", "speak-as", "speak-header", | |||
| "speak-numeral", "speak-punctuation", "speech-rate", "stress", "string-set", | |||
| "tab-size", "table-layout", "target", "target-name", "target-new", | |||
| "target-position", "text-align", "text-align-last", "text-decoration", | |||
| "margin-bottom", "margin-left", "margin-right", "margin-top", "marks", | |||
| "marquee-direction", "marquee-loop", "marquee-play-count", "marquee-speed", | |||
| "marquee-style", "mask-clip", "mask-composite", "mask-image", "mask-mode", | |||
| "mask-origin", "mask-position", "mask-repeat", "mask-size","mask-type", | |||
| "max-block-size", "max-height", "max-inline-size", | |||
| "max-width", "min-block-size", "min-height", "min-inline-size", "min-width", | |||
| "mix-blend-mode", "move-to", "nav-down", "nav-index", "nav-left", "nav-right", | |||
| "nav-up", "object-fit", "object-position", "offset", "offset-anchor", | |||
| "offset-distance", "offset-path", "offset-position", "offset-rotate", | |||
| "opacity", "order", "orphans", "outline", "outline-color", "outline-offset", | |||
| "outline-style", "outline-width", "overflow", "overflow-style", | |||
| "overflow-wrap", "overflow-x", "overflow-y", "padding", "padding-bottom", | |||
| "padding-left", "padding-right", "padding-top", "page", "page-break-after", | |||
| "page-break-before", "page-break-inside", "page-policy", "pause", | |||
| "pause-after", "pause-before", "perspective", "perspective-origin", "pitch", | |||
| "pitch-range", "place-content", "place-items", "place-self", "play-during", | |||
| "position", "presentation-level", "punctuation-trim", "quotes", | |||
| "region-break-after", "region-break-before", "region-break-inside", | |||
| "region-fragment", "rendering-intent", "resize", "rest", "rest-after", | |||
| "rest-before", "richness", "right", "rotate", "rotation", "rotation-point", | |||
| "row-gap", "ruby-align", "ruby-overhang", "ruby-position", "ruby-span", | |||
| "scale", "scroll-behavior", "scroll-margin", "scroll-margin-block", | |||
| "scroll-margin-block-end", "scroll-margin-block-start", "scroll-margin-bottom", | |||
| "scroll-margin-inline", "scroll-margin-inline-end", | |||
| "scroll-margin-inline-start", "scroll-margin-left", "scroll-margin-right", | |||
| "scroll-margin-top", "scroll-padding", "scroll-padding-block", | |||
| "scroll-padding-block-end", "scroll-padding-block-start", | |||
| "scroll-padding-bottom", "scroll-padding-inline", "scroll-padding-inline-end", | |||
| "scroll-padding-inline-start", "scroll-padding-left", "scroll-padding-right", | |||
| "scroll-padding-top", "scroll-snap-align", "scroll-snap-type", | |||
| "shape-image-threshold", "shape-inside", "shape-margin", "shape-outside", | |||
| "size", "speak", "speak-as", "speak-header", "speak-numeral", | |||
| "speak-punctuation", "speech-rate", "stress", "string-set", "tab-size", | |||
| "table-layout", "target", "target-name", "target-new", "target-position", | |||
| "text-align", "text-align-last", "text-combine-upright", "text-decoration", | |||
| "text-decoration-color", "text-decoration-line", "text-decoration-skip", | |||
| "text-decoration-style", "text-emphasis", "text-emphasis-color", | |||
| "text-emphasis-position", "text-emphasis-style", "text-height", | |||
| "text-indent", "text-justify", "text-outline", "text-overflow", "text-shadow", | |||
| "text-size-adjust", "text-space-collapse", "text-transform", "text-underline-position", | |||
| "text-wrap", "top", "transform", "transform-origin", "transform-style", | |||
| "transition", "transition-delay", "transition-duration", | |||
| "transition-property", "transition-timing-function", "unicode-bidi", | |||
| "user-select", "vertical-align", "visibility", "voice-balance", "voice-duration", | |||
| "voice-family", "voice-pitch", "voice-range", "voice-rate", "voice-stress", | |||
| "voice-volume", "volume", "white-space", "widows", "width", "will-change", "word-break", | |||
| "word-spacing", "word-wrap", "z-index", | |||
| "text-decoration-skip-ink", "text-decoration-style", "text-emphasis", | |||
| "text-emphasis-color", "text-emphasis-position", "text-emphasis-style", | |||
| "text-height", "text-indent", "text-justify", "text-orientation", | |||
| "text-outline", "text-overflow", "text-rendering", "text-shadow", | |||
| "text-size-adjust", "text-space-collapse", "text-transform", | |||
| "text-underline-position", "text-wrap", "top", "touch-action", "transform", "transform-origin", | |||
| "transform-style", "transition", "transition-delay", "transition-duration", | |||
| "transition-property", "transition-timing-function", "translate", | |||
| "unicode-bidi", "user-select", "vertical-align", "visibility", "voice-balance", | |||
| "voice-duration", "voice-family", "voice-pitch", "voice-range", "voice-rate", | |||
| "voice-stress", "voice-volume", "volume", "white-space", "widows", "width", | |||
| "will-change", "word-break", "word-spacing", "word-wrap", "writing-mode", "z-index", | |||
| // SVG-specific | |||
| "clip-path", "clip-rule", "mask", "enable-background", "filter", "flood-color", | |||
| "flood-opacity", "lighting-color", "stop-color", "stop-opacity", "pointer-events", | |||
| "color-interpolation", "color-interpolation-filters", | |||
| "color-rendering", "fill", "fill-opacity", "fill-rule", "image-rendering", | |||
| "marker", "marker-end", "marker-mid", "marker-start", "shape-rendering", "stroke", | |||
| "marker", "marker-end", "marker-mid", "marker-start", "paint-order", "shape-rendering", "stroke", | |||
| "stroke-dasharray", "stroke-dashoffset", "stroke-linecap", "stroke-linejoin", | |||
| "stroke-miterlimit", "stroke-opacity", "stroke-width", "text-rendering", | |||
| "baseline-shift", "dominant-baseline", "glyph-orientation-horizontal", | |||
| "glyph-orientation-vertical", "text-anchor", "writing-mode" | |||
| "glyph-orientation-vertical", "text-anchor", "writing-mode", | |||
| ], propertyKeywords = keySet(propertyKeywords_); | |||
| var nonStandardPropertyKeywords_ = [ | |||
| "accent-color", "aspect-ratio", "border-block", "border-block-color", "border-block-end", | |||
| "border-block-end-color", "border-block-end-style", "border-block-end-width", | |||
| "border-block-start", "border-block-start-color", "border-block-start-style", | |||
| "border-block-start-width", "border-block-style", "border-block-width", | |||
| "border-inline", "border-inline-color", "border-inline-end", | |||
| "border-inline-end-color", "border-inline-end-style", | |||
| "border-inline-end-width", "border-inline-start", "border-inline-start-color", | |||
| "border-inline-start-style", "border-inline-start-width", | |||
| "border-inline-style", "border-inline-width", "content-visibility", "margin-block", | |||
| "margin-block-end", "margin-block-start", "margin-inline", "margin-inline-end", | |||
| "margin-inline-start", "overflow-anchor", "overscroll-behavior", "padding-block", "padding-block-end", | |||
| "padding-block-start", "padding-inline", "padding-inline-end", | |||
| "padding-inline-start", "scroll-snap-stop", "scrollbar-3d-light-color", | |||
| "scrollbar-arrow-color", "scrollbar-base-color", "scrollbar-dark-shadow-color", | |||
| "scrollbar-face-color", "scrollbar-highlight-color", "scrollbar-shadow-color", | |||
| "scrollbar-3d-light-color", "scrollbar-track-color", "shape-inside", | |||
| "searchfield-cancel-button", "searchfield-decoration", "searchfield-results-button", | |||
| "searchfield-results-decoration", "zoom" | |||
| "scrollbar-track-color", "searchfield-cancel-button", "searchfield-decoration", | |||
| "searchfield-results-button", "searchfield-results-decoration", "shape-inside", "zoom" | |||
| ], nonStandardPropertyKeywords = keySet(nonStandardPropertyKeywords_); | |||
| var fontProperties_ = [ | |||
| "font-family", "src", "unicode-range", "font-variant", "font-feature-settings", | |||
| "font-stretch", "font-weight", "font-style" | |||
| "font-display", "font-family", "src", "unicode-range", "font-variant", | |||
| "font-feature-settings", "font-stretch", "font-weight", "font-style" | |||
| ], fontProperties = keySet(fontProperties_); | |||
| var counterDescriptors_ = [ | |||
| @@ -565,16 +600,16 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "bisque", "black", "blanchedalmond", "blue", "blueviolet", "brown", | |||
| "burlywood", "cadetblue", "chartreuse", "chocolate", "coral", "cornflowerblue", | |||
| "cornsilk", "crimson", "cyan", "darkblue", "darkcyan", "darkgoldenrod", | |||
| "darkgray", "darkgreen", "darkkhaki", "darkmagenta", "darkolivegreen", | |||
| "darkgray", "darkgreen", "darkgrey", "darkkhaki", "darkmagenta", "darkolivegreen", | |||
| "darkorange", "darkorchid", "darkred", "darksalmon", "darkseagreen", | |||
| "darkslateblue", "darkslategray", "darkturquoise", "darkviolet", | |||
| "deeppink", "deepskyblue", "dimgray", "dodgerblue", "firebrick", | |||
| "darkslateblue", "darkslategray", "darkslategrey", "darkturquoise", "darkviolet", | |||
| "deeppink", "deepskyblue", "dimgray", "dimgrey", "dodgerblue", "firebrick", | |||
| "floralwhite", "forestgreen", "fuchsia", "gainsboro", "ghostwhite", | |||
| "gold", "goldenrod", "gray", "grey", "green", "greenyellow", "honeydew", | |||
| "hotpink", "indianred", "indigo", "ivory", "khaki", "lavender", | |||
| "lavenderblush", "lawngreen", "lemonchiffon", "lightblue", "lightcoral", | |||
| "lightcyan", "lightgoldenrodyellow", "lightgray", "lightgreen", "lightpink", | |||
| "lightsalmon", "lightseagreen", "lightskyblue", "lightslategray", | |||
| "lightcyan", "lightgoldenrodyellow", "lightgray", "lightgreen", "lightgrey", "lightpink", | |||
| "lightsalmon", "lightseagreen", "lightskyblue", "lightslategray", "lightslategrey", | |||
| "lightsteelblue", "lightyellow", "lime", "limegreen", "linen", "magenta", | |||
| "maroon", "mediumaquamarine", "mediumblue", "mediumorchid", "mediumpurple", | |||
| "mediumseagreen", "mediumslateblue", "mediumspringgreen", "mediumturquoise", | |||
| @@ -584,7 +619,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "papayawhip", "peachpuff", "peru", "pink", "plum", "powderblue", | |||
| "purple", "rebeccapurple", "red", "rosybrown", "royalblue", "saddlebrown", | |||
| "salmon", "sandybrown", "seagreen", "seashell", "sienna", "silver", "skyblue", | |||
| "slateblue", "slategray", "snow", "springgreen", "steelblue", "tan", | |||
| "slateblue", "slategray", "slategrey", "snow", "springgreen", "steelblue", "tan", | |||
| "teal", "thistle", "tomato", "turquoise", "violet", "wheat", "white", | |||
| "whitesmoke", "yellow", "yellowgreen" | |||
| ], colorKeywords = keySet(colorKeywords_); | |||
| @@ -594,22 +629,22 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "after-white-space", "ahead", "alias", "all", "all-scroll", "alphabetic", "alternate", | |||
| "always", "amharic", "amharic-abegede", "antialiased", "appworkspace", | |||
| "arabic-indic", "armenian", "asterisks", "attr", "auto", "auto-flow", "avoid", "avoid-column", "avoid-page", | |||
| "avoid-region", "background", "backwards", "baseline", "below", "bidi-override", "binary", | |||
| "bengali", "blink", "block", "block-axis", "bold", "bolder", "border", "border-box", | |||
| "both", "bottom", "break", "break-all", "break-word", "bullets", "button", "button-bevel", | |||
| "avoid-region", "axis-pan", "background", "backwards", "baseline", "below", "bidi-override", "binary", | |||
| "bengali", "blink", "block", "block-axis", "blur", "bold", "bolder", "border", "border-box", | |||
| "both", "bottom", "break", "break-all", "break-word", "brightness", "bullets", "button", | |||
| "buttonface", "buttonhighlight", "buttonshadow", "buttontext", "calc", "cambodian", | |||
| "capitalize", "caps-lock-indicator", "caption", "captiontext", "caret", | |||
| "cell", "center", "checkbox", "circle", "cjk-decimal", "cjk-earthly-branch", | |||
| "cjk-heavenly-stem", "cjk-ideographic", "clear", "clip", "close-quote", | |||
| "col-resize", "collapse", "color", "color-burn", "color-dodge", "column", "column-reverse", | |||
| "compact", "condensed", "contain", "content", "contents", | |||
| "content-box", "context-menu", "continuous", "copy", "counter", "counters", "cover", "crop", | |||
| "cross", "crosshair", "currentcolor", "cursive", "cyclic", "darken", "dashed", "decimal", | |||
| "compact", "condensed", "conic-gradient", "contain", "content", "contents", | |||
| "content-box", "context-menu", "continuous", "contrast", "copy", "counter", "counters", "cover", "crop", | |||
| "cross", "crosshair", "cubic-bezier", "currentcolor", "cursive", "cyclic", "darken", "dashed", "decimal", | |||
| "decimal-leading-zero", "default", "default-button", "dense", "destination-atop", | |||
| "destination-in", "destination-out", "destination-over", "devanagari", "difference", | |||
| "disc", "discard", "disclosure-closed", "disclosure-open", "document", | |||
| "dot-dash", "dot-dot-dash", | |||
| "dotted", "double", "down", "e-resize", "ease", "ease-in", "ease-in-out", "ease-out", | |||
| "dotted", "double", "down", "drop-shadow", "e-resize", "ease", "ease-in", "ease-in-out", "ease-out", | |||
| "element", "ellipse", "ellipsis", "embed", "end", "ethiopic", "ethiopic-abegede", | |||
| "ethiopic-abegede-am-et", "ethiopic-abegede-gez", "ethiopic-abegede-ti-er", | |||
| "ethiopic-abegede-ti-et", "ethiopic-halehame-aa-er", | |||
| @@ -618,11 +653,11 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "ethiopic-halehame-sid-et", "ethiopic-halehame-so-et", | |||
| "ethiopic-halehame-ti-er", "ethiopic-halehame-ti-et", "ethiopic-halehame-tig", | |||
| "ethiopic-numeric", "ew-resize", "exclusion", "expanded", "extends", "extra-condensed", | |||
| "extra-expanded", "fantasy", "fast", "fill", "fixed", "flat", "flex", "flex-end", "flex-start", "footnotes", | |||
| "forwards", "from", "geometricPrecision", "georgian", "graytext", "grid", "groove", | |||
| "extra-expanded", "fantasy", "fast", "fill", "fill-box", "fixed", "flat", "flex", "flex-end", "flex-start", "footnotes", | |||
| "forwards", "from", "geometricPrecision", "georgian", "grayscale", "graytext", "grid", "groove", | |||
| "gujarati", "gurmukhi", "hand", "hangul", "hangul-consonant", "hard-light", "hebrew", | |||
| "help", "hidden", "hide", "higher", "highlight", "highlighttext", | |||
| "hiragana", "hiragana-iroha", "horizontal", "hsl", "hsla", "hue", "icon", "ignore", | |||
| "hiragana", "hiragana-iroha", "horizontal", "hsl", "hsla", "hue", "hue-rotate", "icon", "ignore", | |||
| "inactiveborder", "inactivecaption", "inactivecaptiontext", "infinite", | |||
| "infobackground", "infotext", "inherit", "initial", "inline", "inline-axis", | |||
| "inline-block", "inline-flex", "inline-grid", "inline-table", "inset", "inside", "intrinsic", "invert", | |||
| @@ -633,41 +668,37 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "line-through", "linear", "linear-gradient", "lines", "list-item", "listbox", "listitem", | |||
| "local", "logical", "loud", "lower", "lower-alpha", "lower-armenian", | |||
| "lower-greek", "lower-hexadecimal", "lower-latin", "lower-norwegian", | |||
| "lower-roman", "lowercase", "ltr", "luminosity", "malayalam", "match", "matrix", "matrix3d", | |||
| "media-controls-background", "media-current-time-display", | |||
| "media-fullscreen-button", "media-mute-button", "media-play-button", | |||
| "media-return-to-realtime-button", "media-rewind-button", | |||
| "media-seek-back-button", "media-seek-forward-button", "media-slider", | |||
| "media-sliderthumb", "media-time-remaining-display", "media-volume-slider", | |||
| "media-volume-slider-container", "media-volume-sliderthumb", "medium", | |||
| "menu", "menulist", "menulist-button", "menulist-text", | |||
| "menulist-textfield", "menutext", "message-box", "middle", "min-intrinsic", | |||
| "mix", "mongolian", "monospace", "move", "multiple", "multiply", "myanmar", "n-resize", | |||
| "lower-roman", "lowercase", "ltr", "luminosity", "malayalam", "manipulation", "match", "matrix", "matrix3d", | |||
| "media-play-button", "media-slider", "media-sliderthumb", | |||
| "media-volume-slider", "media-volume-sliderthumb", "medium", | |||
| "menu", "menulist", "menulist-button", | |||
| "menutext", "message-box", "middle", "min-intrinsic", | |||
| "mix", "mongolian", "monospace", "move", "multiple", "multiple_mask_images", "multiply", "myanmar", "n-resize", | |||
| "narrower", "ne-resize", "nesw-resize", "no-close-quote", "no-drop", | |||
| "no-open-quote", "no-repeat", "none", "normal", "not-allowed", "nowrap", | |||
| "ns-resize", "numbers", "numeric", "nw-resize", "nwse-resize", "oblique", "octal", "opacity", "open-quote", | |||
| "optimizeLegibility", "optimizeSpeed", "oriya", "oromo", "outset", | |||
| "outside", "outside-shape", "overlay", "overline", "padding", "padding-box", | |||
| "painted", "page", "paused", "persian", "perspective", "plus-darker", "plus-lighter", | |||
| "painted", "page", "paused", "persian", "perspective", "pinch-zoom", "plus-darker", "plus-lighter", | |||
| "pointer", "polygon", "portrait", "pre", "pre-line", "pre-wrap", "preserve-3d", | |||
| "progress", "push-button", "radial-gradient", "radio", "read-only", | |||
| "read-write", "read-write-plaintext-only", "rectangle", "region", | |||
| "relative", "repeat", "repeating-linear-gradient", | |||
| "repeating-radial-gradient", "repeat-x", "repeat-y", "reset", "reverse", | |||
| "relative", "repeat", "repeating-linear-gradient", "repeating-radial-gradient", | |||
| "repeating-conic-gradient", "repeat-x", "repeat-y", "reset", "reverse", | |||
| "rgb", "rgba", "ridge", "right", "rotate", "rotate3d", "rotateX", "rotateY", | |||
| "rotateZ", "round", "row", "row-resize", "row-reverse", "rtl", "run-in", "running", | |||
| "s-resize", "sans-serif", "saturation", "scale", "scale3d", "scaleX", "scaleY", "scaleZ", "screen", | |||
| "s-resize", "sans-serif", "saturate", "saturation", "scale", "scale3d", "scaleX", "scaleY", "scaleZ", "screen", | |||
| "scroll", "scrollbar", "scroll-position", "se-resize", "searchfield", | |||
| "searchfield-cancel-button", "searchfield-decoration", | |||
| "searchfield-results-button", "searchfield-results-decoration", | |||
| "semi-condensed", "semi-expanded", "separate", "serif", "show", "sidama", | |||
| "searchfield-results-button", "searchfield-results-decoration", "self-start", "self-end", | |||
| "semi-condensed", "semi-expanded", "separate", "sepia", "serif", "show", "sidama", | |||
| "simp-chinese-formal", "simp-chinese-informal", "single", | |||
| "skew", "skewX", "skewY", "skip-white-space", "slide", "slider-horizontal", | |||
| "slider-vertical", "sliderthumb-horizontal", "sliderthumb-vertical", "slow", | |||
| "small", "small-caps", "small-caption", "smaller", "soft-light", "solid", "somali", | |||
| "source-atop", "source-in", "source-out", "source-over", "space", "space-around", "space-between", "spell-out", "square", | |||
| "square-button", "start", "static", "status-bar", "stretch", "stroke", "sub", | |||
| "subpixel-antialiased", "super", "sw-resize", "symbolic", "symbols", "table", | |||
| "source-atop", "source-in", "source-out", "source-over", "space", "space-around", "space-between", "space-evenly", "spell-out", "square", | |||
| "square-button", "start", "static", "status-bar", "stretch", "stroke", "stroke-box", "sub", | |||
| "subpixel-antialiased", "svg_masks", "super", "sw-resize", "symbolic", "symbols", "system-ui", "table", | |||
| "table-caption", "table-cell", "table-column", "table-column-group", | |||
| "table-footer-group", "table-header-group", "table-row", "table-row-group", | |||
| "tamil", | |||
| @@ -677,10 +708,10 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| "tigrinya-er-abegede", "tigrinya-et", "tigrinya-et-abegede", "to", "top", | |||
| "trad-chinese-formal", "trad-chinese-informal", "transform", | |||
| "translate", "translate3d", "translateX", "translateY", "translateZ", | |||
| "transparent", "ultra-condensed", "ultra-expanded", "underline", "unset", "up", | |||
| "transparent", "ultra-condensed", "ultra-expanded", "underline", "unidirectional-pan", "unset", "up", | |||
| "upper-alpha", "upper-armenian", "upper-greek", "upper-hexadecimal", | |||
| "upper-latin", "upper-norwegian", "upper-roman", "uppercase", "urdu", "url", | |||
| "var", "vertical", "vertical-text", "visible", "visibleFill", "visiblePainted", | |||
| "var", "vertical", "vertical-text", "view-box", "visible", "visibleFill", "visiblePainted", | |||
| "visibleStroke", "visual", "w-resize", "wait", "wave", "wider", | |||
| "window", "windowframe", "windowtext", "words", "wrap", "wrap-reverse", "x-large", "x-small", "xor", | |||
| "xx-large", "xx-small" | |||
| @@ -748,8 +779,8 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| } | |||
| }, | |||
| ":": function(stream) { | |||
| if (stream.match(/\s*\{/)) | |||
| return [null, "{"]; | |||
| if (stream.match(/^\s*\{/, false)) | |||
| return [null, null] | |||
| return false; | |||
| }, | |||
| "$": function(stream) { | |||
| @@ -792,7 +823,7 @@ CodeMirror.defineMode("css", function(config, parserConfig) { | |||
| }, | |||
| "@": function(stream) { | |||
| if (stream.eat("{")) return [null, "interpolation"]; | |||
| if (stream.match(/^(charset|document|font-face|import|(-(moz|ms|o|webkit)-)?keyframes|media|namespace|page|supports)\b/, false)) return false; | |||
| if (stream.match(/^(charset|document|font-face|import|(-(moz|ms|o|webkit)-)?keyframes|media|namespace|page|supports)\b/i, false)) return false; | |||
| stream.eatWhile(/[\w\\\-]/); | |||
| if (stream.match(/^\s*:/, false)) | |||
| return ["variable-2", "variable-definition"]; | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| "use strict"; | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| "use strict"; | |||
| @@ -10,8 +10,8 @@ | |||
| MT("variable", | |||
| "[variable-2 @base]: [atom #f04615];", | |||
| "[qualifier .class] {", | |||
| " [property width]: [variable percentage]([number 0.5]); [comment // returns `50%`]", | |||
| " [property color]: [variable saturate]([variable-2 @base], [number 5%]);", | |||
| " [property width]: [variable&callee percentage]([number 0.5]); [comment // returns `50%`]", | |||
| " [property color]: [variable&callee saturate]([variable-2 @base], [number 5%]);", | |||
| "}"); | |||
| MT("amp", | |||
| @@ -26,10 +26,10 @@ | |||
| MT("mixin", | |||
| "[qualifier .mixin] ([variable dark]; [variable-2 @color]) {", | |||
| " [property color]: [atom darken]([variable-2 @color], [number 10%]);", | |||
| " [property color]: [variable&callee darken]([variable-2 @color], [number 10%]);", | |||
| "}", | |||
| "[qualifier .mixin] ([variable light]; [variable-2 @color]) {", | |||
| " [property color]: [atom lighten]([variable-2 @color], [number 10%]);", | |||
| " [property color]: [variable&callee lighten]([variable-2 @color], [number 10%]);", | |||
| "}", | |||
| "[qualifier .mixin] ([variable-2 @_]; [variable-2 @color]) {", | |||
| " [property display]: [atom block];", | |||
| @@ -1,24 +1,24 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "text/x-scss"); | |||
| function MT(name) { test.mode(name, mode, Array.prototype.slice.call(arguments, 1), "scss"); } | |||
| MT('url_with_quotation', | |||
| "[tag foo] { [property background]:[atom url]([string test.jpg]) }"); | |||
| "[tag foo] { [property background]:[variable&callee url]([string test.jpg]) }"); | |||
| MT('url_with_double_quotes', | |||
| "[tag foo] { [property background]:[atom url]([string \"test.jpg\"]) }"); | |||
| "[tag foo] { [property background]:[variable&callee url]([string \"test.jpg\"]) }"); | |||
| MT('url_with_single_quotes', | |||
| "[tag foo] { [property background]:[atom url]([string \'test.jpg\']) }"); | |||
| "[tag foo] { [property background]:[variable&callee url]([string \'test.jpg\']) }"); | |||
| MT('string', | |||
| "[def @import] [string \"compass/css3\"]"); | |||
| MT('important_keyword', | |||
| "[tag foo] { [property background]:[atom url]([string \'test.jpg\']) [keyword !important] }"); | |||
| "[tag foo] { [property background]:[variable&callee url]([string \'test.jpg\']) [keyword !important] }"); | |||
| MT('variable', | |||
| "[variable-2 $blue]:[atom #333]"); | |||
| @@ -95,7 +95,7 @@ | |||
| MT('indent_parentheses', | |||
| "[tag foo] {", | |||
| " [property color]: [atom darken]([variable-2 $blue],", | |||
| " [property color]: [variable&callee darken]([variable-2 $blue],", | |||
| " [number 9%]);", | |||
| "}"); | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "css"); | |||
| @@ -24,6 +24,9 @@ | |||
| MT("atMediaUnknownFeatureValueKeyword", | |||
| "[def @media] ([property orientation]: [error upsidedown]) { }"); | |||
| MT("atMediaUppercase", | |||
| "[def @MEDIA] ([property orienTAtion]: [keyword landScape]) { }"); | |||
| MT("tagSelector", | |||
| "[tag foo] { }"); | |||
| @@ -86,11 +89,11 @@ | |||
| "[tag foo] { [property margin]: [number 0]; [property padding]: [number 0]; }"); | |||
| MT("tagTwoPropertiesURL", | |||
| "[tag foo] { [property background]: [atom url]([string //example.com/foo.png]); [property padding]: [number 0]; }"); | |||
| "[tag foo] { [property background]: [variable&callee url]([string //example.com/foo.png]); [property padding]: [number 0]; }"); | |||
| MT("indent_tagSelector", | |||
| "[tag strong], [tag em] {", | |||
| " [property background]: [atom rgba](", | |||
| " [property background]: [variable&callee rgba](", | |||
| " [number 255], [number 255], [number 0], [number .2]", | |||
| " );", | |||
| "}"); | |||
| @@ -111,7 +114,7 @@ | |||
| MT("indent_parentheses", | |||
| "[tag foo]:[variable-3 before] {", | |||
| " [property background]: [atom url](", | |||
| " [property background]: [variable&callee url](", | |||
| "[string blahblah]", | |||
| "[string etc]", | |||
| "[string ]) [keyword !important];", | |||
| @@ -121,20 +124,20 @@ | |||
| "[def @font-face] {", | |||
| " [property font-family]: [string 'myfont'];", | |||
| " [error nonsense]: [string 'abc'];", | |||
| " [property src]: [atom url]([string http://blah]),", | |||
| " [atom url]([string http://foo]);", | |||
| " [property src]: [variable&callee url]([string http://blah]),", | |||
| " [variable&callee url]([string http://foo]);", | |||
| "}"); | |||
| MT("empty_url", | |||
| "[def @import] [atom url]() [attribute screen];"); | |||
| "[def @import] [variable&callee url]() [attribute screen];"); | |||
| MT("parens", | |||
| "[qualifier .foo] {", | |||
| " [property background-image]: [variable fade]([atom #000], [number 20%]);", | |||
| " [property border-image]: [atom linear-gradient](", | |||
| " [property background-image]: [variable&callee fade]([atom #000], [number 20%]);", | |||
| " [property border-image]: [variable&callee linear-gradient](", | |||
| " [atom to] [atom bottom],", | |||
| " [variable fade]([atom #000], [number 20%]) [number 0%],", | |||
| " [variable fade]([atom #000], [number 20%]) [number 100%]", | |||
| " [variable&callee fade]([atom #000], [number 20%]) [number 0%],", | |||
| " [variable&callee fade]([atom #000], [number 20%]) [number 100%]", | |||
| " );", | |||
| "}"); | |||
| @@ -143,7 +146,15 @@ | |||
| " [variable-2 --main-color]: [atom #06c];", | |||
| "}", | |||
| "[tag h1][builtin #foo] {", | |||
| " [property color]: [atom var]([variable-2 --main-color]);", | |||
| " [property color]: [variable&callee var]([variable-2 --main-color]);", | |||
| "}"); | |||
| MT("blank_css_variable", | |||
| ":[variable-3 root] {", | |||
| " [variable-2 --]: [atom #06c];", | |||
| "}", | |||
| "[tag h1][builtin #foo] {", | |||
| " [property color]: [variable&callee var]([variable-2 --]);", | |||
| "}"); | |||
| MT("supports", | |||
| @@ -152,10 +163,10 @@ | |||
| "}"); | |||
| MT("document", | |||
| "[def @document] [tag url]([string http://blah]),", | |||
| " [tag url-prefix]([string https://]),", | |||
| " [tag domain]([string blah.com]),", | |||
| " [tag regexp]([string \".*blah.+\"]) {", | |||
| "[def @document] [variable&callee url]([string http://blah]),", | |||
| " [variable&callee url-prefix]([string https://]),", | |||
| " [variable&callee domain]([string blah.com]),", | |||
| " [variable&callee regexp]([string \".*blah.+\"]) {", | |||
| " [builtin #id] {", | |||
| " [property background-color]: [keyword white];", | |||
| " }", | |||
| @@ -165,16 +176,16 @@ | |||
| "}"); | |||
| MT("document_url", | |||
| "[def @document] [tag url]([string http://blah]) { [qualifier .class] { } }"); | |||
| "[def @document] [variable&callee url]([string http://blah]) { [qualifier .class] { } }"); | |||
| MT("document_urlPrefix", | |||
| "[def @document] [tag url-prefix]([string https://]) { [builtin #id] { } }"); | |||
| "[def @document] [variable&callee url-prefix]([string https://]) { [builtin #id] { } }"); | |||
| MT("document_domain", | |||
| "[def @document] [tag domain]([string blah.com]) { [tag foo] { } }"); | |||
| "[def @document] [variable&callee domain]([string blah.com]) { [tag foo] { } }"); | |||
| MT("document_regexp", | |||
| "[def @document] [tag regexp]([string \".*blah.+\"]) { [builtin #id] { } }"); | |||
| "[def @document] [variable&callee regexp]([string \".*blah.+\"]) { [builtin #id] { } }"); | |||
| MT("counter-style", | |||
| "[def @counter-style] [variable binary] {", | |||
| @@ -196,5 +207,11 @@ | |||
| "[tag ol][qualifier .roman] { [property list-style]: [variable simple-roman]; }"); | |||
| MT("counter-style-symbols", | |||
| "[tag ol] { [property list-style]: [atom symbols]([atom cyclic] [string \"*\"] [string \"\\2020\"] [string \"\\2021\"] [string \"\\A7\"]); }"); | |||
| "[tag ol] { [property list-style]: [variable&callee symbols]([atom cyclic] [string \"*\"] [string \"\\2020\"] [string \"\\2021\"] [string \"\\A7\"]); }"); | |||
| MT("comment-does-not-disrupt", | |||
| "[def @font-face] [comment /* foo */] {", | |||
| " [property src]: [variable&callee url]([string x]);", | |||
| " [property font-family]: [variable One];", | |||
| "}") | |||
| })(); | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function(mod) { | |||
| if (typeof exports == "object" && typeof module == "object") // CommonJS | |||
| @@ -50,7 +50,7 @@ | |||
| } | |||
| function getTagRegexp(tagName, anchored) { | |||
| return new RegExp((anchored ? "^" : "") + "<\/\s*" + tagName + "\s*>", "i"); | |||
| return new RegExp((anchored ? "^" : "") + "<\/\\s*" + tagName + "\\s*>", "i"); | |||
| } | |||
| function addTags(from, to) { | |||
| @@ -74,7 +74,8 @@ | |||
| name: "xml", | |||
| htmlMode: true, | |||
| multilineTagIndentFactor: parserConfig.multilineTagIndentFactor, | |||
| multilineTagIndentPastTag: parserConfig.multilineTagIndentPastTag | |||
| multilineTagIndentPastTag: parserConfig.multilineTagIndentPastTag, | |||
| allowMissingTagName: parserConfig.allowMissingTagName, | |||
| }); | |||
| var tags = {}; | |||
| @@ -105,7 +106,7 @@ | |||
| return maybeBackup(stream, endTag, state.localMode.token(stream, state.localState)); | |||
| }; | |||
| state.localMode = mode; | |||
| state.localState = CodeMirror.startState(mode, htmlMode.indent(state.htmlState, "")); | |||
| state.localState = CodeMirror.startState(mode, htmlMode.indent(state.htmlState, "", "")); | |||
| } else if (state.inTag) { | |||
| state.inTag += stream.current() | |||
| if (stream.eol()) state.inTag += " " | |||
| @@ -133,11 +134,11 @@ | |||
| return state.token(stream, state); | |||
| }, | |||
| indent: function (state, textAfter) { | |||
| indent: function (state, textAfter, line) { | |||
| if (!state.localMode || /^\s*<\//.test(textAfter)) | |||
| return htmlMode.indent(state.htmlState, textAfter); | |||
| return htmlMode.indent(state.htmlState, textAfter, line); | |||
| else if (state.localMode.indent) | |||
| return state.localMode.indent(state.localState, textAfter); | |||
| return state.localMode.indent(state.localState, textAfter, line); | |||
| else | |||
| return CodeMirror.Pass; | |||
| }, | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function(mod) { | |||
| if (typeof exports == "object" && typeof module == "object") // CommonJS | |||
| @@ -11,16 +11,12 @@ | |||
| })(function(CodeMirror) { | |||
| "use strict"; | |||
| function expressionAllowed(stream, state, backUp) { | |||
| return /^(?:operator|sof|keyword c|case|new|export|default|[\[{}\(,;:]|=>)$/.test(state.lastType) || | |||
| (state.lastType == "quasi" && /\{\s*$/.test(stream.string.slice(0, stream.pos - (backUp || 0)))) | |||
| } | |||
| CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| var indentUnit = config.indentUnit; | |||
| var statementIndent = parserConfig.statementIndent; | |||
| var jsonldMode = parserConfig.jsonld; | |||
| var jsonMode = parserConfig.json || jsonldMode; | |||
| var trackScope = parserConfig.trackScope !== false | |||
| var isTS = parserConfig.typescript; | |||
| var wordRE = parserConfig.wordCharacters || /[\w$\xa1-\uffff]/; | |||
| @@ -28,56 +24,24 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| var keywords = function(){ | |||
| function kw(type) {return {type: type, style: "keyword"};} | |||
| var A = kw("keyword a"), B = kw("keyword b"), C = kw("keyword c"); | |||
| var A = kw("keyword a"), B = kw("keyword b"), C = kw("keyword c"), D = kw("keyword d"); | |||
| var operator = kw("operator"), atom = {type: "atom", style: "atom"}; | |||
| var jsKeywords = { | |||
| return { | |||
| "if": kw("if"), "while": A, "with": A, "else": B, "do": B, "try": B, "finally": B, | |||
| "return": C, "break": C, "continue": C, "new": kw("new"), "delete": C, "throw": C, "debugger": C, | |||
| "var": kw("var"), "const": kw("var"), "let": kw("var"), | |||
| "return": D, "break": D, "continue": D, "new": kw("new"), "delete": C, "void": C, "throw": C, | |||
| "debugger": kw("debugger"), "var": kw("var"), "const": kw("var"), "let": kw("var"), | |||
| "function": kw("function"), "catch": kw("catch"), | |||
| "for": kw("for"), "switch": kw("switch"), "case": kw("case"), "default": kw("default"), | |||
| "in": operator, "typeof": operator, "instanceof": operator, | |||
| "true": atom, "false": atom, "null": atom, "undefined": atom, "NaN": atom, "Infinity": atom, | |||
| "this": kw("this"), "class": kw("class"), "super": kw("atom"), | |||
| "yield": C, "export": kw("export"), "import": kw("import"), "extends": C, | |||
| "await": C, "async": kw("async") | |||
| "await": C | |||
| }; | |||
| // Extend the 'normal' keywords with the TypeScript language extensions | |||
| if (isTS) { | |||
| var type = {type: "variable", style: "variable-3"}; | |||
| var tsKeywords = { | |||
| // object-like things | |||
| "interface": kw("class"), | |||
| "implements": C, | |||
| "namespace": C, | |||
| "module": kw("module"), | |||
| "enum": kw("module"), | |||
| "type": kw("type"), | |||
| // scope modifiers | |||
| "public": kw("modifier"), | |||
| "private": kw("modifier"), | |||
| "protected": kw("modifier"), | |||
| "abstract": kw("modifier"), | |||
| // operators | |||
| "as": operator, | |||
| // types | |||
| "string": type, "number": type, "boolean": type, "any": type | |||
| }; | |||
| for (var attr in tsKeywords) { | |||
| jsKeywords[attr] = tsKeywords[attr]; | |||
| } | |||
| } | |||
| return jsKeywords; | |||
| }(); | |||
| var isOperatorChar = /[+\-*&%=<>!?|~^]/; | |||
| var isOperatorChar = /[+\-*&%=<>!?|~^@]/; | |||
| var isJsonldKeyword = /^@(context|id|value|language|type|container|list|set|reverse|index|base|vocab|graph)"/; | |||
| function readRegexp(stream) { | |||
| @@ -104,7 +68,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (ch == '"' || ch == "'") { | |||
| state.tokenize = tokenString(ch); | |||
| return state.tokenize(stream, state); | |||
| } else if (ch == "." && stream.match(/^\d+(?:[eE][+\-]?\d+)?/)) { | |||
| } else if (ch == "." && stream.match(/^\d[\d_]*(?:[eE][+\-]?[\d_]+)?/)) { | |||
| return ret("number", "number"); | |||
| } else if (ch == "." && stream.match("..")) { | |||
| return ret("spread", "meta"); | |||
| @@ -112,17 +76,10 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| return ret(ch); | |||
| } else if (ch == "=" && stream.eat(">")) { | |||
| return ret("=>", "operator"); | |||
| } else if (ch == "0" && stream.eat(/x/i)) { | |||
| stream.eatWhile(/[\da-f]/i); | |||
| return ret("number", "number"); | |||
| } else if (ch == "0" && stream.eat(/o/i)) { | |||
| stream.eatWhile(/[0-7]/i); | |||
| return ret("number", "number"); | |||
| } else if (ch == "0" && stream.eat(/b/i)) { | |||
| stream.eatWhile(/[01]/i); | |||
| } else if (ch == "0" && stream.match(/^(?:x[\dA-Fa-f_]+|o[0-7_]+|b[01_]+)n?/)) { | |||
| return ret("number", "number"); | |||
| } else if (/\d/.test(ch)) { | |||
| stream.match(/^\d*(?:\.\d*)?(?:[eE][+\-]?\d+)?/); | |||
| stream.match(/^[\d_]*(?:n|(?:\.[\d_]*)?(?:[eE][+\-]?[\d_]+)?)?/); | |||
| return ret("number", "number"); | |||
| } else if (ch == "/") { | |||
| if (stream.eat("*")) { | |||
| @@ -133,27 +90,47 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| return ret("comment", "comment"); | |||
| } else if (expressionAllowed(stream, state, 1)) { | |||
| readRegexp(stream); | |||
| stream.match(/^\b(([gimyu])(?![gimyu]*\2))+\b/); | |||
| stream.match(/^\b(([gimyus])(?![gimyus]*\2))+\b/); | |||
| return ret("regexp", "string-2"); | |||
| } else { | |||
| stream.eatWhile(isOperatorChar); | |||
| stream.eat("="); | |||
| return ret("operator", "operator", stream.current()); | |||
| } | |||
| } else if (ch == "`") { | |||
| state.tokenize = tokenQuasi; | |||
| return tokenQuasi(stream, state); | |||
| } else if (ch == "#") { | |||
| } else if (ch == "#" && stream.peek() == "!") { | |||
| stream.skipToEnd(); | |||
| return ret("error", "error"); | |||
| return ret("meta", "meta"); | |||
| } else if (ch == "#" && stream.eatWhile(wordRE)) { | |||
| return ret("variable", "property") | |||
| } else if (ch == "<" && stream.match("!--") || | |||
| (ch == "-" && stream.match("->") && !/\S/.test(stream.string.slice(0, stream.start)))) { | |||
| stream.skipToEnd() | |||
| return ret("comment", "comment") | |||
| } else if (isOperatorChar.test(ch)) { | |||
| if (ch != ">" || !state.lexical || state.lexical.type != ">") | |||
| stream.eatWhile(isOperatorChar); | |||
| if (ch != ">" || !state.lexical || state.lexical.type != ">") { | |||
| if (stream.eat("=")) { | |||
| if (ch == "!" || ch == "=") stream.eat("=") | |||
| } else if (/[<>*+\-|&?]/.test(ch)) { | |||
| stream.eat(ch) | |||
| if (ch == ">") stream.eat(ch) | |||
| } | |||
| } | |||
| if (ch == "?" && stream.eat(".")) return ret(".") | |||
| return ret("operator", "operator", stream.current()); | |||
| } else if (wordRE.test(ch)) { | |||
| stream.eatWhile(wordRE); | |||
| var word = stream.current(), known = keywords.propertyIsEnumerable(word) && keywords[word]; | |||
| return (known && state.lastType != ".") ? ret(known.type, known.style, word) : | |||
| ret("variable", "variable", word); | |||
| var word = stream.current() | |||
| if (state.lastType != ".") { | |||
| if (keywords.propertyIsEnumerable(word)) { | |||
| var kw = keywords[word] | |||
| return ret(kw.type, kw.style, word) | |||
| } | |||
| if (word == "async" && stream.match(/^(\s|\/\*([^*]|\*(?!\/))*?\*\/)*[\[\(\w]/, false)) | |||
| return ret("async", "keyword", word) | |||
| } | |||
| return ret("variable", "variable", word) | |||
| } | |||
| } | |||
| @@ -226,8 +203,12 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| ++depth; | |||
| } else if (wordRE.test(ch)) { | |||
| sawSomething = true; | |||
| } else if (/["'\/]/.test(ch)) { | |||
| return; | |||
| } else if (/["'\/`]/.test(ch)) { | |||
| for (;; --pos) { | |||
| if (pos == 0) return | |||
| var next = stream.string.charAt(pos - 1) | |||
| if (next == ch && stream.string.charAt(pos - 2) != "\\") { pos--; break } | |||
| } | |||
| } else if (sawSomething && !depth) { | |||
| ++pos; | |||
| break; | |||
| @@ -238,7 +219,8 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| // Parser | |||
| var atomicTypes = {"atom": true, "number": true, "variable": true, "string": true, "regexp": true, "this": true, "jsonld-keyword": true}; | |||
| var atomicTypes = {"atom": true, "number": true, "variable": true, "string": true, | |||
| "regexp": true, "this": true, "import": true, "jsonld-keyword": true}; | |||
| function JSLexical(indented, column, type, align, prev, info) { | |||
| this.indented = indented; | |||
| @@ -250,6 +232,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| } | |||
| function inScope(state, varname) { | |||
| if (!trackScope) return false | |||
| for (var v = state.localVars; v; v = v.next) | |||
| if (v.name == varname) return true; | |||
| for (var cx = state.context; cx; cx = cx.prev) { | |||
| @@ -289,35 +272,70 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| pass.apply(null, arguments); | |||
| return true; | |||
| } | |||
| function inList(name, list) { | |||
| for (var v = list; v; v = v.next) if (v.name == name) return true | |||
| return false; | |||
| } | |||
| function register(varname) { | |||
| function inList(list) { | |||
| for (var v = list; v; v = v.next) | |||
| if (v.name == varname) return true; | |||
| return false; | |||
| } | |||
| var state = cx.state; | |||
| cx.marked = "def"; | |||
| if (!trackScope) return | |||
| if (state.context) { | |||
| if (inList(state.localVars)) return; | |||
| state.localVars = {name: varname, next: state.localVars}; | |||
| if (state.lexical.info == "var" && state.context && state.context.block) { | |||
| // FIXME function decls are also not block scoped | |||
| var newContext = registerVarScoped(varname, state.context) | |||
| if (newContext != null) { | |||
| state.context = newContext | |||
| return | |||
| } | |||
| } else if (!inList(varname, state.localVars)) { | |||
| state.localVars = new Var(varname, state.localVars) | |||
| return | |||
| } | |||
| } | |||
| // Fall through means this is global | |||
| if (parserConfig.globalVars && !inList(varname, state.globalVars)) | |||
| state.globalVars = new Var(varname, state.globalVars) | |||
| } | |||
| function registerVarScoped(varname, context) { | |||
| if (!context) { | |||
| return null | |||
| } else if (context.block) { | |||
| var inner = registerVarScoped(varname, context.prev) | |||
| if (!inner) return null | |||
| if (inner == context.prev) return context | |||
| return new Context(inner, context.vars, true) | |||
| } else if (inList(varname, context.vars)) { | |||
| return context | |||
| } else { | |||
| if (inList(state.globalVars)) return; | |||
| if (parserConfig.globalVars) | |||
| state.globalVars = {name: varname, next: state.globalVars}; | |||
| return new Context(context.prev, new Var(varname, context.vars), false) | |||
| } | |||
| } | |||
| function isModifier(name) { | |||
| return name == "public" || name == "private" || name == "protected" || name == "abstract" || name == "readonly" | |||
| } | |||
| // Combinators | |||
| var defaultVars = {name: "this", next: {name: "arguments"}}; | |||
| function Context(prev, vars, block) { this.prev = prev; this.vars = vars; this.block = block } | |||
| function Var(name, next) { this.name = name; this.next = next } | |||
| var defaultVars = new Var("this", new Var("arguments", null)) | |||
| function pushcontext() { | |||
| cx.state.context = {prev: cx.state.context, vars: cx.state.localVars}; | |||
| cx.state.localVars = defaultVars; | |||
| cx.state.context = new Context(cx.state.context, cx.state.localVars, false) | |||
| cx.state.localVars = defaultVars | |||
| } | |||
| function pushblockcontext() { | |||
| cx.state.context = new Context(cx.state.context, cx.state.localVars, true) | |||
| cx.state.localVars = null | |||
| } | |||
| pushcontext.lex = pushblockcontext.lex = true | |||
| function popcontext() { | |||
| cx.state.localVars = cx.state.context.vars; | |||
| cx.state.context = cx.state.context.prev; | |||
| cx.state.localVars = cx.state.context.vars | |||
| cx.state.context = cx.state.context.prev | |||
| } | |||
| popcontext.lex = true | |||
| function pushlex(type, info) { | |||
| var result = function() { | |||
| var state = cx.state, indent = state.indented; | |||
| @@ -342,17 +360,19 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| function expect(wanted) { | |||
| function exp(type) { | |||
| if (type == wanted) return cont(); | |||
| else if (wanted == ";") return pass(); | |||
| else if (wanted == ";" || type == "}" || type == ")" || type == "]") return pass(); | |||
| else return cont(exp); | |||
| }; | |||
| return exp; | |||
| } | |||
| function statement(type, value) { | |||
| if (type == "var") return cont(pushlex("vardef", value.length), vardef, expect(";"), poplex); | |||
| if (type == "var") return cont(pushlex("vardef", value), vardef, expect(";"), poplex); | |||
| if (type == "keyword a") return cont(pushlex("form"), parenExpr, statement, poplex); | |||
| if (type == "keyword b") return cont(pushlex("form"), statement, poplex); | |||
| if (type == "{") return cont(pushlex("}"), block, poplex); | |||
| if (type == "keyword d") return cx.stream.match(/^\s*$/, false) ? cont() : cont(pushlex("stat"), maybeexpression, expect(";"), poplex); | |||
| if (type == "debugger") return cont(expect(";")); | |||
| if (type == "{") return cont(pushlex("}"), pushblockcontext, block, poplex, popcontext); | |||
| if (type == ";") return cont(); | |||
| if (type == "if") { | |||
| if (cx.state.lexical.info == "else" && cx.state.cc[cx.state.cc.length - 1] == poplex) | |||
| @@ -360,44 +380,66 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| return cont(pushlex("form"), parenExpr, statement, poplex, maybeelse); | |||
| } | |||
| if (type == "function") return cont(functiondef); | |||
| if (type == "for") return cont(pushlex("form"), forspec, statement, poplex); | |||
| if (type == "variable") return cont(pushlex("stat"), maybelabel); | |||
| if (type == "switch") return cont(pushlex("form"), parenExpr, pushlex("}", "switch"), expect("{"), | |||
| block, poplex, poplex); | |||
| if (type == "for") return cont(pushlex("form"), pushblockcontext, forspec, statement, popcontext, poplex); | |||
| if (type == "class" || (isTS && value == "interface")) { | |||
| cx.marked = "keyword" | |||
| return cont(pushlex("form", type == "class" ? type : value), className, poplex) | |||
| } | |||
| if (type == "variable") { | |||
| if (isTS && value == "declare") { | |||
| cx.marked = "keyword" | |||
| return cont(statement) | |||
| } else if (isTS && (value == "module" || value == "enum" || value == "type") && cx.stream.match(/^\s*\w/, false)) { | |||
| cx.marked = "keyword" | |||
| if (value == "enum") return cont(enumdef); | |||
| else if (value == "type") return cont(typename, expect("operator"), typeexpr, expect(";")); | |||
| else return cont(pushlex("form"), pattern, expect("{"), pushlex("}"), block, poplex, poplex) | |||
| } else if (isTS && value == "namespace") { | |||
| cx.marked = "keyword" | |||
| return cont(pushlex("form"), expression, statement, poplex) | |||
| } else if (isTS && value == "abstract") { | |||
| cx.marked = "keyword" | |||
| return cont(statement) | |||
| } else { | |||
| return cont(pushlex("stat"), maybelabel); | |||
| } | |||
| } | |||
| if (type == "switch") return cont(pushlex("form"), parenExpr, expect("{"), pushlex("}", "switch"), pushblockcontext, | |||
| block, poplex, poplex, popcontext); | |||
| if (type == "case") return cont(expression, expect(":")); | |||
| if (type == "default") return cont(expect(":")); | |||
| if (type == "catch") return cont(pushlex("form"), pushcontext, expect("("), funarg, expect(")"), | |||
| statement, poplex, popcontext); | |||
| if (type == "class") return cont(pushlex("form"), className, poplex); | |||
| if (type == "catch") return cont(pushlex("form"), pushcontext, maybeCatchBinding, statement, poplex, popcontext); | |||
| if (type == "export") return cont(pushlex("stat"), afterExport, poplex); | |||
| if (type == "import") return cont(pushlex("stat"), afterImport, poplex); | |||
| if (type == "module") return cont(pushlex("form"), pattern, pushlex("}"), expect("{"), block, poplex, poplex) | |||
| if (type == "type") return cont(typeexpr, expect("operator"), typeexpr, expect(";")); | |||
| if (type == "async") return cont(statement) | |||
| if (value == "@") return cont(expression, statement) | |||
| return pass(pushlex("stat"), expression, expect(";"), poplex); | |||
| } | |||
| function expression(type) { | |||
| return expressionInner(type, false); | |||
| function maybeCatchBinding(type) { | |||
| if (type == "(") return cont(funarg, expect(")")) | |||
| } | |||
| function expressionNoComma(type) { | |||
| return expressionInner(type, true); | |||
| function expression(type, value) { | |||
| return expressionInner(type, value, false); | |||
| } | |||
| function expressionNoComma(type, value) { | |||
| return expressionInner(type, value, true); | |||
| } | |||
| function parenExpr(type) { | |||
| if (type != "(") return pass() | |||
| return cont(pushlex(")"), expression, expect(")"), poplex) | |||
| return cont(pushlex(")"), maybeexpression, expect(")"), poplex) | |||
| } | |||
| function expressionInner(type, noComma) { | |||
| function expressionInner(type, value, noComma) { | |||
| if (cx.state.fatArrowAt == cx.stream.start) { | |||
| var body = noComma ? arrowBodyNoComma : arrowBody; | |||
| if (type == "(") return cont(pushcontext, pushlex(")"), commasep(pattern, ")"), poplex, expect("=>"), body, popcontext); | |||
| if (type == "(") return cont(pushcontext, pushlex(")"), commasep(funarg, ")"), poplex, expect("=>"), body, popcontext); | |||
| else if (type == "variable") return pass(pushcontext, pattern, expect("=>"), body, popcontext); | |||
| } | |||
| var maybeop = noComma ? maybeoperatorNoComma : maybeoperatorComma; | |||
| if (atomicTypes.hasOwnProperty(type)) return cont(maybeop); | |||
| if (type == "function") return cont(functiondef, maybeop); | |||
| if (type == "class") return cont(pushlex("form"), classExpression, poplex); | |||
| if (type == "keyword c" || type == "async") return cont(noComma ? maybeexpressionNoComma : maybeexpression); | |||
| if (type == "class" || (isTS && value == "interface")) { cx.marked = "keyword"; return cont(pushlex("form"), classExpression, poplex); } | |||
| if (type == "keyword c" || type == "async") return cont(noComma ? expressionNoComma : expression); | |||
| if (type == "(") return cont(pushlex(")"), maybeexpression, expect(")"), poplex, maybeop); | |||
| if (type == "operator" || type == "spread") return cont(noComma ? expressionNoComma : expression); | |||
| if (type == "[") return cont(pushlex("]"), arrayLiteral, poplex, maybeop); | |||
| @@ -410,13 +452,9 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (type.match(/[;\}\)\],]/)) return pass(); | |||
| return pass(expression); | |||
| } | |||
| function maybeexpressionNoComma(type) { | |||
| if (type.match(/[;\}\)\],]/)) return pass(); | |||
| return pass(expressionNoComma); | |||
| } | |||
| function maybeoperatorComma(type, value) { | |||
| if (type == ",") return cont(expression); | |||
| if (type == ",") return cont(maybeexpression); | |||
| return maybeoperatorNoComma(type, value, false); | |||
| } | |||
| function maybeoperatorNoComma(type, value, noComma) { | |||
| @@ -424,7 +462,9 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| var expr = noComma == false ? expression : expressionNoComma; | |||
| if (type == "=>") return cont(pushcontext, noComma ? arrowBodyNoComma : arrowBody, popcontext); | |||
| if (type == "operator") { | |||
| if (/\+\+|--/.test(value)) return cont(me); | |||
| if (/\+\+|--/.test(value) || isTS && value == "!") return cont(me); | |||
| if (isTS && value == "<" && cx.stream.match(/^([^<>]|<[^<>]*>)*>\s*\(/, false)) | |||
| return cont(pushlex(">"), commasep(typeexpr, ">"), poplex, me); | |||
| if (value == "?") return cont(expression, expect(":"), expr); | |||
| return cont(expr); | |||
| } | |||
| @@ -433,11 +473,17 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (type == "(") return contCommasep(expressionNoComma, ")", "call", me); | |||
| if (type == ".") return cont(property, me); | |||
| if (type == "[") return cont(pushlex("]"), maybeexpression, expect("]"), poplex, me); | |||
| if (isTS && value == "as") { cx.marked = "keyword"; return cont(typeexpr, me) } | |||
| if (type == "regexp") { | |||
| cx.state.lastType = cx.marked = "operator" | |||
| cx.stream.backUp(cx.stream.pos - cx.stream.start - 1) | |||
| return cont(expr) | |||
| } | |||
| } | |||
| function quasi(type, value) { | |||
| if (type != "quasi") return pass(); | |||
| if (value.slice(value.length - 2) != "${") return cont(quasi); | |||
| return cont(expression, continueQuasi); | |||
| return cont(maybeexpression, continueQuasi); | |||
| } | |||
| function continueQuasi(type) { | |||
| if (type == "}") { | |||
| @@ -457,6 +503,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| function maybeTarget(noComma) { | |||
| return function(type) { | |||
| if (type == ".") return cont(noComma ? targetNoComma : target); | |||
| else if (type == "variable" && isTS) return cont(maybeTypeArgs, noComma ? maybeoperatorNoComma : maybeoperatorComma) | |||
| else return pass(noComma ? expressionNoComma : expression); | |||
| }; | |||
| } | |||
| @@ -480,18 +527,25 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| } else if (type == "variable" || cx.style == "keyword") { | |||
| cx.marked = "property"; | |||
| if (value == "get" || value == "set") return cont(getterSetter); | |||
| var m // Work around fat-arrow-detection complication for detecting typescript typed arrow params | |||
| if (isTS && cx.state.fatArrowAt == cx.stream.start && (m = cx.stream.match(/^\s*:\s*/, false))) | |||
| cx.state.fatArrowAt = cx.stream.pos + m[0].length | |||
| return cont(afterprop); | |||
| } else if (type == "number" || type == "string") { | |||
| cx.marked = jsonldMode ? "property" : (cx.style + " property"); | |||
| return cont(afterprop); | |||
| } else if (type == "jsonld-keyword") { | |||
| return cont(afterprop); | |||
| } else if (type == "modifier") { | |||
| } else if (isTS && isModifier(value)) { | |||
| cx.marked = "keyword" | |||
| return cont(objprop) | |||
| } else if (type == "[") { | |||
| return cont(expression, expect("]"), afterprop); | |||
| return cont(expression, maybetype, expect("]"), afterprop); | |||
| } else if (type == "spread") { | |||
| return cont(expression); | |||
| return cont(expressionNoComma, afterprop); | |||
| } else if (value == "*") { | |||
| cx.marked = "keyword"; | |||
| return cont(objprop); | |||
| } else if (type == ":") { | |||
| return pass(afterprop) | |||
| } | |||
| @@ -516,6 +570,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| }, proceed); | |||
| } | |||
| if (type == end || value == end) return cont(); | |||
| if (sep && sep.indexOf(";") > -1) return pass(what) | |||
| return cont(expect(end)); | |||
| } | |||
| return function(type, value) { | |||
| @@ -538,42 +593,105 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (value == "?") return cont(maybetype); | |||
| } | |||
| } | |||
| function typeexpr(type) { | |||
| if (type == "variable") {cx.marked = "variable-3"; return cont(afterType);} | |||
| function maybetypeOrIn(type, value) { | |||
| if (isTS && (type == ":" || value == "in")) return cont(typeexpr) | |||
| } | |||
| function mayberettype(type) { | |||
| if (isTS && type == ":") { | |||
| if (cx.stream.match(/^\s*\w+\s+is\b/, false)) return cont(expression, isKW, typeexpr) | |||
| else return cont(typeexpr) | |||
| } | |||
| } | |||
| function isKW(_, value) { | |||
| if (value == "is") { | |||
| cx.marked = "keyword" | |||
| return cont() | |||
| } | |||
| } | |||
| function typeexpr(type, value) { | |||
| if (value == "keyof" || value == "typeof" || value == "infer" || value == "readonly") { | |||
| cx.marked = "keyword" | |||
| return cont(value == "typeof" ? expressionNoComma : typeexpr) | |||
| } | |||
| if (type == "variable" || value == "void") { | |||
| cx.marked = "type" | |||
| return cont(afterType) | |||
| } | |||
| if (value == "|" || value == "&") return cont(typeexpr) | |||
| if (type == "string" || type == "number" || type == "atom") return cont(afterType); | |||
| if (type == "{") return cont(pushlex("}"), commasep(typeprop, "}", ",;"), poplex) | |||
| if (type == "(") return cont(commasep(typearg, ")"), maybeReturnType) | |||
| if (type == "[") return cont(pushlex("]"), commasep(typeexpr, "]", ","), poplex, afterType) | |||
| if (type == "{") return cont(pushlex("}"), typeprops, poplex, afterType) | |||
| if (type == "(") return cont(commasep(typearg, ")"), maybeReturnType, afterType) | |||
| if (type == "<") return cont(commasep(typeexpr, ">"), typeexpr) | |||
| if (type == "quasi") { return pass(quasiType, afterType); } | |||
| } | |||
| function maybeReturnType(type) { | |||
| if (type == "=>") return cont(typeexpr) | |||
| } | |||
| function typeprops(type) { | |||
| if (type.match(/[\}\)\]]/)) return cont() | |||
| if (type == "," || type == ";") return cont(typeprops) | |||
| return pass(typeprop, typeprops) | |||
| } | |||
| function typeprop(type, value) { | |||
| if (type == "variable" || cx.style == "keyword") { | |||
| cx.marked = "property" | |||
| return cont(typeprop) | |||
| } else if (value == "?") { | |||
| } else if (value == "?" || type == "number" || type == "string") { | |||
| return cont(typeprop) | |||
| } else if (type == ":") { | |||
| return cont(typeexpr) | |||
| } else if (type == "[") { | |||
| return cont(expect("variable"), maybetypeOrIn, expect("]"), typeprop) | |||
| } else if (type == "(") { | |||
| return pass(functiondecl, typeprop) | |||
| } else if (!type.match(/[;\}\)\],]/)) { | |||
| return cont() | |||
| } | |||
| } | |||
| function quasiType(type, value) { | |||
| if (type != "quasi") return pass(); | |||
| if (value.slice(value.length - 2) != "${") return cont(quasiType); | |||
| return cont(typeexpr, continueQuasiType); | |||
| } | |||
| function continueQuasiType(type) { | |||
| if (type == "}") { | |||
| cx.marked = "string-2"; | |||
| cx.state.tokenize = tokenQuasi; | |||
| return cont(quasiType); | |||
| } | |||
| } | |||
| function typearg(type) { | |||
| if (type == "variable") return cont(typearg) | |||
| else if (type == ":") return cont(typeexpr) | |||
| function typearg(type, value) { | |||
| if (type == "variable" && cx.stream.match(/^\s*[?:]/, false) || value == "?") return cont(typearg) | |||
| if (type == ":") return cont(typeexpr) | |||
| if (type == "spread") return cont(typearg) | |||
| return pass(typeexpr) | |||
| } | |||
| function afterType(type, value) { | |||
| if (value == "<") return cont(pushlex(">"), commasep(typeexpr, ">"), poplex, afterType) | |||
| if (value == "|" || type == ".") return cont(typeexpr) | |||
| if (type == "[") return cont(expect("]"), afterType) | |||
| if (value == "|" || type == "." || value == "&") return cont(typeexpr) | |||
| if (type == "[") return cont(typeexpr, expect("]"), afterType) | |||
| if (value == "extends" || value == "implements") { cx.marked = "keyword"; return cont(typeexpr) } | |||
| if (value == "?") return cont(typeexpr, expect(":"), typeexpr) | |||
| } | |||
| function maybeTypeArgs(_, value) { | |||
| if (value == "<") return cont(pushlex(">"), commasep(typeexpr, ">"), poplex, afterType) | |||
| } | |||
| function vardef() { | |||
| function typeparam() { | |||
| return pass(typeexpr, maybeTypeDefault) | |||
| } | |||
| function maybeTypeDefault(_, value) { | |||
| if (value == "=") return cont(typeexpr) | |||
| } | |||
| function vardef(_, value) { | |||
| if (value == "enum") {cx.marked = "keyword"; return cont(enumdef)} | |||
| return pass(pattern, maybetype, maybeAssign, vardefCont); | |||
| } | |||
| function pattern(type, value) { | |||
| if (type == "modifier") return cont(pattern) | |||
| if (isTS && isModifier(value)) { cx.marked = "keyword"; return cont(pattern) } | |||
| if (type == "variable") { register(value); return cont(); } | |||
| if (type == "spread") return cont(pattern); | |||
| if (type == "[") return contCommasep(pattern, "]"); | |||
| if (type == "[") return contCommasep(eltpattern, "]"); | |||
| if (type == "{") return contCommasep(proppattern, "}"); | |||
| } | |||
| function proppattern(type, value) { | |||
| @@ -584,8 +702,12 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (type == "variable") cx.marked = "property"; | |||
| if (type == "spread") return cont(pattern); | |||
| if (type == "}") return pass(); | |||
| if (type == "[") return cont(expression, expect(']'), expect(':'), proppattern); | |||
| return cont(expect(":"), pattern, maybeAssign); | |||
| } | |||
| function eltpattern() { | |||
| return pass(pattern, maybeAssign) | |||
| } | |||
| function maybeAssign(_type, value) { | |||
| if (value == "=") return cont(expressionNoComma); | |||
| } | |||
| @@ -595,34 +717,46 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| function maybeelse(type, value) { | |||
| if (type == "keyword b" && value == "else") return cont(pushlex("form", "else"), statement, poplex); | |||
| } | |||
| function forspec(type) { | |||
| if (type == "(") return cont(pushlex(")"), forspec1, expect(")"), poplex); | |||
| function forspec(type, value) { | |||
| if (value == "await") return cont(forspec); | |||
| if (type == "(") return cont(pushlex(")"), forspec1, poplex); | |||
| } | |||
| function forspec1(type) { | |||
| if (type == "var") return cont(vardef, expect(";"), forspec2); | |||
| if (type == ";") return cont(forspec2); | |||
| if (type == "variable") return cont(formaybeinof); | |||
| return pass(expression, expect(";"), forspec2); | |||
| } | |||
| function formaybeinof(_type, value) { | |||
| if (value == "in" || value == "of") { cx.marked = "keyword"; return cont(expression); } | |||
| return cont(maybeoperatorComma, forspec2); | |||
| if (type == "var") return cont(vardef, forspec2); | |||
| if (type == "variable") return cont(forspec2); | |||
| return pass(forspec2) | |||
| } | |||
| function forspec2(type, value) { | |||
| if (type == ";") return cont(forspec3); | |||
| if (value == "in" || value == "of") { cx.marked = "keyword"; return cont(expression); } | |||
| return pass(expression, expect(";"), forspec3); | |||
| } | |||
| function forspec3(type) { | |||
| if (type != ")") cont(expression); | |||
| if (type == ")") return cont() | |||
| if (type == ";") return cont(forspec2) | |||
| if (value == "in" || value == "of") { cx.marked = "keyword"; return cont(expression, forspec2) } | |||
| return pass(expression, forspec2) | |||
| } | |||
| function functiondef(type, value) { | |||
| if (value == "*") {cx.marked = "keyword"; return cont(functiondef);} | |||
| if (type == "variable") {register(value); return cont(functiondef);} | |||
| if (type == "(") return cont(pushcontext, pushlex(")"), commasep(funarg, ")"), poplex, maybetype, statement, popcontext); | |||
| if (type == "(") return cont(pushcontext, pushlex(")"), commasep(funarg, ")"), poplex, mayberettype, statement, popcontext); | |||
| if (isTS && value == "<") return cont(pushlex(">"), commasep(typeparam, ">"), poplex, functiondef) | |||
| } | |||
| function functiondecl(type, value) { | |||
| if (value == "*") {cx.marked = "keyword"; return cont(functiondecl);} | |||
| if (type == "variable") {register(value); return cont(functiondecl);} | |||
| if (type == "(") return cont(pushcontext, pushlex(")"), commasep(funarg, ")"), poplex, mayberettype, popcontext); | |||
| if (isTS && value == "<") return cont(pushlex(">"), commasep(typeparam, ">"), poplex, functiondecl) | |||
| } | |||
| function typename(type, value) { | |||
| if (type == "keyword" || type == "variable") { | |||
| cx.marked = "type" | |||
| return cont(typename) | |||
| } else if (value == "<") { | |||
| return cont(pushlex(">"), commasep(typeparam, ">"), poplex) | |||
| } | |||
| } | |||
| function funarg(type) { | |||
| function funarg(type, value) { | |||
| if (value == "@") cont(expression, funarg) | |||
| if (type == "spread") return cont(funarg); | |||
| if (isTS && isModifier(value)) { cx.marked = "keyword"; return cont(funarg); } | |||
| if (isTS && type == "this") return cont(maybetype, maybeAssign) | |||
| return pass(pattern, maybetype, maybeAssign); | |||
| } | |||
| function classExpression(type, value) { | |||
| @@ -634,34 +768,44 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (type == "variable") {register(value); return cont(classNameAfter);} | |||
| } | |||
| function classNameAfter(type, value) { | |||
| if (value == "extends" || value == "implements" || (isTS && type == ",")) | |||
| if (value == "<") return cont(pushlex(">"), commasep(typeparam, ">"), poplex, classNameAfter) | |||
| if (value == "extends" || value == "implements" || (isTS && type == ",")) { | |||
| if (value == "implements") cx.marked = "keyword"; | |||
| return cont(isTS ? typeexpr : expression, classNameAfter); | |||
| } | |||
| if (type == "{") return cont(pushlex("}"), classBody, poplex); | |||
| } | |||
| function classBody(type, value) { | |||
| if (type == "async" || | |||
| (type == "variable" && | |||
| (value == "static" || value == "get" || value == "set" || (isTS && isModifier(value))) && | |||
| cx.stream.match(/^\s+[\w$\xa1-\uffff]/, false))) { | |||
| cx.marked = "keyword"; | |||
| return cont(classBody); | |||
| } | |||
| if (type == "variable" || cx.style == "keyword") { | |||
| if ((value == "async" || value == "static" || value == "get" || value == "set" || | |||
| (isTS && (value == "public" || value == "private" || value == "protected" || value == "readonly" || value == "abstract"))) && | |||
| cx.stream.match(/^\s+[\w$\xa1-\uffff]/, false)) { | |||
| cx.marked = "keyword"; | |||
| return cont(classBody); | |||
| } | |||
| cx.marked = "property"; | |||
| return cont(isTS ? classfield : functiondef, classBody); | |||
| return cont(classfield, classBody); | |||
| } | |||
| if (type == "number" || type == "string") return cont(classfield, classBody); | |||
| if (type == "[") | |||
| return cont(expression, expect("]"), isTS ? classfield : functiondef, classBody) | |||
| return cont(expression, maybetype, expect("]"), classfield, classBody) | |||
| if (value == "*") { | |||
| cx.marked = "keyword"; | |||
| return cont(classBody); | |||
| } | |||
| if (type == ";") return cont(classBody); | |||
| if (isTS && type == "(") return pass(functiondecl, classBody) | |||
| if (type == ";" || type == ",") return cont(classBody); | |||
| if (type == "}") return cont(); | |||
| if (value == "@") return cont(expression, classBody) | |||
| } | |||
| function classfield(type, value) { | |||
| if (value == "!") return cont(classfield) | |||
| if (value == "?") return cont(classfield) | |||
| if (type == ":") return cont(typeexpr, maybeAssign) | |||
| return pass(functiondef) | |||
| if (value == "=") return cont(expressionNoComma) | |||
| var context = cx.state.lexical.prev, isInterface = context && context.info == "interface" | |||
| return pass(isInterface ? functiondecl : functiondef) | |||
| } | |||
| function afterExport(type, value) { | |||
| if (value == "*") { cx.marked = "keyword"; return cont(maybeFrom, expect(";")); } | |||
| @@ -675,6 +819,8 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| } | |||
| function afterImport(type) { | |||
| if (type == "string") return cont(); | |||
| if (type == "(") return pass(expression); | |||
| if (type == ".") return pass(maybeoperatorComma); | |||
| return pass(importSpec, maybeMoreImports, maybeFrom); | |||
| } | |||
| function importSpec(type, value) { | |||
| @@ -696,6 +842,12 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| if (type == "]") return cont(); | |||
| return pass(commasep(expressionNoComma, "]")); | |||
| } | |||
| function enumdef() { | |||
| return pass(pushlex("form"), pattern, expect("{"), pushlex("}"), commasep(enummember, "}"), poplex, poplex) | |||
| } | |||
| function enummember() { | |||
| return pass(pattern, maybeAssign); | |||
| } | |||
| function isContinuedStatement(state, textAfter) { | |||
| return state.lastType == "operator" || state.lastType == "," || | |||
| @@ -703,6 +855,12 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| /[,.]/.test(textAfter.charAt(0)); | |||
| } | |||
| function expressionAllowed(stream, state, backUp) { | |||
| return state.tokenize == tokenBase && | |||
| /^(?:operator|sof|keyword [bcd]|case|new|export|default|spread|[\[{}\(,;:]|=>)$/.test(state.lastType) || | |||
| (state.lastType == "quasi" && /\{\s*$/.test(stream.string.slice(0, stream.pos - (backUp || 0)))) | |||
| } | |||
| // Interface | |||
| return { | |||
| @@ -713,7 +871,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| cc: [], | |||
| lexical: new JSLexical((basecolumn || 0) - indentUnit, 0, "block", false), | |||
| localVars: parserConfig.localVars, | |||
| context: parserConfig.localVars && {vars: parserConfig.localVars}, | |||
| context: parserConfig.localVars && new Context(null, null, false), | |||
| indented: basecolumn || 0 | |||
| }; | |||
| if (parserConfig.globalVars && typeof parserConfig.globalVars == "object") | |||
| @@ -736,14 +894,14 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| }, | |||
| indent: function(state, textAfter) { | |||
| if (state.tokenize == tokenComment) return CodeMirror.Pass; | |||
| if (state.tokenize == tokenComment || state.tokenize == tokenQuasi) return CodeMirror.Pass; | |||
| if (state.tokenize != tokenBase) return 0; | |||
| var firstChar = textAfter && textAfter.charAt(0), lexical = state.lexical, top | |||
| // Kludge to prevent 'maybelse' from blocking lexical scope pops | |||
| if (!/^\s*else\b/.test(textAfter)) for (var i = state.cc.length - 1; i >= 0; --i) { | |||
| var c = state.cc[i]; | |||
| if (c == poplex) lexical = lexical.prev; | |||
| else if (c != maybeelse) break; | |||
| else if (c != maybeelse && c != popcontext) break; | |||
| } | |||
| while ((lexical.type == "stat" || lexical.type == "form") && | |||
| (firstChar == "}" || ((top = state.cc[state.cc.length - 1]) && | |||
| @@ -754,7 +912,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| lexical = lexical.prev; | |||
| var type = lexical.type, closing = firstChar == type; | |||
| if (type == "vardef") return lexical.indented + (state.lastType == "operator" || state.lastType == "," ? lexical.info + 1 : 0); | |||
| if (type == "vardef") return lexical.indented + (state.lastType == "operator" || state.lastType == "," ? lexical.info.length + 1 : 0); | |||
| else if (type == "form" && firstChar == "{") return lexical.indented; | |||
| else if (type == "form") return lexical.indented + indentUnit; | |||
| else if (type == "stat") | |||
| @@ -768,6 +926,7 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| electricInput: /^\s*(?:case .*?:|default:|\{|\})$/, | |||
| blockCommentStart: jsonMode ? null : "/*", | |||
| blockCommentEnd: jsonMode ? null : "*/", | |||
| blockCommentContinue: jsonMode ? null : " * ", | |||
| lineComment: jsonMode ? null : "//", | |||
| fold: "brace", | |||
| closeBrackets: "()[]{}''\"\"``", | |||
| @@ -777,9 +936,9 @@ CodeMirror.defineMode("javascript", function(config, parserConfig) { | |||
| jsonMode: jsonMode, | |||
| expressionAllowed: expressionAllowed, | |||
| skipExpression: function(state) { | |||
| var top = state.cc[state.cc.length - 1] | |||
| if (top == expression || top == expressionNoComma) state.cc.pop() | |||
| parseJS(state, "atom", "atom", "true", new CodeMirror.StringStream("", 2, null)) | |||
| } | |||
| }; | |||
| }); | |||
| @@ -791,9 +950,10 @@ CodeMirror.defineMIME("text/ecmascript", "javascript"); | |||
| CodeMirror.defineMIME("application/javascript", "javascript"); | |||
| CodeMirror.defineMIME("application/x-javascript", "javascript"); | |||
| CodeMirror.defineMIME("application/ecmascript", "javascript"); | |||
| CodeMirror.defineMIME("application/json", {name: "javascript", json: true}); | |||
| CodeMirror.defineMIME("application/x-json", {name: "javascript", json: true}); | |||
| CodeMirror.defineMIME("application/ld+json", {name: "javascript", jsonld: true}); | |||
| CodeMirror.defineMIME("application/json", { name: "javascript", json: true }); | |||
| CodeMirror.defineMIME("application/x-json", { name: "javascript", json: true }); | |||
| CodeMirror.defineMIME("application/manifest+json", { name: "javascript", json: true }) | |||
| CodeMirror.defineMIME("application/ld+json", { name: "javascript", jsonld: true }); | |||
| CodeMirror.defineMIME("text/typescript", { name: "javascript", typescript: true }); | |||
| CodeMirror.defineMIME("application/typescript", { name: "javascript", typescript: true }); | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "javascript"); | |||
| @@ -63,6 +63,12 @@ | |||
| MT("import_trailing_comma", | |||
| "[keyword import] {[def foo], [def bar],} [keyword from] [string 'baz']") | |||
| MT("import_dynamic", | |||
| "[keyword import]([string 'baz']).[property then]") | |||
| MT("import_dynamic", | |||
| "[keyword const] [def t] [operator =] [keyword import]([string 'baz']).[property then]") | |||
| MT("const", | |||
| "[keyword function] [def f]() {", | |||
| " [keyword const] [[ [def a], [def b] ]] [operator =] [[ [number 1], [number 2] ]];", | |||
| @@ -71,12 +77,44 @@ | |||
| MT("for/of", | |||
| "[keyword for]([keyword let] [def of] [keyword of] [variable something]) {}"); | |||
| MT("for await", | |||
| "[keyword for] [keyword await]([keyword let] [def of] [keyword of] [variable something]) {}"); | |||
| MT("generator", | |||
| "[keyword function*] [def repeat]([def n]) {", | |||
| " [keyword for]([keyword var] [def i] [operator =] [number 0]; [variable-2 i] [operator <] [variable-2 n]; [operator ++][variable-2 i])", | |||
| " [keyword yield] [variable-2 i];", | |||
| "}"); | |||
| MT("let_scoping", | |||
| "[keyword function] [def scoped]([def n]) {", | |||
| " { [keyword var] [def i]; } [variable-2 i];", | |||
| " { [keyword let] [def j]; [variable-2 j]; } [variable j];", | |||
| " [keyword if] ([atom true]) { [keyword const] [def k]; [variable-2 k]; } [variable k];", | |||
| "}"); | |||
| MT("switch_scoping", | |||
| "[keyword switch] ([variable x]) {", | |||
| " [keyword default]:", | |||
| " [keyword let] [def j];", | |||
| " [keyword return] [variable-2 j]", | |||
| "}", | |||
| "[variable j];") | |||
| MT("leaving_scope", | |||
| "[keyword function] [def a]() {", | |||
| " {", | |||
| " [keyword const] [def x] [operator =] [number 1]", | |||
| " [keyword if] ([atom true]) {", | |||
| " [keyword let] [def y] [operator =] [number 2]", | |||
| " [keyword var] [def z] [operator =] [number 3]", | |||
| " [variable console].[property log]([variable-2 x], [variable-2 y], [variable-2 z])", | |||
| " }", | |||
| " [variable console].[property log]([variable-2 x], [variable y], [variable-2 z])", | |||
| " }", | |||
| " [variable console].[property log]([variable x], [variable y], [variable-2 z])", | |||
| "}") | |||
| MT("quotedStringAddition", | |||
| "[keyword let] [def f] [operator =] [variable a] [operator +] [string 'fatarrow'] [operator +] [variable c];"); | |||
| @@ -89,6 +127,9 @@ | |||
| "[keyword let] [def f] [operator =] ([[ [def a], [def b] ]], [def c]) [operator =>] [variable-2 a] [operator +] [variable-2 c];", | |||
| "[variable c];"); | |||
| MT("fatArrow_stringDefault", | |||
| "([def a], [def b] [operator =] [string 'x\\'y']) [operator =>] [variable-2 a] [operator +] [variable-2 b]") | |||
| MT("spread", | |||
| "[keyword function] [def f]([def a], [meta ...][def b]) {", | |||
| " [variable something]([variable-2 a], [meta ...][variable-2 b]);", | |||
| @@ -123,9 +164,9 @@ | |||
| MT("indent_for", | |||
| "[keyword for] ([keyword var] [def i] [operator =] [number 0];", | |||
| " [variable i] [operator <] [number 100];", | |||
| " [variable i][operator ++])", | |||
| " [variable doSomething]([variable i]);", | |||
| " [variable-2 i] [operator <] [number 100];", | |||
| " [variable-2 i][operator ++])", | |||
| " [variable doSomething]([variable-2 i]);", | |||
| "[keyword debugger];"); | |||
| MT("indent_c_style", | |||
| @@ -188,6 +229,12 @@ | |||
| " [keyword return] [variable-2 x];", | |||
| "}"); | |||
| MT( | |||
| "param_destructuring", | |||
| "[keyword function] [def foo]([def x] [operator =] [string-2 `foo${][number 10][string-2 }bar`]) {", | |||
| " [keyword return] [variable-2 x];", | |||
| "}"); | |||
| MT("new_target", | |||
| "[keyword function] [def F]([def target]) {", | |||
| " [keyword if] ([variable-2 target] [operator &&] [keyword new].[keyword target].[property name]) {", | |||
| @@ -205,7 +252,7 @@ | |||
| MT("async_object", | |||
| "[keyword let] [def obj] [operator =] { [property async]: [atom false] };"); | |||
| // async be highlighet as keyword and foo as def, but it requires potentially expensive look-ahead. See #4173 | |||
| // async be highlighted as keyword and foo as def, but it requires potentially expensive look-ahead. See #4173 | |||
| MT("async_object_function", | |||
| "[keyword let] [def obj] [operator =] { [property async] [property foo]([def args]) { [keyword return] [atom true]; } };"); | |||
| @@ -226,21 +273,73 @@ | |||
| " [property method]: [string 'GET']", | |||
| "});"); | |||
| MT("async_variable", | |||
| "[keyword const] [def async] [operator =] {[property a]: [number 1]};", | |||
| "[keyword const] [def foo] [operator =] [string-2 `bar ${][variable async].[property a][string-2 }`];") | |||
| MT("bigint", "[number 1n] [operator +] [number 0x1afn] [operator +] [number 0o064n] [operator +] [number 0b100n];") | |||
| MT("async_comment", | |||
| "[keyword async] [comment /**/] [keyword function] [def foo]([def args]) { [keyword return] [atom true]; }"); | |||
| MT("indent_switch", | |||
| "[keyword switch] ([variable x]) {", | |||
| " [keyword default]:", | |||
| " [keyword return] [number 2]", | |||
| "}") | |||
| MT("regexp_corner_case", | |||
| "[operator +]{} [operator /] [atom undefined];", | |||
| "[[[meta ...][string-2 /\\//] ]];", | |||
| "[keyword void] [string-2 /\\//];", | |||
| "[keyword do] [string-2 /\\//]; [keyword while] ([number 0]);", | |||
| "[keyword if] ([number 0]) {} [keyword else] [string-2 /\\//];", | |||
| "[string-2 `${][variable async][operator ++][string-2 }//`];", | |||
| "[string-2 `${]{} [operator /] [string-2 /\\//}`];") | |||
| MT("return_eol", | |||
| "[keyword return]", | |||
| "{} [string-2 /5/]") | |||
| MT("numeric separator", | |||
| "[number 123_456];", | |||
| "[number 0xdead_c0de];", | |||
| "[number 0o123_456];", | |||
| "[number 0b1101_1101];", | |||
| "[number .123_456e0_1];", | |||
| "[number 1E+123_456];", | |||
| "[number 12_34_56n];") | |||
| MT("underscore property", | |||
| "[variable something].[property _property];", | |||
| "[variable something].[property _123];", | |||
| "[variable something].[property _for];", | |||
| "[variable _for];", | |||
| "[variable _123];") | |||
| MT("private properties", | |||
| "[keyword class] [def C] {", | |||
| " [property #x] [operator =] [number 2];", | |||
| " [property #read]() {", | |||
| " [keyword return] [keyword this].[property #x]", | |||
| " }", | |||
| "}") | |||
| var ts_mode = CodeMirror.getMode({indentUnit: 2}, "application/typescript") | |||
| function TS(name) { | |||
| test.mode(name, ts_mode, Array.prototype.slice.call(arguments, 1)) | |||
| } | |||
| TS("extend_type", | |||
| "[keyword class] [def Foo] [keyword extends] [variable-3 Some][operator <][variable-3 Type][operator >] {}") | |||
| TS("typescript_extend_type", | |||
| "[keyword class] [def Foo] [keyword extends] [type Some][operator <][type Type][operator >] {}") | |||
| TS("arrow_type", | |||
| "[keyword let] [def x]: ([variable arg]: [variable-3 Type]) [operator =>] [variable-3 ReturnType]") | |||
| TS("typescript_arrow_type", | |||
| "[keyword let] [def x]: ([variable arg]: [type Type]) [operator =>] [type ReturnType]") | |||
| TS("typescript_class", | |||
| "[keyword class] [def Foo] {", | |||
| " [keyword public] [keyword static] [property main]() {}", | |||
| " [keyword private] [property _foo]: [variable-3 string];", | |||
| " [keyword private] [property _foo]: [type string];", | |||
| "}") | |||
| TS("typescript_literal_types", | |||
| @@ -249,46 +348,139 @@ | |||
| " [property truthy]: [string 'true'] [operator |] [number 1] [operator |] [atom true];", | |||
| " [property falsy]: [string 'false'] [operator |] [number 0] [operator |] [atom false];", | |||
| "}", | |||
| "[keyword interface] [def MyInstance] [keyword extends] [variable-3 Sequelize].[variable-3 Instance] [operator <] [variable-3 MyAttributes] [operator >] {", | |||
| " [property rawAttributes]: [variable-3 MyAttributes];", | |||
| "[keyword interface] [def MyInstance] [keyword extends] [type Sequelize].[type Instance] [operator <] [type MyAttributes] [operator >] {", | |||
| " [property rawAttributes]: [type MyAttributes];", | |||
| " [property truthy]: [string 'true'] [operator |] [number 1] [operator |] [atom true];", | |||
| " [property falsy]: [string 'false'] [operator |] [number 0] [operator |] [atom false];", | |||
| "}") | |||
| TS("typescript_extend_operators", | |||
| "[keyword export] [keyword interface] [def UserModel] [keyword extends]", | |||
| " [variable-3 Sequelize].[variable-3 Model] [operator <] [variable-3 UserInstance], [variable-3 UserAttributes] [operator >] {", | |||
| " [type Sequelize].[type Model] [operator <] [type UserInstance], [type UserAttributes] [operator >] {", | |||
| " [property findById]: (", | |||
| " [variable userId]: [variable-3 number]", | |||
| " ) [operator =>] [variable-3 Promise] [operator <] [variable-3 Array] [operator <] { [property id], [property name] } [operator >>];", | |||
| " [variable userId]: [type number]", | |||
| " ) [operator =>] [type Promise] [operator <] [type Array] [operator <] { [property id], [property name] } [operator >>];", | |||
| " [property updateById]: (", | |||
| " [variable userId]: [variable-3 number],", | |||
| " [variable isActive]: [variable-3 boolean]", | |||
| " ) [operator =>] [variable-3 Promise] [operator <] [variable-3 AccountHolderNotificationPreferenceInstance] [operator >];", | |||
| " [variable userId]: [type number],", | |||
| " [variable isActive]: [type boolean]", | |||
| " ) [operator =>] [type Promise] [operator <] [type AccountHolderNotificationPreferenceInstance] [operator >];", | |||
| " }") | |||
| TS("typescript_interface_with_const", | |||
| "[keyword const] [def hello]: {", | |||
| " [property prop1][operator ?]: [variable-3 string];", | |||
| " [property prop2][operator ?]: [variable-3 string];", | |||
| " [property prop1][operator ?]: [type string];", | |||
| " [property prop2][operator ?]: [type string];", | |||
| "} [operator =] {};") | |||
| TS("typescript_double_extend", | |||
| "[keyword export] [keyword interface] [def UserAttributes] {", | |||
| " [property id][operator ?]: [variable-3 number];", | |||
| " [property createdAt][operator ?]: [variable-3 Date];", | |||
| " [property id][operator ?]: [type number];", | |||
| " [property createdAt][operator ?]: [type Date];", | |||
| "}", | |||
| "[keyword export] [keyword interface] [def UserInstance] [keyword extends] [variable-3 Sequelize].[variable-3 Instance][operator <][variable-3 UserAttributes][operator >], [variable-3 UserAttributes] {", | |||
| " [property id]: [variable-3 number];", | |||
| " [property createdAt]: [variable-3 Date];", | |||
| "[keyword export] [keyword interface] [def UserInstance] [keyword extends] [type Sequelize].[type Instance][operator <][type UserAttributes][operator >], [type UserAttributes] {", | |||
| " [property id]: [type number];", | |||
| " [property createdAt]: [type Date];", | |||
| "}"); | |||
| TS("typescript_index_signature", | |||
| "[keyword interface] [def A] {", | |||
| " [[ [variable prop]: [variable-3 string] ]]: [variable-3 any];", | |||
| " [property prop1]: [variable-3 any];", | |||
| " [[ [variable prop]: [type string] ]]: [type any];", | |||
| " [property prop1]: [type any];", | |||
| "}"); | |||
| TS("typescript_generic_class", | |||
| "[keyword class] [def Foo][operator <][type T][operator >] {", | |||
| " [property bar]() {}", | |||
| " [property foo](): [type Foo] {}", | |||
| "}") | |||
| TS("typescript_type_when_keyword", | |||
| "[keyword export] [keyword type] [type AB] [operator =] [type A] [operator |] [type B];", | |||
| "[keyword type] [type Flags] [operator =] {", | |||
| " [property p1]: [type string];", | |||
| " [property p2]: [type boolean];", | |||
| "};") | |||
| TS("typescript_type_when_not_keyword", | |||
| "[keyword class] [def HasType] {", | |||
| " [property type]: [type string];", | |||
| " [property constructor]([def type]: [type string]) {", | |||
| " [keyword this].[property type] [operator =] [variable-2 type];", | |||
| " }", | |||
| " [property setType]({ [def type] }: { [property type]: [type string]; }) {", | |||
| " [keyword this].[property type] [operator =] [variable-2 type];", | |||
| " }", | |||
| "}") | |||
| TS("typescript_function_generics", | |||
| "[keyword function] [def a]() {}", | |||
| "[keyword function] [def b][operator <][type IA] [keyword extends] [type object], [type IB] [keyword extends] [type object][operator >]() {}", | |||
| "[keyword function] [def c]() {}") | |||
| TS("typescript_complex_return_type", | |||
| "[keyword function] [def A]() {", | |||
| " [keyword return] [keyword this].[property property];", | |||
| "}", | |||
| "[keyword function] [def B](): [type Promise][operator <]{ [[ [variable key]: [type string] ]]: [type any] } [operator |] [atom null][operator >] {", | |||
| " [keyword return] [keyword this].[property property];", | |||
| "}") | |||
| TS("typescript_complex_type_casting", | |||
| "[keyword const] [def giftpay] [operator =] [variable config].[property get]([string 'giftpay']) [keyword as] { [[ [variable platformUuid]: [type string] ]]: { [property version]: [type number]; [property apiCode]: [type string]; } };") | |||
| TS("typescript_keyof", | |||
| "[keyword function] [def x][operator <][type T] [keyword extends] [keyword keyof] [type X][operator >]([def a]: [type T]) {", | |||
| " [keyword return]") | |||
| TS("typescript_new_typeargs", | |||
| "[keyword let] [def x] [operator =] [keyword new] [variable Map][operator <][type string], [type Date][operator >]([string-2 `foo${][variable bar][string-2 }`])") | |||
| TS("modifiers", | |||
| "[keyword class] [def Foo] {", | |||
| " [keyword public] [keyword abstract] [property bar]() {}", | |||
| " [property constructor]([keyword readonly] [keyword private] [def x]) {}", | |||
| "}") | |||
| TS("arrow prop", | |||
| "({[property a]: [def p] [operator =>] [variable-2 p]})") | |||
| TS("generic in function call", | |||
| "[keyword this].[property a][operator <][type Type][operator >]([variable foo]);", | |||
| "[keyword this].[property a][operator <][variable Type][operator >][variable foo];") | |||
| TS("type guard", | |||
| "[keyword class] [def Appler] {", | |||
| " [keyword static] [property assertApple]([def fruit]: [type Fruit]): [variable-2 fruit] [keyword is] [type Apple] {", | |||
| " [keyword if] ([operator !]([variable-2 fruit] [keyword instanceof] [variable Apple]))", | |||
| " [keyword throw] [keyword new] [variable Error]();", | |||
| " }", | |||
| "}") | |||
| TS("type as variable", | |||
| "[variable type] [operator =] [variable x] [keyword as] [type Bar];"); | |||
| TS("enum body", | |||
| "[keyword export] [keyword const] [keyword enum] [def CodeInspectionResultType] {", | |||
| " [def ERROR] [operator =] [string 'problem_type_error'],", | |||
| " [def WARNING] [operator =] [string 'problem_type_warning'],", | |||
| " [def META],", | |||
| "}") | |||
| TS("parenthesized type", | |||
| "[keyword class] [def Foo] {", | |||
| " [property x] [operator =] [keyword new] [variable A][operator <][type B], [type string][operator |](() [operator =>] [type void])[operator >]();", | |||
| " [keyword private] [property bar]();", | |||
| "}") | |||
| TS("abstract class", | |||
| "[keyword export] [keyword abstract] [keyword class] [def Foo] {}") | |||
| TS("interface without semicolons", | |||
| "[keyword interface] [def Foo] {", | |||
| " [property greet]([def x]: [type int]): [type blah]", | |||
| " [property bar]: [type void]", | |||
| "}") | |||
| var jsonld_mode = CodeMirror.getMode( | |||
| {indentUnit: 2}, | |||
| {name: "javascript", jsonld: true} | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "php"); | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function() { | |||
| var mode = CodeMirror.getMode({indentUnit: 2}, "xml"), mname = "xml"; | |||
| @@ -1,5 +1,5 @@ | |||
| // CodeMirror, copyright (c) by Marijn Haverbeke and others | |||
| // Distributed under an MIT license: http://codemirror.net/LICENSE | |||
| // Distributed under an MIT license: https://codemirror.net/5/LICENSE | |||
| (function(mod) { | |||
| if (typeof exports == "object" && typeof module == "object") // CommonJS | |||
| @@ -52,6 +52,7 @@ var xmlConfig = { | |||
| doNotIndent: {}, | |||
| allowUnquoted: false, | |||
| allowMissing: false, | |||
| allowMissingTagName: false, | |||
| caseFold: false | |||
| } | |||
| @@ -162,8 +163,9 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| stream.next(); | |||
| } | |||
| return style; | |||
| }; | |||
| } | |||
| } | |||
| function doctype(depth) { | |||
| return function(stream, state) { | |||
| var ch; | |||
| @@ -185,9 +187,13 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| }; | |||
| } | |||
| function lower(tagName) { | |||
| return tagName && tagName.toLowerCase(); | |||
| } | |||
| function Context(state, tagName, startOfLine) { | |||
| this.prev = state.context; | |||
| this.tagName = tagName; | |||
| this.tagName = tagName || ""; | |||
| this.indent = state.indented; | |||
| this.startOfLine = startOfLine; | |||
| if (config.doNotIndent.hasOwnProperty(tagName) || (state.context && state.context.noIndent)) | |||
| @@ -203,8 +209,8 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| return; | |||
| } | |||
| parentTagName = state.context.tagName; | |||
| if (!config.contextGrabbers.hasOwnProperty(parentTagName) || | |||
| !config.contextGrabbers[parentTagName].hasOwnProperty(nextTagName)) { | |||
| if (!config.contextGrabbers.hasOwnProperty(lower(parentTagName)) || | |||
| !config.contextGrabbers[lower(parentTagName)].hasOwnProperty(lower(nextTagName))) { | |||
| return; | |||
| } | |||
| popContext(state); | |||
| @@ -226,6 +232,9 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| state.tagName = stream.current(); | |||
| setStyle = "tag"; | |||
| return attrState; | |||
| } else if (config.allowMissingTagName && type == "endTag") { | |||
| setStyle = "tag bracket"; | |||
| return attrState(type, stream, state); | |||
| } else { | |||
| setStyle = "error"; | |||
| return tagNameState; | |||
| @@ -235,7 +244,7 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| if (type == "word") { | |||
| var tagName = stream.current(); | |||
| if (state.context && state.context.tagName != tagName && | |||
| config.implicitlyClosed.hasOwnProperty(state.context.tagName)) | |||
| config.implicitlyClosed.hasOwnProperty(lower(state.context.tagName))) | |||
| popContext(state); | |||
| if ((state.context && state.context.tagName == tagName) || config.matchClosing === false) { | |||
| setStyle = "tag"; | |||
| @@ -244,6 +253,9 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| setStyle = "tag error"; | |||
| return closeStateErr; | |||
| } | |||
| } else if (config.allowMissingTagName && type == "endTag") { | |||
| setStyle = "tag bracket"; | |||
| return closeState(type, stream, state); | |||
| } else { | |||
| setStyle = "error"; | |||
| return closeStateErr; | |||
| @@ -271,7 +283,7 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| var tagName = state.tagName, tagStart = state.tagStart; | |||
| state.tagName = state.tagStart = null; | |||
| if (type == "selfcloseTag" || | |||
| config.autoSelfClosers.hasOwnProperty(tagName)) { | |||
| config.autoSelfClosers.hasOwnProperty(lower(tagName))) { | |||
| maybePopContext(state, tagName); | |||
| } else { | |||
| maybePopContext(state, tagName); | |||
| @@ -351,7 +363,7 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| if (context.tagName == tagAfter[2]) { | |||
| context = context.prev; | |||
| break; | |||
| } else if (config.implicitlyClosed.hasOwnProperty(context.tagName)) { | |||
| } else if (config.implicitlyClosed.hasOwnProperty(lower(context.tagName))) { | |||
| context = context.prev; | |||
| } else { | |||
| break; | |||
| @@ -359,8 +371,8 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| } | |||
| } else if (tagAfter) { // Opening tag spotted | |||
| while (context) { | |||
| var grabbers = config.contextGrabbers[context.tagName]; | |||
| if (grabbers && grabbers.hasOwnProperty(tagAfter[2])) | |||
| var grabbers = config.contextGrabbers[lower(context.tagName)]; | |||
| if (grabbers && grabbers.hasOwnProperty(lower(tagAfter[2]))) | |||
| context = context.prev; | |||
| else | |||
| break; | |||
| @@ -382,6 +394,17 @@ CodeMirror.defineMode("xml", function(editorConf, config_) { | |||
| skipAttribute: function(state) { | |||
| if (state.state == attrValueState) | |||
| state.state = attrState | |||
| }, | |||
| xmlCurrentTag: function(state) { | |||
| return state.tagName ? {name: state.tagName, close: state.type == "closeTag"} : null | |||
| }, | |||
| xmlCurrentContext: function(state) { | |||
| var context = [] | |||
| for (var cx = state.context; cx; cx = cx.prev) | |||
| context.push(cx.tagName) | |||
| return context.reverse() | |||
| } | |||
| }; | |||
| }); | |||