@codemirror/view 6.1.4 → 6.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +30 -0
- package/dist/index.cjs +103 -45
- package/dist/index.d.ts +15 -3
- package/dist/index.js +103 -45
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,33 @@
|
|
|
1
|
+
## 6.2.2 (2022-08-31)
|
|
2
|
+
|
|
3
|
+
### Bug fixes
|
|
4
|
+
|
|
5
|
+
Don't reset the selection for selection change events that were suppressed by a node view.
|
|
6
|
+
|
|
7
|
+
## 6.2.1 (2022-08-25)
|
|
8
|
+
|
|
9
|
+
### Bug fixes
|
|
10
|
+
|
|
11
|
+
Don't use the global `document` variable to track focus, since that doesn't work in another window/frame.
|
|
12
|
+
|
|
13
|
+
Fix an issue where key handlers that didn't return true were sometimes called twice for the same keypress.
|
|
14
|
+
|
|
15
|
+
Avoid editing glitches when using deletion keys like ctrl-d on iOS.
|
|
16
|
+
|
|
17
|
+
Properly treat characters from the 'Arabic Presentation Forms-A' Unicode block as right-to-left.
|
|
18
|
+
|
|
19
|
+
Work around a Firefox bug that inserts text at the wrong point for specific cross-line selections.
|
|
20
|
+
|
|
21
|
+
## 6.2.0 (2022-08-05)
|
|
22
|
+
|
|
23
|
+
### Bug fixes
|
|
24
|
+
|
|
25
|
+
Fix a bug where `posAtCoords` would return the wrong results for positions to the right of wrapped lines.
|
|
26
|
+
|
|
27
|
+
### New features
|
|
28
|
+
|
|
29
|
+
The new `EditorView.setRoot` method can be used when an editor view is moved to a new document or shadow root.
|
|
30
|
+
|
|
1
31
|
## 6.1.4 (2022-08-04)
|
|
2
32
|
|
|
3
33
|
### Bug fixes
|
package/dist/index.cjs
CHANGED
|
@@ -22,8 +22,8 @@ function getSelection(root) {
|
|
|
22
22
|
function contains(dom, node) {
|
|
23
23
|
return node ? dom == node || dom.contains(node.nodeType != 1 ? node.parentNode : node) : false;
|
|
24
24
|
}
|
|
25
|
-
function deepActiveElement() {
|
|
26
|
-
let elt =
|
|
25
|
+
function deepActiveElement(doc) {
|
|
26
|
+
let elt = doc.activeElement;
|
|
27
27
|
while (elt && elt.shadowRoot)
|
|
28
28
|
elt = elt.shadowRoot.activeElement;
|
|
29
29
|
return elt;
|
|
@@ -762,7 +762,7 @@ class MarkView extends ContentView {
|
|
|
762
762
|
return new MarkView(this.mark, result, length);
|
|
763
763
|
}
|
|
764
764
|
domAtPos(pos) {
|
|
765
|
-
return inlineDOMAtPos(this
|
|
765
|
+
return inlineDOMAtPos(this, pos);
|
|
766
766
|
}
|
|
767
767
|
coordsAt(pos, side) {
|
|
768
768
|
return coordsInChildren(this, pos, side);
|
|
@@ -913,11 +913,14 @@ class CompositionView extends WidgetView {
|
|
|
913
913
|
// offset.
|
|
914
914
|
function scanCompositionTree(pos, side, view, text, enterView, fromText) {
|
|
915
915
|
if (view instanceof MarkView) {
|
|
916
|
-
for (let child
|
|
917
|
-
let
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
916
|
+
for (let child = view.dom.firstChild; child; child = child.nextSibling) {
|
|
917
|
+
let desc = ContentView.get(child);
|
|
918
|
+
if (!desc)
|
|
919
|
+
return fromText(pos, side);
|
|
920
|
+
let hasComp = contains(child, text);
|
|
921
|
+
let len = desc.length + (hasComp ? text.nodeValue.length : 0);
|
|
922
|
+
if (pos < len || pos == len && desc.getSide() <= 0)
|
|
923
|
+
return hasComp ? scanCompositionTree(pos, side, desc, text, enterView, fromText) : enterView(desc, pos, side);
|
|
921
924
|
pos -= len;
|
|
922
925
|
}
|
|
923
926
|
return enterView(view, view.length, -1);
|
|
@@ -1007,8 +1010,8 @@ function inlineSiblingRect(view, side) {
|
|
|
1007
1010
|
}
|
|
1008
1011
|
return undefined;
|
|
1009
1012
|
}
|
|
1010
|
-
function inlineDOMAtPos(
|
|
1011
|
-
let i = 0;
|
|
1013
|
+
function inlineDOMAtPos(parent, pos) {
|
|
1014
|
+
let dom = parent.dom, { children } = parent, i = 0;
|
|
1012
1015
|
for (let off = 0; i < children.length; i++) {
|
|
1013
1016
|
let child = children[i], end = off + child.length;
|
|
1014
1017
|
if (end == off && child.getSide() <= 0)
|
|
@@ -1019,10 +1022,16 @@ function inlineDOMAtPos(dom, children, pos) {
|
|
|
1019
1022
|
break;
|
|
1020
1023
|
off = end;
|
|
1021
1024
|
}
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1025
|
+
// if (i) return DOMPos.after(children[i - 1].dom!)
|
|
1026
|
+
for (let j = i; j > 0; j--) {
|
|
1027
|
+
let prev = children[j - 1];
|
|
1028
|
+
if (prev.dom.parentNode == dom)
|
|
1029
|
+
return prev.domAtPos(prev.length);
|
|
1030
|
+
}
|
|
1031
|
+
for (let j = i; j < children.length; j++) {
|
|
1032
|
+
let next = children[j];
|
|
1033
|
+
if (next.dom.parentNode == dom)
|
|
1034
|
+
return next.domAtPos(0);
|
|
1026
1035
|
}
|
|
1027
1036
|
return new DOMPos(dom, 0);
|
|
1028
1037
|
}
|
|
@@ -1431,7 +1440,7 @@ class LineView extends ContentView {
|
|
|
1431
1440
|
this.attrs = combineAttrs({ class: cls }, this.attrs || {});
|
|
1432
1441
|
}
|
|
1433
1442
|
domAtPos(pos) {
|
|
1434
|
-
return inlineDOMAtPos(this
|
|
1443
|
+
return inlineDOMAtPos(this, pos);
|
|
1435
1444
|
}
|
|
1436
1445
|
reuseDOM(node) {
|
|
1437
1446
|
if (node.nodeName == "DIV") {
|
|
@@ -2077,9 +2086,10 @@ function charType(ch) {
|
|
|
2077
2086
|
0x600 <= ch && ch <= 0x6f9 ? ArabicTypes[ch - 0x600] :
|
|
2078
2087
|
0x6ee <= ch && ch <= 0x8ac ? 4 /* AL */ :
|
|
2079
2088
|
0x2000 <= ch && ch <= 0x200b ? 256 /* NI */ :
|
|
2080
|
-
ch
|
|
2089
|
+
0xfb50 <= ch && ch <= 0xfdff ? 4 /* AL */ :
|
|
2090
|
+
ch == 0x200c ? 256 /* NI */ : 1 /* L */;
|
|
2081
2091
|
}
|
|
2082
|
-
const BidiRE = /[\u0590-\u05f4\u0600-\u06ff\u0700-\u08ac]/;
|
|
2092
|
+
const BidiRE = /[\u0590-\u05f4\u0600-\u06ff\u0700-\u08ac\ufb50-\ufdff]/;
|
|
2083
2093
|
/**
|
|
2084
2094
|
Represents a contiguous range of text that has a single direction
|
|
2085
2095
|
(as in left-to-right or right-to-left).
|
|
@@ -2483,7 +2493,6 @@ class DocView extends ContentView {
|
|
|
2483
2493
|
this.updateDeco();
|
|
2484
2494
|
this.updateInner([new ChangedRange(0, 0, 0, view.state.doc.length)], 0);
|
|
2485
2495
|
}
|
|
2486
|
-
get root() { return this.view.root; }
|
|
2487
2496
|
get editorView() { return this.view; }
|
|
2488
2497
|
get length() { return this.view.state.doc.length; }
|
|
2489
2498
|
// Update the document view to a given state. scrollIntoView can be
|
|
@@ -2606,7 +2615,7 @@ class DocView extends ContentView {
|
|
|
2606
2615
|
this.dom.blur();
|
|
2607
2616
|
this.dom.focus({ preventScroll: true });
|
|
2608
2617
|
}
|
|
2609
|
-
let rawSel = getSelection(this.root);
|
|
2618
|
+
let rawSel = getSelection(this.view.root);
|
|
2610
2619
|
if (!rawSel) ;
|
|
2611
2620
|
else if (main.empty) {
|
|
2612
2621
|
// Work around https://bugzilla.mozilla.org/show_bug.cgi?id=1612076
|
|
@@ -2649,7 +2658,7 @@ class DocView extends ContentView {
|
|
|
2649
2658
|
if (this.compositionDeco.size)
|
|
2650
2659
|
return;
|
|
2651
2660
|
let cursor = this.view.state.selection.main;
|
|
2652
|
-
let sel = getSelection(this.root);
|
|
2661
|
+
let sel = getSelection(this.view.root);
|
|
2653
2662
|
if (!sel || !cursor.empty || !cursor.assoc || !sel.modify)
|
|
2654
2663
|
return;
|
|
2655
2664
|
let line = LineView.find(this, cursor.head);
|
|
@@ -2666,7 +2675,7 @@ class DocView extends ContentView {
|
|
|
2666
2675
|
sel.modify("move", cursor.assoc < 0 ? "forward" : "backward", "lineboundary");
|
|
2667
2676
|
}
|
|
2668
2677
|
mayControlSelection() {
|
|
2669
|
-
let active = this.root.activeElement;
|
|
2678
|
+
let active = this.view.root.activeElement;
|
|
2670
2679
|
return active == this.dom ||
|
|
2671
2680
|
hasSelection(this.dom, this.view.observer.selectionRange) && !(active && this.dom.contains(active));
|
|
2672
2681
|
}
|
|
@@ -3019,7 +3028,7 @@ function upBot(rect, bottom) {
|
|
|
3019
3028
|
return bottom > rect.bottom ? { top: rect.top, left: rect.left, right: rect.right, bottom } : rect;
|
|
3020
3029
|
}
|
|
3021
3030
|
function domPosAtCoords(parent, x, y) {
|
|
3022
|
-
let closest, closestRect, closestX, closestY;
|
|
3031
|
+
let closest, closestRect, closestX, closestY, closestOverlap = false;
|
|
3023
3032
|
let above, below, aboveRect, belowRect;
|
|
3024
3033
|
for (let child = parent.firstChild; child; child = child.nextSibling) {
|
|
3025
3034
|
let rects = clientRectsFor(child);
|
|
@@ -3035,6 +3044,7 @@ function domPosAtCoords(parent, x, y) {
|
|
|
3035
3044
|
closestRect = rect;
|
|
3036
3045
|
closestX = dx;
|
|
3037
3046
|
closestY = dy;
|
|
3047
|
+
closestOverlap = !dx || (dx > 0 ? i < rects.length - 1 : i > 0);
|
|
3038
3048
|
}
|
|
3039
3049
|
if (dx == 0) {
|
|
3040
3050
|
if (y > rect.bottom && (!aboveRect || aboveRect.bottom < rect.bottom)) {
|
|
@@ -3067,7 +3077,7 @@ function domPosAtCoords(parent, x, y) {
|
|
|
3067
3077
|
let clipX = Math.max(closestRect.left, Math.min(closestRect.right, x));
|
|
3068
3078
|
if (closest.nodeType == 3)
|
|
3069
3079
|
return domPosInText(closest, clipX, y);
|
|
3070
|
-
if (
|
|
3080
|
+
if (closestOverlap && closest.contentEditable != "false")
|
|
3071
3081
|
return domPosAtCoords(closest, clipX, y);
|
|
3072
3082
|
let offset = Array.prototype.indexOf.call(parent.childNodes, closest) +
|
|
3073
3083
|
(x >= (closestRect.left + closestRect.right) / 2 ? 1 : 0);
|
|
@@ -3164,7 +3174,8 @@ function posAtCoords(view, { x, y }, precise, bias = -1) {
|
|
|
3164
3174
|
let range = doc.caretRangeFromPoint(x, y);
|
|
3165
3175
|
if (range) {
|
|
3166
3176
|
({ startContainer: node, startOffset: offset } = range);
|
|
3167
|
-
if (
|
|
3177
|
+
if (!view.contentDOM.contains(node) ||
|
|
3178
|
+
browser.safari && isSuspiciousSafariCaretResult(node, offset, x) ||
|
|
3168
3179
|
browser.chrome && isSuspiciousChromeCaretResult(node, offset, x))
|
|
3169
3180
|
node = undefined;
|
|
3170
3181
|
}
|
|
@@ -3457,9 +3468,10 @@ class InputState {
|
|
|
3457
3468
|
// applyDOMChange, notify key handlers of it and reset to
|
|
3458
3469
|
// the state they produce.
|
|
3459
3470
|
let pending;
|
|
3460
|
-
if (browser.ios &&
|
|
3461
|
-
|
|
3462
|
-
|
|
3471
|
+
if (browser.ios && !event.synthetic && !event.altKey && !event.metaKey &&
|
|
3472
|
+
((pending = PendingKeys.find(key => key.keyCode == event.keyCode)) && !event.ctrlKey ||
|
|
3473
|
+
EmacsyPendingKeys.indexOf(event.key) > -1 && event.ctrlKey && !event.shiftKey)) {
|
|
3474
|
+
this.pendingIOSKey = pending || event;
|
|
3463
3475
|
setTimeout(() => this.flushIOSKey(view), 250);
|
|
3464
3476
|
return true;
|
|
3465
3477
|
}
|
|
@@ -3514,6 +3526,7 @@ const PendingKeys = [
|
|
|
3514
3526
|
{ key: "Enter", keyCode: 13, inputType: "insertParagraph" },
|
|
3515
3527
|
{ key: "Delete", keyCode: 46, inputType: "deleteContentForward" }
|
|
3516
3528
|
];
|
|
3529
|
+
const EmacsyPendingKeys = "dthko";
|
|
3517
3530
|
// Key codes for modifier keys
|
|
3518
3531
|
const modifierCodes = [16, 17, 18, 20, 91, 92, 224, 225];
|
|
3519
3532
|
class MouseSelection {
|
|
@@ -5378,6 +5391,7 @@ const baseTheme$1 = buildTheme("." + baseThemeID, {
|
|
|
5378
5391
|
".cm-widgetBuffer": {
|
|
5379
5392
|
verticalAlign: "text-top",
|
|
5380
5393
|
height: "1em",
|
|
5394
|
+
width: 0,
|
|
5381
5395
|
display: "inline"
|
|
5382
5396
|
},
|
|
5383
5397
|
".cm-placeholder": {
|
|
@@ -5487,7 +5501,9 @@ class DOMObserver {
|
|
|
5487
5501
|
this.flushSoon();
|
|
5488
5502
|
};
|
|
5489
5503
|
this.onSelectionChange = this.onSelectionChange.bind(this);
|
|
5490
|
-
|
|
5504
|
+
this.onResize = this.onResize.bind(this);
|
|
5505
|
+
this.onPrint = this.onPrint.bind(this);
|
|
5506
|
+
this.onScroll = this.onScroll.bind(this);
|
|
5491
5507
|
if (typeof ResizeObserver == "function") {
|
|
5492
5508
|
this.resize = new ResizeObserver(() => {
|
|
5493
5509
|
if (this.view.docView.lastUpdate < Date.now() - 75)
|
|
@@ -5495,9 +5511,9 @@ class DOMObserver {
|
|
|
5495
5511
|
});
|
|
5496
5512
|
this.resize.observe(view.scrollDOM);
|
|
5497
5513
|
}
|
|
5498
|
-
|
|
5514
|
+
this.win = view.dom.ownerDocument.defaultView;
|
|
5515
|
+
this.addWindowListeners(this.win);
|
|
5499
5516
|
this.start();
|
|
5500
|
-
window.addEventListener("scroll", this.onScroll = this.onScroll.bind(this));
|
|
5501
5517
|
if (typeof IntersectionObserver == "function") {
|
|
5502
5518
|
this.intersection = new IntersectionObserver(entries => {
|
|
5503
5519
|
if (this.parentCheck < 0)
|
|
@@ -5516,7 +5532,6 @@ class DOMObserver {
|
|
|
5516
5532
|
}
|
|
5517
5533
|
this.listenForScroll();
|
|
5518
5534
|
this.readSelectionRange();
|
|
5519
|
-
this.dom.ownerDocument.addEventListener("selectionchange", this.onSelectionChange);
|
|
5520
5535
|
}
|
|
5521
5536
|
onScroll(e) {
|
|
5522
5537
|
if (this.intersecting)
|
|
@@ -5547,14 +5562,18 @@ class DOMObserver {
|
|
|
5547
5562
|
}
|
|
5548
5563
|
}
|
|
5549
5564
|
onSelectionChange(event) {
|
|
5565
|
+
let wasChanged = this.selectionChanged;
|
|
5550
5566
|
if (!this.readSelectionRange() || this.delayedAndroidKey)
|
|
5551
5567
|
return;
|
|
5552
5568
|
let { view } = this, sel = this.selectionRange;
|
|
5553
5569
|
if (view.state.facet(editable) ? view.root.activeElement != this.dom : !hasSelection(view.dom, sel))
|
|
5554
5570
|
return;
|
|
5555
5571
|
let context = sel.anchorNode && view.docView.nearest(sel.anchorNode);
|
|
5556
|
-
if (context && context.ignoreEvent(event))
|
|
5572
|
+
if (context && context.ignoreEvent(event)) {
|
|
5573
|
+
if (!wasChanged)
|
|
5574
|
+
this.selectionChanged = false;
|
|
5557
5575
|
return;
|
|
5576
|
+
}
|
|
5558
5577
|
// Deletions on IE11 fire their events in the wrong order, giving
|
|
5559
5578
|
// us a selection change event before the DOM changes are
|
|
5560
5579
|
// reported.
|
|
@@ -5571,7 +5590,8 @@ class DOMObserver {
|
|
|
5571
5590
|
let { view } = this;
|
|
5572
5591
|
// The Selection object is broken in shadow roots in Safari. See
|
|
5573
5592
|
// https://github.com/codemirror/dev/issues/414
|
|
5574
|
-
let range = browser.safari && view.root.nodeType == 11 &&
|
|
5593
|
+
let range = browser.safari && view.root.nodeType == 11 &&
|
|
5594
|
+
deepActiveElement(this.dom.ownerDocument) == this.dom &&
|
|
5575
5595
|
safariSelectionRangeHack(this.view) || getSelection(view.root);
|
|
5576
5596
|
if (!range || this.selectionRange.eq(range))
|
|
5577
5597
|
return false;
|
|
@@ -5731,6 +5751,7 @@ class DOMObserver {
|
|
|
5731
5751
|
let newSel = this.selectionChanged && hasSelection(this.dom, this.selectionRange);
|
|
5732
5752
|
if (from < 0 && !newSel)
|
|
5733
5753
|
return;
|
|
5754
|
+
this.view.inputState.lastFocusTime = 0;
|
|
5734
5755
|
this.selectionChanged = false;
|
|
5735
5756
|
let startState = this.view.state;
|
|
5736
5757
|
let handled = this.onChange(from, to, typeOver);
|
|
@@ -5759,6 +5780,25 @@ class DOMObserver {
|
|
|
5759
5780
|
return null;
|
|
5760
5781
|
}
|
|
5761
5782
|
}
|
|
5783
|
+
setWindow(win) {
|
|
5784
|
+
if (win != this.win) {
|
|
5785
|
+
this.removeWindowListeners(this.win);
|
|
5786
|
+
this.win = win;
|
|
5787
|
+
this.addWindowListeners(this.win);
|
|
5788
|
+
}
|
|
5789
|
+
}
|
|
5790
|
+
addWindowListeners(win) {
|
|
5791
|
+
win.addEventListener("resize", this.onResize);
|
|
5792
|
+
win.addEventListener("beforeprint", this.onPrint);
|
|
5793
|
+
win.addEventListener("scroll", this.onScroll);
|
|
5794
|
+
win.document.addEventListener("selectionchange", this.onSelectionChange);
|
|
5795
|
+
}
|
|
5796
|
+
removeWindowListeners(win) {
|
|
5797
|
+
win.removeEventListener("scroll", this.onScroll);
|
|
5798
|
+
win.removeEventListener("resize", this.onResize);
|
|
5799
|
+
win.removeEventListener("beforeprint", this.onPrint);
|
|
5800
|
+
win.document.removeEventListener("selectionchange", this.onSelectionChange);
|
|
5801
|
+
}
|
|
5762
5802
|
destroy() {
|
|
5763
5803
|
var _a, _b, _c;
|
|
5764
5804
|
this.stop();
|
|
@@ -5767,10 +5807,7 @@ class DOMObserver {
|
|
|
5767
5807
|
(_c = this.resize) === null || _c === void 0 ? void 0 : _c.disconnect();
|
|
5768
5808
|
for (let dom of this.scrollTargets)
|
|
5769
5809
|
dom.removeEventListener("scroll", this.onScroll);
|
|
5770
|
-
|
|
5771
|
-
window.removeEventListener("resize", this.onResize);
|
|
5772
|
-
window.removeEventListener("beforeprint", this.onPrint);
|
|
5773
|
-
this.dom.ownerDocument.removeEventListener("selectionchange", this.onSelectionChange);
|
|
5810
|
+
this.removeWindowListeners(this.win);
|
|
5774
5811
|
clearTimeout(this.parentCheck);
|
|
5775
5812
|
clearTimeout(this.resizeTimeout);
|
|
5776
5813
|
}
|
|
@@ -5799,7 +5836,7 @@ function safariSelectionRangeHack(view) {
|
|
|
5799
5836
|
found = event.getTargetRanges()[0];
|
|
5800
5837
|
}
|
|
5801
5838
|
view.contentDOM.addEventListener("beforeinput", read, true);
|
|
5802
|
-
|
|
5839
|
+
view.dom.ownerDocument.execCommand("indent");
|
|
5803
5840
|
view.contentDOM.removeEventListener("beforeinput", read, true);
|
|
5804
5841
|
if (!found)
|
|
5805
5842
|
return null;
|
|
@@ -6078,7 +6115,7 @@ class EditorView {
|
|
|
6078
6115
|
this.dom.appendChild(this.scrollDOM);
|
|
6079
6116
|
this._dispatch = config.dispatch || ((tr) => this.update([tr]));
|
|
6080
6117
|
this.dispatch = this.dispatch.bind(this);
|
|
6081
|
-
this.
|
|
6118
|
+
this._root = (config.root || getRoot(config.parent) || document);
|
|
6082
6119
|
this.viewState = new ViewState(config.state || state.EditorState.create(config));
|
|
6083
6120
|
this.plugins = this.state.facet(viewPlugin).map(spec => new PluginInstance(spec));
|
|
6084
6121
|
for (let plugin of this.plugins)
|
|
@@ -6139,6 +6176,10 @@ class EditorView {
|
|
|
6139
6176
|
composition there.
|
|
6140
6177
|
*/
|
|
6141
6178
|
get compositionStarted() { return this.inputState.composing >= 0; }
|
|
6179
|
+
/**
|
|
6180
|
+
The document or shadow root that the view lives in.
|
|
6181
|
+
*/
|
|
6182
|
+
get root() { return this._root; }
|
|
6142
6183
|
dispatch(...input) {
|
|
6143
6184
|
this._dispatch(input.length == 1 && input[0] instanceof state.Transaction ? input[0]
|
|
6144
6185
|
: this.state.update(...input));
|
|
@@ -6474,7 +6515,7 @@ class EditorView {
|
|
|
6474
6515
|
/**
|
|
6475
6516
|
Find the text line or block widget at the given vertical
|
|
6476
6517
|
position (which is interpreted as relative to the [top of the
|
|
6477
|
-
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)
|
|
6518
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)).
|
|
6478
6519
|
*/
|
|
6479
6520
|
elementAtHeight(height) {
|
|
6480
6521
|
this.readMeasured();
|
|
@@ -6483,7 +6524,8 @@ class EditorView {
|
|
|
6483
6524
|
/**
|
|
6484
6525
|
Find the line block (see
|
|
6485
6526
|
[`lineBlockAt`](https://codemirror.net/6/docs/ref/#view.EditorView.lineBlockAt) at the given
|
|
6486
|
-
height
|
|
6527
|
+
height, again interpreted relative to the [top of the
|
|
6528
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop).
|
|
6487
6529
|
*/
|
|
6488
6530
|
lineBlockAtHeight(height) {
|
|
6489
6531
|
this.readMeasured();
|
|
@@ -6677,7 +6719,7 @@ class EditorView {
|
|
|
6677
6719
|
// or closing, which leads us to ignore selection changes from the
|
|
6678
6720
|
// context menu because it looks like the editor isn't focused.
|
|
6679
6721
|
// This kludges around that.
|
|
6680
|
-
return (
|
|
6722
|
+
return (this.dom.ownerDocument.hasFocus() || browser.safari && ((_a = this.inputState) === null || _a === void 0 ? void 0 : _a.lastContextMenu) > Date.now() - 3e4) &&
|
|
6681
6723
|
this.root.activeElement == this.contentDOM;
|
|
6682
6724
|
}
|
|
6683
6725
|
/**
|
|
@@ -6690,6 +6732,17 @@ class EditorView {
|
|
|
6690
6732
|
});
|
|
6691
6733
|
}
|
|
6692
6734
|
/**
|
|
6735
|
+
Update the [root](https://codemirror.net/6/docs/ref/##view.EditorViewConfig.root) in which the editor lives. This is only
|
|
6736
|
+
necessary when moving the editor's existing DOM to a new window or shadow root.
|
|
6737
|
+
*/
|
|
6738
|
+
setRoot(root) {
|
|
6739
|
+
if (this._root != root) {
|
|
6740
|
+
this._root = root;
|
|
6741
|
+
this.observer.setWindow((root.nodeType == 9 ? root : root.ownerDocument).defaultView);
|
|
6742
|
+
this.mountStyles();
|
|
6743
|
+
}
|
|
6744
|
+
}
|
|
6745
|
+
/**
|
|
6693
6746
|
Clean up this editor view, removing its element from the
|
|
6694
6747
|
document, unregistering event handlers, and notifying
|
|
6695
6748
|
plugins. The view instance can no longer be used after
|
|
@@ -6851,6 +6904,11 @@ the editor's vertical layout structure. The ones provided as
|
|
|
6851
6904
|
functions are called _after_ the new viewport has been computed,
|
|
6852
6905
|
and thus **must not** introduce block widgets or replacing
|
|
6853
6906
|
decorations that cover line breaks.
|
|
6907
|
+
|
|
6908
|
+
If you want decorated ranges to behave like atomic units for
|
|
6909
|
+
cursor motion and deletion purposes, also provide the range set
|
|
6910
|
+
containing the decorations to
|
|
6911
|
+
[`EditorView.atomicRanges`](https://codemirror.net/6/docs/ref/#view.EditorView^atomicRanges).
|
|
6854
6912
|
*/
|
|
6855
6913
|
EditorView.decorations = decorations;
|
|
6856
6914
|
/**
|
|
@@ -7081,7 +7139,7 @@ function runHandlers(map, event, view, scope) {
|
|
|
7081
7139
|
}
|
|
7082
7140
|
return false;
|
|
7083
7141
|
};
|
|
7084
|
-
let scopeObj = map[scope], baseName;
|
|
7142
|
+
let scopeObj = map[scope], baseName, shiftName;
|
|
7085
7143
|
if (scopeObj) {
|
|
7086
7144
|
if (runFor(scopeObj[prefix + modifiers(name, event, !isChar)]))
|
|
7087
7145
|
return true;
|
|
@@ -7089,8 +7147,8 @@ function runHandlers(map, event, view, scope) {
|
|
|
7089
7147
|
(baseName = w3cKeyname.base[event.keyCode]) && baseName != name) {
|
|
7090
7148
|
if (runFor(scopeObj[prefix + modifiers(baseName, event, true)]))
|
|
7091
7149
|
return true;
|
|
7092
|
-
else if (event.shiftKey && w3cKeyname.shift[event.keyCode] != baseName &&
|
|
7093
|
-
runFor(scopeObj[prefix + modifiers(
|
|
7150
|
+
else if (event.shiftKey && (shiftName = w3cKeyname.shift[event.keyCode]) != name && shiftName != baseName &&
|
|
7151
|
+
runFor(scopeObj[prefix + modifiers(shiftName, event, false)]))
|
|
7094
7152
|
return true;
|
|
7095
7153
|
}
|
|
7096
7154
|
else if (isChar && event.shiftKey) {
|
package/dist/index.d.ts
CHANGED
|
@@ -647,10 +647,11 @@ declare class EditorView {
|
|
|
647
647
|
*/
|
|
648
648
|
get compositionStarted(): boolean;
|
|
649
649
|
private _dispatch;
|
|
650
|
+
private _root;
|
|
650
651
|
/**
|
|
651
652
|
The document or shadow root that the view lives in.
|
|
652
653
|
*/
|
|
653
|
-
|
|
654
|
+
get root(): DocumentOrShadowRoot;
|
|
654
655
|
/**
|
|
655
656
|
The DOM element that wraps the entire editor view.
|
|
656
657
|
*/
|
|
@@ -752,13 +753,14 @@ declare class EditorView {
|
|
|
752
753
|
/**
|
|
753
754
|
Find the text line or block widget at the given vertical
|
|
754
755
|
position (which is interpreted as relative to the [top of the
|
|
755
|
-
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)
|
|
756
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)).
|
|
756
757
|
*/
|
|
757
758
|
elementAtHeight(height: number): BlockInfo;
|
|
758
759
|
/**
|
|
759
760
|
Find the line block (see
|
|
760
761
|
[`lineBlockAt`](https://codemirror.net/6/docs/ref/#view.EditorView.lineBlockAt) at the given
|
|
761
|
-
height
|
|
762
|
+
height, again interpreted relative to the [top of the
|
|
763
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop).
|
|
762
764
|
*/
|
|
763
765
|
lineBlockAtHeight(height: number): BlockInfo;
|
|
764
766
|
/**
|
|
@@ -921,6 +923,11 @@ declare class EditorView {
|
|
|
921
923
|
*/
|
|
922
924
|
focus(): void;
|
|
923
925
|
/**
|
|
926
|
+
Update the [root](https://codemirror.net/6/docs/ref/##view.EditorViewConfig.root) in which the editor lives. This is only
|
|
927
|
+
necessary when moving the editor's existing DOM to a new window or shadow root.
|
|
928
|
+
*/
|
|
929
|
+
setRoot(root: Document | ShadowRoot): void;
|
|
930
|
+
/**
|
|
924
931
|
Clean up this editor view, removing its element from the
|
|
925
932
|
document, unregistering event handlers, and notifying
|
|
926
933
|
plugins. The view instance can no longer be used after
|
|
@@ -1047,6 +1054,11 @@ declare class EditorView {
|
|
|
1047
1054
|
functions are called _after_ the new viewport has been computed,
|
|
1048
1055
|
and thus **must not** introduce block widgets or replacing
|
|
1049
1056
|
decorations that cover line breaks.
|
|
1057
|
+
|
|
1058
|
+
If you want decorated ranges to behave like atomic units for
|
|
1059
|
+
cursor motion and deletion purposes, also provide the range set
|
|
1060
|
+
containing the decorations to
|
|
1061
|
+
[`EditorView.atomicRanges`](https://codemirror.net/6/docs/ref/#view.EditorView^atomicRanges).
|
|
1050
1062
|
*/
|
|
1051
1063
|
static decorations: Facet<DecorationSet | ((view: EditorView) => DecorationSet), readonly (DecorationSet | ((view: EditorView) => DecorationSet))[]>;
|
|
1052
1064
|
/**
|
package/dist/index.js
CHANGED
|
@@ -18,8 +18,8 @@ function getSelection(root) {
|
|
|
18
18
|
function contains(dom, node) {
|
|
19
19
|
return node ? dom == node || dom.contains(node.nodeType != 1 ? node.parentNode : node) : false;
|
|
20
20
|
}
|
|
21
|
-
function deepActiveElement() {
|
|
22
|
-
let elt =
|
|
21
|
+
function deepActiveElement(doc) {
|
|
22
|
+
let elt = doc.activeElement;
|
|
23
23
|
while (elt && elt.shadowRoot)
|
|
24
24
|
elt = elt.shadowRoot.activeElement;
|
|
25
25
|
return elt;
|
|
@@ -758,7 +758,7 @@ class MarkView extends ContentView {
|
|
|
758
758
|
return new MarkView(this.mark, result, length);
|
|
759
759
|
}
|
|
760
760
|
domAtPos(pos) {
|
|
761
|
-
return inlineDOMAtPos(this
|
|
761
|
+
return inlineDOMAtPos(this, pos);
|
|
762
762
|
}
|
|
763
763
|
coordsAt(pos, side) {
|
|
764
764
|
return coordsInChildren(this, pos, side);
|
|
@@ -909,11 +909,14 @@ class CompositionView extends WidgetView {
|
|
|
909
909
|
// offset.
|
|
910
910
|
function scanCompositionTree(pos, side, view, text, enterView, fromText) {
|
|
911
911
|
if (view instanceof MarkView) {
|
|
912
|
-
for (let child
|
|
913
|
-
let
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
912
|
+
for (let child = view.dom.firstChild; child; child = child.nextSibling) {
|
|
913
|
+
let desc = ContentView.get(child);
|
|
914
|
+
if (!desc)
|
|
915
|
+
return fromText(pos, side);
|
|
916
|
+
let hasComp = contains(child, text);
|
|
917
|
+
let len = desc.length + (hasComp ? text.nodeValue.length : 0);
|
|
918
|
+
if (pos < len || pos == len && desc.getSide() <= 0)
|
|
919
|
+
return hasComp ? scanCompositionTree(pos, side, desc, text, enterView, fromText) : enterView(desc, pos, side);
|
|
917
920
|
pos -= len;
|
|
918
921
|
}
|
|
919
922
|
return enterView(view, view.length, -1);
|
|
@@ -1003,8 +1006,8 @@ function inlineSiblingRect(view, side) {
|
|
|
1003
1006
|
}
|
|
1004
1007
|
return undefined;
|
|
1005
1008
|
}
|
|
1006
|
-
function inlineDOMAtPos(
|
|
1007
|
-
let i = 0;
|
|
1009
|
+
function inlineDOMAtPos(parent, pos) {
|
|
1010
|
+
let dom = parent.dom, { children } = parent, i = 0;
|
|
1008
1011
|
for (let off = 0; i < children.length; i++) {
|
|
1009
1012
|
let child = children[i], end = off + child.length;
|
|
1010
1013
|
if (end == off && child.getSide() <= 0)
|
|
@@ -1015,10 +1018,16 @@ function inlineDOMAtPos(dom, children, pos) {
|
|
|
1015
1018
|
break;
|
|
1016
1019
|
off = end;
|
|
1017
1020
|
}
|
|
1018
|
-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
1021
|
+
// if (i) return DOMPos.after(children[i - 1].dom!)
|
|
1022
|
+
for (let j = i; j > 0; j--) {
|
|
1023
|
+
let prev = children[j - 1];
|
|
1024
|
+
if (prev.dom.parentNode == dom)
|
|
1025
|
+
return prev.domAtPos(prev.length);
|
|
1026
|
+
}
|
|
1027
|
+
for (let j = i; j < children.length; j++) {
|
|
1028
|
+
let next = children[j];
|
|
1029
|
+
if (next.dom.parentNode == dom)
|
|
1030
|
+
return next.domAtPos(0);
|
|
1022
1031
|
}
|
|
1023
1032
|
return new DOMPos(dom, 0);
|
|
1024
1033
|
}
|
|
@@ -1426,7 +1435,7 @@ class LineView extends ContentView {
|
|
|
1426
1435
|
this.attrs = combineAttrs({ class: cls }, this.attrs || {});
|
|
1427
1436
|
}
|
|
1428
1437
|
domAtPos(pos) {
|
|
1429
|
-
return inlineDOMAtPos(this
|
|
1438
|
+
return inlineDOMAtPos(this, pos);
|
|
1430
1439
|
}
|
|
1431
1440
|
reuseDOM(node) {
|
|
1432
1441
|
if (node.nodeName == "DIV") {
|
|
@@ -2071,9 +2080,10 @@ function charType(ch) {
|
|
|
2071
2080
|
0x600 <= ch && ch <= 0x6f9 ? ArabicTypes[ch - 0x600] :
|
|
2072
2081
|
0x6ee <= ch && ch <= 0x8ac ? 4 /* AL */ :
|
|
2073
2082
|
0x2000 <= ch && ch <= 0x200b ? 256 /* NI */ :
|
|
2074
|
-
ch
|
|
2083
|
+
0xfb50 <= ch && ch <= 0xfdff ? 4 /* AL */ :
|
|
2084
|
+
ch == 0x200c ? 256 /* NI */ : 1 /* L */;
|
|
2075
2085
|
}
|
|
2076
|
-
const BidiRE = /[\u0590-\u05f4\u0600-\u06ff\u0700-\u08ac]/;
|
|
2086
|
+
const BidiRE = /[\u0590-\u05f4\u0600-\u06ff\u0700-\u08ac\ufb50-\ufdff]/;
|
|
2077
2087
|
/**
|
|
2078
2088
|
Represents a contiguous range of text that has a single direction
|
|
2079
2089
|
(as in left-to-right or right-to-left).
|
|
@@ -2477,7 +2487,6 @@ class DocView extends ContentView {
|
|
|
2477
2487
|
this.updateDeco();
|
|
2478
2488
|
this.updateInner([new ChangedRange(0, 0, 0, view.state.doc.length)], 0);
|
|
2479
2489
|
}
|
|
2480
|
-
get root() { return this.view.root; }
|
|
2481
2490
|
get editorView() { return this.view; }
|
|
2482
2491
|
get length() { return this.view.state.doc.length; }
|
|
2483
2492
|
// Update the document view to a given state. scrollIntoView can be
|
|
@@ -2600,7 +2609,7 @@ class DocView extends ContentView {
|
|
|
2600
2609
|
this.dom.blur();
|
|
2601
2610
|
this.dom.focus({ preventScroll: true });
|
|
2602
2611
|
}
|
|
2603
|
-
let rawSel = getSelection(this.root);
|
|
2612
|
+
let rawSel = getSelection(this.view.root);
|
|
2604
2613
|
if (!rawSel) ;
|
|
2605
2614
|
else if (main.empty) {
|
|
2606
2615
|
// Work around https://bugzilla.mozilla.org/show_bug.cgi?id=1612076
|
|
@@ -2643,7 +2652,7 @@ class DocView extends ContentView {
|
|
|
2643
2652
|
if (this.compositionDeco.size)
|
|
2644
2653
|
return;
|
|
2645
2654
|
let cursor = this.view.state.selection.main;
|
|
2646
|
-
let sel = getSelection(this.root);
|
|
2655
|
+
let sel = getSelection(this.view.root);
|
|
2647
2656
|
if (!sel || !cursor.empty || !cursor.assoc || !sel.modify)
|
|
2648
2657
|
return;
|
|
2649
2658
|
let line = LineView.find(this, cursor.head);
|
|
@@ -2660,7 +2669,7 @@ class DocView extends ContentView {
|
|
|
2660
2669
|
sel.modify("move", cursor.assoc < 0 ? "forward" : "backward", "lineboundary");
|
|
2661
2670
|
}
|
|
2662
2671
|
mayControlSelection() {
|
|
2663
|
-
let active = this.root.activeElement;
|
|
2672
|
+
let active = this.view.root.activeElement;
|
|
2664
2673
|
return active == this.dom ||
|
|
2665
2674
|
hasSelection(this.dom, this.view.observer.selectionRange) && !(active && this.dom.contains(active));
|
|
2666
2675
|
}
|
|
@@ -3013,7 +3022,7 @@ function upBot(rect, bottom) {
|
|
|
3013
3022
|
return bottom > rect.bottom ? { top: rect.top, left: rect.left, right: rect.right, bottom } : rect;
|
|
3014
3023
|
}
|
|
3015
3024
|
function domPosAtCoords(parent, x, y) {
|
|
3016
|
-
let closest, closestRect, closestX, closestY;
|
|
3025
|
+
let closest, closestRect, closestX, closestY, closestOverlap = false;
|
|
3017
3026
|
let above, below, aboveRect, belowRect;
|
|
3018
3027
|
for (let child = parent.firstChild; child; child = child.nextSibling) {
|
|
3019
3028
|
let rects = clientRectsFor(child);
|
|
@@ -3029,6 +3038,7 @@ function domPosAtCoords(parent, x, y) {
|
|
|
3029
3038
|
closestRect = rect;
|
|
3030
3039
|
closestX = dx;
|
|
3031
3040
|
closestY = dy;
|
|
3041
|
+
closestOverlap = !dx || (dx > 0 ? i < rects.length - 1 : i > 0);
|
|
3032
3042
|
}
|
|
3033
3043
|
if (dx == 0) {
|
|
3034
3044
|
if (y > rect.bottom && (!aboveRect || aboveRect.bottom < rect.bottom)) {
|
|
@@ -3061,7 +3071,7 @@ function domPosAtCoords(parent, x, y) {
|
|
|
3061
3071
|
let clipX = Math.max(closestRect.left, Math.min(closestRect.right, x));
|
|
3062
3072
|
if (closest.nodeType == 3)
|
|
3063
3073
|
return domPosInText(closest, clipX, y);
|
|
3064
|
-
if (
|
|
3074
|
+
if (closestOverlap && closest.contentEditable != "false")
|
|
3065
3075
|
return domPosAtCoords(closest, clipX, y);
|
|
3066
3076
|
let offset = Array.prototype.indexOf.call(parent.childNodes, closest) +
|
|
3067
3077
|
(x >= (closestRect.left + closestRect.right) / 2 ? 1 : 0);
|
|
@@ -3158,7 +3168,8 @@ function posAtCoords(view, { x, y }, precise, bias = -1) {
|
|
|
3158
3168
|
let range = doc.caretRangeFromPoint(x, y);
|
|
3159
3169
|
if (range) {
|
|
3160
3170
|
({ startContainer: node, startOffset: offset } = range);
|
|
3161
|
-
if (
|
|
3171
|
+
if (!view.contentDOM.contains(node) ||
|
|
3172
|
+
browser.safari && isSuspiciousSafariCaretResult(node, offset, x) ||
|
|
3162
3173
|
browser.chrome && isSuspiciousChromeCaretResult(node, offset, x))
|
|
3163
3174
|
node = undefined;
|
|
3164
3175
|
}
|
|
@@ -3451,9 +3462,10 @@ class InputState {
|
|
|
3451
3462
|
// applyDOMChange, notify key handlers of it and reset to
|
|
3452
3463
|
// the state they produce.
|
|
3453
3464
|
let pending;
|
|
3454
|
-
if (browser.ios &&
|
|
3455
|
-
|
|
3456
|
-
|
|
3465
|
+
if (browser.ios && !event.synthetic && !event.altKey && !event.metaKey &&
|
|
3466
|
+
((pending = PendingKeys.find(key => key.keyCode == event.keyCode)) && !event.ctrlKey ||
|
|
3467
|
+
EmacsyPendingKeys.indexOf(event.key) > -1 && event.ctrlKey && !event.shiftKey)) {
|
|
3468
|
+
this.pendingIOSKey = pending || event;
|
|
3457
3469
|
setTimeout(() => this.flushIOSKey(view), 250);
|
|
3458
3470
|
return true;
|
|
3459
3471
|
}
|
|
@@ -3508,6 +3520,7 @@ const PendingKeys = [
|
|
|
3508
3520
|
{ key: "Enter", keyCode: 13, inputType: "insertParagraph" },
|
|
3509
3521
|
{ key: "Delete", keyCode: 46, inputType: "deleteContentForward" }
|
|
3510
3522
|
];
|
|
3523
|
+
const EmacsyPendingKeys = "dthko";
|
|
3511
3524
|
// Key codes for modifier keys
|
|
3512
3525
|
const modifierCodes = [16, 17, 18, 20, 91, 92, 224, 225];
|
|
3513
3526
|
class MouseSelection {
|
|
@@ -5371,6 +5384,7 @@ const baseTheme$1 = /*@__PURE__*/buildTheme("." + baseThemeID, {
|
|
|
5371
5384
|
".cm-widgetBuffer": {
|
|
5372
5385
|
verticalAlign: "text-top",
|
|
5373
5386
|
height: "1em",
|
|
5387
|
+
width: 0,
|
|
5374
5388
|
display: "inline"
|
|
5375
5389
|
},
|
|
5376
5390
|
".cm-placeholder": {
|
|
@@ -5480,7 +5494,9 @@ class DOMObserver {
|
|
|
5480
5494
|
this.flushSoon();
|
|
5481
5495
|
};
|
|
5482
5496
|
this.onSelectionChange = this.onSelectionChange.bind(this);
|
|
5483
|
-
|
|
5497
|
+
this.onResize = this.onResize.bind(this);
|
|
5498
|
+
this.onPrint = this.onPrint.bind(this);
|
|
5499
|
+
this.onScroll = this.onScroll.bind(this);
|
|
5484
5500
|
if (typeof ResizeObserver == "function") {
|
|
5485
5501
|
this.resize = new ResizeObserver(() => {
|
|
5486
5502
|
if (this.view.docView.lastUpdate < Date.now() - 75)
|
|
@@ -5488,9 +5504,9 @@ class DOMObserver {
|
|
|
5488
5504
|
});
|
|
5489
5505
|
this.resize.observe(view.scrollDOM);
|
|
5490
5506
|
}
|
|
5491
|
-
|
|
5507
|
+
this.win = view.dom.ownerDocument.defaultView;
|
|
5508
|
+
this.addWindowListeners(this.win);
|
|
5492
5509
|
this.start();
|
|
5493
|
-
window.addEventListener("scroll", this.onScroll = this.onScroll.bind(this));
|
|
5494
5510
|
if (typeof IntersectionObserver == "function") {
|
|
5495
5511
|
this.intersection = new IntersectionObserver(entries => {
|
|
5496
5512
|
if (this.parentCheck < 0)
|
|
@@ -5509,7 +5525,6 @@ class DOMObserver {
|
|
|
5509
5525
|
}
|
|
5510
5526
|
this.listenForScroll();
|
|
5511
5527
|
this.readSelectionRange();
|
|
5512
|
-
this.dom.ownerDocument.addEventListener("selectionchange", this.onSelectionChange);
|
|
5513
5528
|
}
|
|
5514
5529
|
onScroll(e) {
|
|
5515
5530
|
if (this.intersecting)
|
|
@@ -5540,14 +5555,18 @@ class DOMObserver {
|
|
|
5540
5555
|
}
|
|
5541
5556
|
}
|
|
5542
5557
|
onSelectionChange(event) {
|
|
5558
|
+
let wasChanged = this.selectionChanged;
|
|
5543
5559
|
if (!this.readSelectionRange() || this.delayedAndroidKey)
|
|
5544
5560
|
return;
|
|
5545
5561
|
let { view } = this, sel = this.selectionRange;
|
|
5546
5562
|
if (view.state.facet(editable) ? view.root.activeElement != this.dom : !hasSelection(view.dom, sel))
|
|
5547
5563
|
return;
|
|
5548
5564
|
let context = sel.anchorNode && view.docView.nearest(sel.anchorNode);
|
|
5549
|
-
if (context && context.ignoreEvent(event))
|
|
5565
|
+
if (context && context.ignoreEvent(event)) {
|
|
5566
|
+
if (!wasChanged)
|
|
5567
|
+
this.selectionChanged = false;
|
|
5550
5568
|
return;
|
|
5569
|
+
}
|
|
5551
5570
|
// Deletions on IE11 fire their events in the wrong order, giving
|
|
5552
5571
|
// us a selection change event before the DOM changes are
|
|
5553
5572
|
// reported.
|
|
@@ -5564,7 +5583,8 @@ class DOMObserver {
|
|
|
5564
5583
|
let { view } = this;
|
|
5565
5584
|
// The Selection object is broken in shadow roots in Safari. See
|
|
5566
5585
|
// https://github.com/codemirror/dev/issues/414
|
|
5567
|
-
let range = browser.safari && view.root.nodeType == 11 &&
|
|
5586
|
+
let range = browser.safari && view.root.nodeType == 11 &&
|
|
5587
|
+
deepActiveElement(this.dom.ownerDocument) == this.dom &&
|
|
5568
5588
|
safariSelectionRangeHack(this.view) || getSelection(view.root);
|
|
5569
5589
|
if (!range || this.selectionRange.eq(range))
|
|
5570
5590
|
return false;
|
|
@@ -5724,6 +5744,7 @@ class DOMObserver {
|
|
|
5724
5744
|
let newSel = this.selectionChanged && hasSelection(this.dom, this.selectionRange);
|
|
5725
5745
|
if (from < 0 && !newSel)
|
|
5726
5746
|
return;
|
|
5747
|
+
this.view.inputState.lastFocusTime = 0;
|
|
5727
5748
|
this.selectionChanged = false;
|
|
5728
5749
|
let startState = this.view.state;
|
|
5729
5750
|
let handled = this.onChange(from, to, typeOver);
|
|
@@ -5752,6 +5773,25 @@ class DOMObserver {
|
|
|
5752
5773
|
return null;
|
|
5753
5774
|
}
|
|
5754
5775
|
}
|
|
5776
|
+
setWindow(win) {
|
|
5777
|
+
if (win != this.win) {
|
|
5778
|
+
this.removeWindowListeners(this.win);
|
|
5779
|
+
this.win = win;
|
|
5780
|
+
this.addWindowListeners(this.win);
|
|
5781
|
+
}
|
|
5782
|
+
}
|
|
5783
|
+
addWindowListeners(win) {
|
|
5784
|
+
win.addEventListener("resize", this.onResize);
|
|
5785
|
+
win.addEventListener("beforeprint", this.onPrint);
|
|
5786
|
+
win.addEventListener("scroll", this.onScroll);
|
|
5787
|
+
win.document.addEventListener("selectionchange", this.onSelectionChange);
|
|
5788
|
+
}
|
|
5789
|
+
removeWindowListeners(win) {
|
|
5790
|
+
win.removeEventListener("scroll", this.onScroll);
|
|
5791
|
+
win.removeEventListener("resize", this.onResize);
|
|
5792
|
+
win.removeEventListener("beforeprint", this.onPrint);
|
|
5793
|
+
win.document.removeEventListener("selectionchange", this.onSelectionChange);
|
|
5794
|
+
}
|
|
5755
5795
|
destroy() {
|
|
5756
5796
|
var _a, _b, _c;
|
|
5757
5797
|
this.stop();
|
|
@@ -5760,10 +5800,7 @@ class DOMObserver {
|
|
|
5760
5800
|
(_c = this.resize) === null || _c === void 0 ? void 0 : _c.disconnect();
|
|
5761
5801
|
for (let dom of this.scrollTargets)
|
|
5762
5802
|
dom.removeEventListener("scroll", this.onScroll);
|
|
5763
|
-
|
|
5764
|
-
window.removeEventListener("resize", this.onResize);
|
|
5765
|
-
window.removeEventListener("beforeprint", this.onPrint);
|
|
5766
|
-
this.dom.ownerDocument.removeEventListener("selectionchange", this.onSelectionChange);
|
|
5803
|
+
this.removeWindowListeners(this.win);
|
|
5767
5804
|
clearTimeout(this.parentCheck);
|
|
5768
5805
|
clearTimeout(this.resizeTimeout);
|
|
5769
5806
|
}
|
|
@@ -5792,7 +5829,7 @@ function safariSelectionRangeHack(view) {
|
|
|
5792
5829
|
found = event.getTargetRanges()[0];
|
|
5793
5830
|
}
|
|
5794
5831
|
view.contentDOM.addEventListener("beforeinput", read, true);
|
|
5795
|
-
|
|
5832
|
+
view.dom.ownerDocument.execCommand("indent");
|
|
5796
5833
|
view.contentDOM.removeEventListener("beforeinput", read, true);
|
|
5797
5834
|
if (!found)
|
|
5798
5835
|
return null;
|
|
@@ -6071,7 +6108,7 @@ class EditorView {
|
|
|
6071
6108
|
this.dom.appendChild(this.scrollDOM);
|
|
6072
6109
|
this._dispatch = config.dispatch || ((tr) => this.update([tr]));
|
|
6073
6110
|
this.dispatch = this.dispatch.bind(this);
|
|
6074
|
-
this.
|
|
6111
|
+
this._root = (config.root || getRoot(config.parent) || document);
|
|
6075
6112
|
this.viewState = new ViewState(config.state || EditorState.create(config));
|
|
6076
6113
|
this.plugins = this.state.facet(viewPlugin).map(spec => new PluginInstance(spec));
|
|
6077
6114
|
for (let plugin of this.plugins)
|
|
@@ -6132,6 +6169,10 @@ class EditorView {
|
|
|
6132
6169
|
composition there.
|
|
6133
6170
|
*/
|
|
6134
6171
|
get compositionStarted() { return this.inputState.composing >= 0; }
|
|
6172
|
+
/**
|
|
6173
|
+
The document or shadow root that the view lives in.
|
|
6174
|
+
*/
|
|
6175
|
+
get root() { return this._root; }
|
|
6135
6176
|
dispatch(...input) {
|
|
6136
6177
|
this._dispatch(input.length == 1 && input[0] instanceof Transaction ? input[0]
|
|
6137
6178
|
: this.state.update(...input));
|
|
@@ -6467,7 +6508,7 @@ class EditorView {
|
|
|
6467
6508
|
/**
|
|
6468
6509
|
Find the text line or block widget at the given vertical
|
|
6469
6510
|
position (which is interpreted as relative to the [top of the
|
|
6470
|
-
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)
|
|
6511
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop)).
|
|
6471
6512
|
*/
|
|
6472
6513
|
elementAtHeight(height) {
|
|
6473
6514
|
this.readMeasured();
|
|
@@ -6476,7 +6517,8 @@ class EditorView {
|
|
|
6476
6517
|
/**
|
|
6477
6518
|
Find the line block (see
|
|
6478
6519
|
[`lineBlockAt`](https://codemirror.net/6/docs/ref/#view.EditorView.lineBlockAt) at the given
|
|
6479
|
-
height
|
|
6520
|
+
height, again interpreted relative to the [top of the
|
|
6521
|
+
document](https://codemirror.net/6/docs/ref/#view.EditorView.documentTop).
|
|
6480
6522
|
*/
|
|
6481
6523
|
lineBlockAtHeight(height) {
|
|
6482
6524
|
this.readMeasured();
|
|
@@ -6670,7 +6712,7 @@ class EditorView {
|
|
|
6670
6712
|
// or closing, which leads us to ignore selection changes from the
|
|
6671
6713
|
// context menu because it looks like the editor isn't focused.
|
|
6672
6714
|
// This kludges around that.
|
|
6673
|
-
return (
|
|
6715
|
+
return (this.dom.ownerDocument.hasFocus() || browser.safari && ((_a = this.inputState) === null || _a === void 0 ? void 0 : _a.lastContextMenu) > Date.now() - 3e4) &&
|
|
6674
6716
|
this.root.activeElement == this.contentDOM;
|
|
6675
6717
|
}
|
|
6676
6718
|
/**
|
|
@@ -6683,6 +6725,17 @@ class EditorView {
|
|
|
6683
6725
|
});
|
|
6684
6726
|
}
|
|
6685
6727
|
/**
|
|
6728
|
+
Update the [root](https://codemirror.net/6/docs/ref/##view.EditorViewConfig.root) in which the editor lives. This is only
|
|
6729
|
+
necessary when moving the editor's existing DOM to a new window or shadow root.
|
|
6730
|
+
*/
|
|
6731
|
+
setRoot(root) {
|
|
6732
|
+
if (this._root != root) {
|
|
6733
|
+
this._root = root;
|
|
6734
|
+
this.observer.setWindow((root.nodeType == 9 ? root : root.ownerDocument).defaultView);
|
|
6735
|
+
this.mountStyles();
|
|
6736
|
+
}
|
|
6737
|
+
}
|
|
6738
|
+
/**
|
|
6686
6739
|
Clean up this editor view, removing its element from the
|
|
6687
6740
|
document, unregistering event handlers, and notifying
|
|
6688
6741
|
plugins. The view instance can no longer be used after
|
|
@@ -6844,6 +6897,11 @@ the editor's vertical layout structure. The ones provided as
|
|
|
6844
6897
|
functions are called _after_ the new viewport has been computed,
|
|
6845
6898
|
and thus **must not** introduce block widgets or replacing
|
|
6846
6899
|
decorations that cover line breaks.
|
|
6900
|
+
|
|
6901
|
+
If you want decorated ranges to behave like atomic units for
|
|
6902
|
+
cursor motion and deletion purposes, also provide the range set
|
|
6903
|
+
containing the decorations to
|
|
6904
|
+
[`EditorView.atomicRanges`](https://codemirror.net/6/docs/ref/#view.EditorView^atomicRanges).
|
|
6847
6905
|
*/
|
|
6848
6906
|
EditorView.decorations = decorations;
|
|
6849
6907
|
/**
|
|
@@ -7074,7 +7132,7 @@ function runHandlers(map, event, view, scope) {
|
|
|
7074
7132
|
}
|
|
7075
7133
|
return false;
|
|
7076
7134
|
};
|
|
7077
|
-
let scopeObj = map[scope], baseName;
|
|
7135
|
+
let scopeObj = map[scope], baseName, shiftName;
|
|
7078
7136
|
if (scopeObj) {
|
|
7079
7137
|
if (runFor(scopeObj[prefix + modifiers(name, event, !isChar)]))
|
|
7080
7138
|
return true;
|
|
@@ -7082,8 +7140,8 @@ function runHandlers(map, event, view, scope) {
|
|
|
7082
7140
|
(baseName = base[event.keyCode]) && baseName != name) {
|
|
7083
7141
|
if (runFor(scopeObj[prefix + modifiers(baseName, event, true)]))
|
|
7084
7142
|
return true;
|
|
7085
|
-
else if (event.shiftKey && shift[event.keyCode] != baseName &&
|
|
7086
|
-
runFor(scopeObj[prefix + modifiers(
|
|
7143
|
+
else if (event.shiftKey && (shiftName = shift[event.keyCode]) != name && shiftName != baseName &&
|
|
7144
|
+
runFor(scopeObj[prefix + modifiers(shiftName, event, false)]))
|
|
7087
7145
|
return true;
|
|
7088
7146
|
}
|
|
7089
7147
|
else if (isChar && event.shiftKey) {
|