@codemirror/view 6.0.0 → 6.0.3
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/.github/workflows/dispatch.yml +1 -1
- package/CHANGELOG.md +26 -0
- package/README.md +5 -5
- package/dist/index.cjs +53 -19
- package/dist/index.js +55 -21
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,29 @@
|
|
|
1
|
+
## 6.0.3 (2022-07-08)
|
|
2
|
+
|
|
3
|
+
### Bug fixes
|
|
4
|
+
|
|
5
|
+
Fix a problem where `posAtCoords` could incorrectly return the start of the next line when querying positions between lines.
|
|
6
|
+
|
|
7
|
+
Fix an issue where registering a high-precedence keymap made keymap handling take precedence over other keydown event handlers.
|
|
8
|
+
|
|
9
|
+
Ctrl/Cmd-clicking can now remove ranges from a multi-range selection.
|
|
10
|
+
|
|
11
|
+
## 6.0.2 (2022-06-23)
|
|
12
|
+
|
|
13
|
+
### Bug fixes
|
|
14
|
+
|
|
15
|
+
Fix a CSS issue that broke horizontal scroll width stabilization.
|
|
16
|
+
|
|
17
|
+
Fix a bug where `defaultLineHeight` could get an incorrect value in very narrow editors.
|
|
18
|
+
|
|
19
|
+
## 6.0.1 (2022-06-17)
|
|
20
|
+
|
|
21
|
+
### Bug fixes
|
|
22
|
+
|
|
23
|
+
Avoid DOM selection corruption when the editor doesn't have focus but has selection and updates its content.
|
|
24
|
+
|
|
25
|
+
Fall back to dispatching by key code when a key event produces a non-ASCII character (so that Cyrillic and Arabic keyboards can still use bindings specified with Latin characters).
|
|
26
|
+
|
|
1
27
|
## 6.0.0 (2022-06-08)
|
|
2
28
|
|
|
3
29
|
### New features
|
package/README.md
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
# @codemirror/view [](https://www.npmjs.org/package/@codemirror/view)
|
|
2
2
|
|
|
3
|
-
[ [**WEBSITE**](https://codemirror.net/
|
|
3
|
+
[ [**WEBSITE**](https://codemirror.net/) | [**DOCS**](https://codemirror.net/docs/ref/#view) | [**ISSUES**](https://github.com/codemirror/dev/issues) | [**FORUM**](https://discuss.codemirror.net/c/next/) | [**CHANGELOG**](https://github.com/codemirror/view/blob/main/CHANGELOG.md) ]
|
|
4
4
|
|
|
5
5
|
This package implements the DOM view component for the
|
|
6
|
-
[CodeMirror](https://codemirror.net/
|
|
6
|
+
[CodeMirror](https://codemirror.net/) code editor.
|
|
7
7
|
|
|
8
|
-
The [project page](https://codemirror.net/
|
|
9
|
-
number of [examples](https://codemirror.net/
|
|
10
|
-
[documentation](https://codemirror.net/
|
|
8
|
+
The [project page](https://codemirror.net/) has more information, a
|
|
9
|
+
number of [examples](https://codemirror.net/examples/) and the
|
|
10
|
+
[documentation](https://codemirror.net/docs/).
|
|
11
11
|
|
|
12
12
|
This code is released under an
|
|
13
13
|
[MIT license](https://github.com/codemirror/view/tree/main/LICENSE).
|
package/dist/index.cjs
CHANGED
|
@@ -2545,7 +2545,7 @@ class DocView extends ContentView {
|
|
|
2545
2545
|
}
|
|
2546
2546
|
// Sync the DOM selection to this.state.selection
|
|
2547
2547
|
updateSelection(mustRead = false, fromPointer = false) {
|
|
2548
|
-
if (mustRead)
|
|
2548
|
+
if (mustRead || !this.view.observer.selectionRange.focusNode)
|
|
2549
2549
|
this.view.observer.readSelectionRange();
|
|
2550
2550
|
if (!(fromPointer || this.mayControlSelection()) ||
|
|
2551
2551
|
browser.ios && this.view.inputState.rapidCompositionStart)
|
|
@@ -2580,7 +2580,8 @@ class DocView extends ContentView {
|
|
|
2580
2580
|
this.dom.focus({ preventScroll: true });
|
|
2581
2581
|
}
|
|
2582
2582
|
let rawSel = getSelection(this.root);
|
|
2583
|
-
if (
|
|
2583
|
+
if (!rawSel) ;
|
|
2584
|
+
else if (main.empty) {
|
|
2584
2585
|
// Work around https://bugzilla.mozilla.org/show_bug.cgi?id=1612076
|
|
2585
2586
|
if (browser.gecko) {
|
|
2586
2587
|
let nextTo = nextToUneditable(anchor.node, anchor.offset);
|
|
@@ -2622,7 +2623,7 @@ class DocView extends ContentView {
|
|
|
2622
2623
|
return;
|
|
2623
2624
|
let cursor = this.view.state.selection.main;
|
|
2624
2625
|
let sel = getSelection(this.root);
|
|
2625
|
-
if (!cursor.empty || !cursor.assoc || !sel.modify)
|
|
2626
|
+
if (!sel || !cursor.empty || !cursor.assoc || !sel.modify)
|
|
2626
2627
|
return;
|
|
2627
2628
|
let line = LineView.find(this, cursor.head);
|
|
2628
2629
|
if (!line)
|
|
@@ -2638,8 +2639,9 @@ class DocView extends ContentView {
|
|
|
2638
2639
|
sel.modify("move", cursor.assoc < 0 ? "forward" : "backward", "lineboundary");
|
|
2639
2640
|
}
|
|
2640
2641
|
mayControlSelection() {
|
|
2641
|
-
|
|
2642
|
-
|
|
2642
|
+
let active = this.root.activeElement;
|
|
2643
|
+
return active == this.dom ||
|
|
2644
|
+
hasSelection(this.dom, this.view.observer.selectionRange) && !(active && this.dom.contains(active));
|
|
2643
2645
|
}
|
|
2644
2646
|
nearest(dom) {
|
|
2645
2647
|
for (let cur = dom; cur;) {
|
|
@@ -2724,6 +2726,7 @@ class DocView extends ContentView {
|
|
|
2724
2726
|
// If no workable line exists, force a layout of a measurable element
|
|
2725
2727
|
let dummy = document.createElement("div"), lineHeight, charWidth;
|
|
2726
2728
|
dummy.className = "cm-line";
|
|
2729
|
+
dummy.style.width = "99999px";
|
|
2727
2730
|
dummy.textContent = "abc def ghi jkl mno pqr stu";
|
|
2728
2731
|
this.view.observer.ignore(() => {
|
|
2729
2732
|
this.dom.appendChild(dummy);
|
|
@@ -3134,7 +3137,8 @@ function posAtCoords(view, { x, y }, precise, bias = -1) {
|
|
|
3134
3137
|
let range = doc.caretRangeFromPoint(x, y);
|
|
3135
3138
|
if (range) {
|
|
3136
3139
|
({ startContainer: node, startOffset: offset } = range);
|
|
3137
|
-
if (browser.safari &&
|
|
3140
|
+
if (browser.safari && isSuspiciousSafariCaretResult(node, offset, x) ||
|
|
3141
|
+
browser.chrome && isSuspiciousChromeCaretResult(node, offset, x))
|
|
3138
3142
|
node = undefined;
|
|
3139
3143
|
}
|
|
3140
3144
|
}
|
|
@@ -3161,7 +3165,7 @@ function posAtCoordsImprecise(view, contentRect, block, x, y) {
|
|
|
3161
3165
|
// the space between lines as belonging to the last character of the
|
|
3162
3166
|
// line before. This is used to detect such a result so that it can be
|
|
3163
3167
|
// ignored (issue #401).
|
|
3164
|
-
function
|
|
3168
|
+
function isSuspiciousSafariCaretResult(node, offset, x) {
|
|
3165
3169
|
let len;
|
|
3166
3170
|
if (node.nodeType != 3 || offset != (len = node.nodeValue.length))
|
|
3167
3171
|
return false;
|
|
@@ -3170,6 +3174,22 @@ function isSuspiciousCaretResult(node, offset, x) {
|
|
|
3170
3174
|
return false;
|
|
3171
3175
|
return textRange(node, len - 1, len).getBoundingClientRect().left > x;
|
|
3172
3176
|
}
|
|
3177
|
+
// Chrome will move positions between lines to the start of the next line
|
|
3178
|
+
function isSuspiciousChromeCaretResult(node, offset, x) {
|
|
3179
|
+
if (offset != 0)
|
|
3180
|
+
return false;
|
|
3181
|
+
for (let cur = node;;) {
|
|
3182
|
+
let parent = cur.parentNode;
|
|
3183
|
+
if (!parent || parent.nodeType != 1 || parent.firstChild != cur)
|
|
3184
|
+
return false;
|
|
3185
|
+
if (parent.classList.contains("cm-line"))
|
|
3186
|
+
break;
|
|
3187
|
+
cur = parent;
|
|
3188
|
+
}
|
|
3189
|
+
let rect = node.nodeType == 1 ? node.getBoundingClientRect()
|
|
3190
|
+
: textRange(node, 0, Math.max(node.nodeValue.length, 1)).getBoundingClientRect();
|
|
3191
|
+
return x - rect.left > 5;
|
|
3192
|
+
}
|
|
3173
3193
|
function moveToLineBoundary(view, start, forward, includeWrap) {
|
|
3174
3194
|
let line = view.state.doc.lineAt(start.head);
|
|
3175
3195
|
let coords = !includeWrap || !view.lineWrapping ? null
|
|
@@ -3536,7 +3556,7 @@ function isInPrimarySelection(view, event) {
|
|
|
3536
3556
|
// On boundary clicks, check whether the coordinates are inside the
|
|
3537
3557
|
// selection's client rectangles
|
|
3538
3558
|
let sel = getSelection(view.root);
|
|
3539
|
-
if (sel.rangeCount == 0)
|
|
3559
|
+
if (!sel || sel.rangeCount == 0)
|
|
3540
3560
|
return true;
|
|
3541
3561
|
let rects = sel.getRangeAt(0).getClientRects();
|
|
3542
3562
|
for (let i = 0; i < rects.length; i++) {
|
|
@@ -3728,6 +3748,8 @@ function basicMouseSelection(view, event) {
|
|
|
3728
3748
|
}
|
|
3729
3749
|
if (extend)
|
|
3730
3750
|
return startSel.replaceRange(startSel.main.extend(range.from, range.to));
|
|
3751
|
+
else if (multiple && startSel.ranges.length > 1 && startSel.ranges.some(r => r.eq(range)))
|
|
3752
|
+
return removeRange(startSel, range);
|
|
3731
3753
|
else if (multiple)
|
|
3732
3754
|
return startSel.addRange(range);
|
|
3733
3755
|
else
|
|
@@ -3735,6 +3757,12 @@ function basicMouseSelection(view, event) {
|
|
|
3735
3757
|
}
|
|
3736
3758
|
};
|
|
3737
3759
|
}
|
|
3760
|
+
function removeRange(sel, range) {
|
|
3761
|
+
for (let i = 0;; i++) {
|
|
3762
|
+
if (sel.ranges[i].eq(range))
|
|
3763
|
+
return state.EditorSelection.create(sel.ranges.slice(0, i).concat(sel.ranges.slice(i + 1)), sel.mainIndex == i ? 0 : sel.mainIndex - (sel.mainIndex > i ? 1 : 0));
|
|
3764
|
+
}
|
|
3765
|
+
}
|
|
3738
3766
|
handlers.dragstart = (view, event) => {
|
|
3739
3767
|
let { selection: { main } } = view.state;
|
|
3740
3768
|
let { mouseSelection } = view.inputState;
|
|
@@ -5164,6 +5192,7 @@ const baseTheme$1 = buildTheme("." + baseThemeID, {
|
|
|
5164
5192
|
".cm-content": {
|
|
5165
5193
|
margin: 0,
|
|
5166
5194
|
flexGrow: 2,
|
|
5195
|
+
flexShrink: 0,
|
|
5167
5196
|
minHeight: "100%",
|
|
5168
5197
|
display: "block",
|
|
5169
5198
|
whiteSpace: "pre",
|
|
@@ -5179,7 +5208,8 @@ const baseTheme$1 = buildTheme("." + baseThemeID, {
|
|
|
5179
5208
|
whiteSpace_fallback: "pre-wrap",
|
|
5180
5209
|
whiteSpace: "break-spaces",
|
|
5181
5210
|
wordBreak: "break-word",
|
|
5182
|
-
overflowWrap: "anywhere"
|
|
5211
|
+
overflowWrap: "anywhere",
|
|
5212
|
+
flexShrink: 1
|
|
5183
5213
|
},
|
|
5184
5214
|
"&light .cm-content": { caretColor: "black" },
|
|
5185
5215
|
"&dark .cm-content": { caretColor: "white" },
|
|
@@ -5217,8 +5247,8 @@ const baseTheme$1 = buildTheme("." + baseThemeID, {
|
|
|
5217
5247
|
// Two animations defined so that we can switch between them to
|
|
5218
5248
|
// restart the animation without forcing another style
|
|
5219
5249
|
// recomputation.
|
|
5220
|
-
"@keyframes cm-blink": { "0%": {}, "50%": {
|
|
5221
|
-
"@keyframes cm-blink2": { "0%": {}, "50%": {
|
|
5250
|
+
"@keyframes cm-blink": { "0%": {}, "50%": { opacity: 0 }, "100%": {} },
|
|
5251
|
+
"@keyframes cm-blink2": { "0%": {}, "50%": { opacity: 0 }, "100%": {} },
|
|
5222
5252
|
".cm-cursor, .cm-dropCursor": {
|
|
5223
5253
|
position: "absolute",
|
|
5224
5254
|
borderLeft: "1.2px solid black",
|
|
@@ -5495,12 +5525,12 @@ class DOMObserver {
|
|
|
5495
5525
|
this.flush(false);
|
|
5496
5526
|
}
|
|
5497
5527
|
readSelectionRange() {
|
|
5498
|
-
let { root } = this.view
|
|
5528
|
+
let { root } = this.view;
|
|
5499
5529
|
// The Selection object is broken in shadow roots in Safari. See
|
|
5500
|
-
// https://github.com/codemirror/
|
|
5530
|
+
// https://github.com/codemirror/dev/issues/414
|
|
5501
5531
|
let range = browser.safari && root.nodeType == 11 && deepActiveElement() == this.view.contentDOM &&
|
|
5502
|
-
safariSelectionRangeHack(this.view) ||
|
|
5503
|
-
if (this.selectionRange.eq(range))
|
|
5532
|
+
safariSelectionRangeHack(this.view) || getSelection(root);
|
|
5533
|
+
if (!range || this.selectionRange.eq(range))
|
|
5504
5534
|
return false;
|
|
5505
5535
|
this.selectionRange.setRange(range);
|
|
5506
5536
|
return this.selectionChanged = true;
|
|
@@ -6885,11 +6915,11 @@ function modifiers(name, event, shift) {
|
|
|
6885
6915
|
name = "Shift-" + name;
|
|
6886
6916
|
return name;
|
|
6887
6917
|
}
|
|
6888
|
-
const handleKeyEvents = EditorView.domEventHandlers({
|
|
6918
|
+
const handleKeyEvents = state.Prec.default(EditorView.domEventHandlers({
|
|
6889
6919
|
keydown(event, view) {
|
|
6890
6920
|
return runHandlers(getKeymap(view.state), event, view, "editor");
|
|
6891
6921
|
}
|
|
6892
|
-
});
|
|
6922
|
+
}));
|
|
6893
6923
|
/**
|
|
6894
6924
|
Facet used for registering keymaps.
|
|
6895
6925
|
|
|
@@ -6966,7 +6996,8 @@ function buildKeymap(bindings, platform = currentPlatform) {
|
|
|
6966
6996
|
return bound;
|
|
6967
6997
|
}
|
|
6968
6998
|
function runHandlers(map, event, view, scope) {
|
|
6969
|
-
let name = w3cKeyname.keyName(event)
|
|
6999
|
+
let name = w3cKeyname.keyName(event);
|
|
7000
|
+
let charCode = state.codePointAt(name, 0), isChar = state.codePointSize(charCode) == name.length && name != " ";
|
|
6970
7001
|
let prefix = "", fallthrough = false;
|
|
6971
7002
|
if (storedPrefix && storedPrefix.view == view && storedPrefix.scope == scope) {
|
|
6972
7003
|
prefix = storedPrefix.prefix + " ";
|
|
@@ -6987,10 +7018,13 @@ function runHandlers(map, event, view, scope) {
|
|
|
6987
7018
|
if (scopeObj) {
|
|
6988
7019
|
if (runFor(scopeObj[prefix + modifiers(name, event, !isChar)]))
|
|
6989
7020
|
return true;
|
|
6990
|
-
if (isChar && (event.shiftKey || event.altKey || event.metaKey) &&
|
|
7021
|
+
if (isChar && (event.shiftKey || event.altKey || event.metaKey || charCode > 127) &&
|
|
6991
7022
|
(baseName = w3cKeyname.base[event.keyCode]) && baseName != name) {
|
|
6992
7023
|
if (runFor(scopeObj[prefix + modifiers(baseName, event, true)]))
|
|
6993
7024
|
return true;
|
|
7025
|
+
else if (event.shiftKey && w3cKeyname.shift[event.keyCode] != baseName &&
|
|
7026
|
+
runFor(scopeObj[prefix + modifiers(w3cKeyname.shift[event.keyCode], event, false)]))
|
|
7027
|
+
return true;
|
|
6994
7028
|
}
|
|
6995
7029
|
else if (isChar && event.shiftKey) {
|
|
6996
7030
|
if (runFor(scopeObj[prefix + modifiers(name, event, true)]))
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { Text, RangeSet, MapMode, RangeValue, Facet, StateEffect, ChangeSet, findClusterBreak, EditorSelection, EditorState, findColumn, CharCategory, Prec, Transaction, combineConfig, StateField, RangeSetBuilder,
|
|
1
|
+
import { Text, RangeSet, MapMode, RangeValue, Facet, StateEffect, ChangeSet, findClusterBreak, EditorSelection, EditorState, findColumn, CharCategory, Prec, Transaction, codePointAt, codePointSize, combineConfig, StateField, RangeSetBuilder, countColumn } from '@codemirror/state';
|
|
2
2
|
import { StyleModule } from 'style-mod';
|
|
3
|
-
import { keyName, base } from 'w3c-keyname';
|
|
3
|
+
import { keyName, base, shift } from 'w3c-keyname';
|
|
4
4
|
|
|
5
5
|
function getSelection(root) {
|
|
6
6
|
let target;
|
|
@@ -2539,7 +2539,7 @@ class DocView extends ContentView {
|
|
|
2539
2539
|
}
|
|
2540
2540
|
// Sync the DOM selection to this.state.selection
|
|
2541
2541
|
updateSelection(mustRead = false, fromPointer = false) {
|
|
2542
|
-
if (mustRead)
|
|
2542
|
+
if (mustRead || !this.view.observer.selectionRange.focusNode)
|
|
2543
2543
|
this.view.observer.readSelectionRange();
|
|
2544
2544
|
if (!(fromPointer || this.mayControlSelection()) ||
|
|
2545
2545
|
browser.ios && this.view.inputState.rapidCompositionStart)
|
|
@@ -2574,7 +2574,8 @@ class DocView extends ContentView {
|
|
|
2574
2574
|
this.dom.focus({ preventScroll: true });
|
|
2575
2575
|
}
|
|
2576
2576
|
let rawSel = getSelection(this.root);
|
|
2577
|
-
if (
|
|
2577
|
+
if (!rawSel) ;
|
|
2578
|
+
else if (main.empty) {
|
|
2578
2579
|
// Work around https://bugzilla.mozilla.org/show_bug.cgi?id=1612076
|
|
2579
2580
|
if (browser.gecko) {
|
|
2580
2581
|
let nextTo = nextToUneditable(anchor.node, anchor.offset);
|
|
@@ -2616,7 +2617,7 @@ class DocView extends ContentView {
|
|
|
2616
2617
|
return;
|
|
2617
2618
|
let cursor = this.view.state.selection.main;
|
|
2618
2619
|
let sel = getSelection(this.root);
|
|
2619
|
-
if (!cursor.empty || !cursor.assoc || !sel.modify)
|
|
2620
|
+
if (!sel || !cursor.empty || !cursor.assoc || !sel.modify)
|
|
2620
2621
|
return;
|
|
2621
2622
|
let line = LineView.find(this, cursor.head);
|
|
2622
2623
|
if (!line)
|
|
@@ -2632,8 +2633,9 @@ class DocView extends ContentView {
|
|
|
2632
2633
|
sel.modify("move", cursor.assoc < 0 ? "forward" : "backward", "lineboundary");
|
|
2633
2634
|
}
|
|
2634
2635
|
mayControlSelection() {
|
|
2635
|
-
|
|
2636
|
-
|
|
2636
|
+
let active = this.root.activeElement;
|
|
2637
|
+
return active == this.dom ||
|
|
2638
|
+
hasSelection(this.dom, this.view.observer.selectionRange) && !(active && this.dom.contains(active));
|
|
2637
2639
|
}
|
|
2638
2640
|
nearest(dom) {
|
|
2639
2641
|
for (let cur = dom; cur;) {
|
|
@@ -2718,6 +2720,7 @@ class DocView extends ContentView {
|
|
|
2718
2720
|
// If no workable line exists, force a layout of a measurable element
|
|
2719
2721
|
let dummy = document.createElement("div"), lineHeight, charWidth;
|
|
2720
2722
|
dummy.className = "cm-line";
|
|
2723
|
+
dummy.style.width = "99999px";
|
|
2721
2724
|
dummy.textContent = "abc def ghi jkl mno pqr stu";
|
|
2722
2725
|
this.view.observer.ignore(() => {
|
|
2723
2726
|
this.dom.appendChild(dummy);
|
|
@@ -3128,7 +3131,8 @@ function posAtCoords(view, { x, y }, precise, bias = -1) {
|
|
|
3128
3131
|
let range = doc.caretRangeFromPoint(x, y);
|
|
3129
3132
|
if (range) {
|
|
3130
3133
|
({ startContainer: node, startOffset: offset } = range);
|
|
3131
|
-
if (browser.safari &&
|
|
3134
|
+
if (browser.safari && isSuspiciousSafariCaretResult(node, offset, x) ||
|
|
3135
|
+
browser.chrome && isSuspiciousChromeCaretResult(node, offset, x))
|
|
3132
3136
|
node = undefined;
|
|
3133
3137
|
}
|
|
3134
3138
|
}
|
|
@@ -3155,7 +3159,7 @@ function posAtCoordsImprecise(view, contentRect, block, x, y) {
|
|
|
3155
3159
|
// the space between lines as belonging to the last character of the
|
|
3156
3160
|
// line before. This is used to detect such a result so that it can be
|
|
3157
3161
|
// ignored (issue #401).
|
|
3158
|
-
function
|
|
3162
|
+
function isSuspiciousSafariCaretResult(node, offset, x) {
|
|
3159
3163
|
let len;
|
|
3160
3164
|
if (node.nodeType != 3 || offset != (len = node.nodeValue.length))
|
|
3161
3165
|
return false;
|
|
@@ -3164,6 +3168,22 @@ function isSuspiciousCaretResult(node, offset, x) {
|
|
|
3164
3168
|
return false;
|
|
3165
3169
|
return textRange(node, len - 1, len).getBoundingClientRect().left > x;
|
|
3166
3170
|
}
|
|
3171
|
+
// Chrome will move positions between lines to the start of the next line
|
|
3172
|
+
function isSuspiciousChromeCaretResult(node, offset, x) {
|
|
3173
|
+
if (offset != 0)
|
|
3174
|
+
return false;
|
|
3175
|
+
for (let cur = node;;) {
|
|
3176
|
+
let parent = cur.parentNode;
|
|
3177
|
+
if (!parent || parent.nodeType != 1 || parent.firstChild != cur)
|
|
3178
|
+
return false;
|
|
3179
|
+
if (parent.classList.contains("cm-line"))
|
|
3180
|
+
break;
|
|
3181
|
+
cur = parent;
|
|
3182
|
+
}
|
|
3183
|
+
let rect = node.nodeType == 1 ? node.getBoundingClientRect()
|
|
3184
|
+
: textRange(node, 0, Math.max(node.nodeValue.length, 1)).getBoundingClientRect();
|
|
3185
|
+
return x - rect.left > 5;
|
|
3186
|
+
}
|
|
3167
3187
|
function moveToLineBoundary(view, start, forward, includeWrap) {
|
|
3168
3188
|
let line = view.state.doc.lineAt(start.head);
|
|
3169
3189
|
let coords = !includeWrap || !view.lineWrapping ? null
|
|
@@ -3530,7 +3550,7 @@ function isInPrimarySelection(view, event) {
|
|
|
3530
3550
|
// On boundary clicks, check whether the coordinates are inside the
|
|
3531
3551
|
// selection's client rectangles
|
|
3532
3552
|
let sel = getSelection(view.root);
|
|
3533
|
-
if (sel.rangeCount == 0)
|
|
3553
|
+
if (!sel || sel.rangeCount == 0)
|
|
3534
3554
|
return true;
|
|
3535
3555
|
let rects = sel.getRangeAt(0).getClientRects();
|
|
3536
3556
|
for (let i = 0; i < rects.length; i++) {
|
|
@@ -3722,6 +3742,8 @@ function basicMouseSelection(view, event) {
|
|
|
3722
3742
|
}
|
|
3723
3743
|
if (extend)
|
|
3724
3744
|
return startSel.replaceRange(startSel.main.extend(range.from, range.to));
|
|
3745
|
+
else if (multiple && startSel.ranges.length > 1 && startSel.ranges.some(r => r.eq(range)))
|
|
3746
|
+
return removeRange(startSel, range);
|
|
3725
3747
|
else if (multiple)
|
|
3726
3748
|
return startSel.addRange(range);
|
|
3727
3749
|
else
|
|
@@ -3729,6 +3751,12 @@ function basicMouseSelection(view, event) {
|
|
|
3729
3751
|
}
|
|
3730
3752
|
};
|
|
3731
3753
|
}
|
|
3754
|
+
function removeRange(sel, range) {
|
|
3755
|
+
for (let i = 0;; i++) {
|
|
3756
|
+
if (sel.ranges[i].eq(range))
|
|
3757
|
+
return EditorSelection.create(sel.ranges.slice(0, i).concat(sel.ranges.slice(i + 1)), sel.mainIndex == i ? 0 : sel.mainIndex - (sel.mainIndex > i ? 1 : 0));
|
|
3758
|
+
}
|
|
3759
|
+
}
|
|
3732
3760
|
handlers.dragstart = (view, event) => {
|
|
3733
3761
|
let { selection: { main } } = view.state;
|
|
3734
3762
|
let { mouseSelection } = view.inputState;
|
|
@@ -5157,6 +5185,7 @@ const baseTheme$1 = /*@__PURE__*/buildTheme("." + baseThemeID, {
|
|
|
5157
5185
|
".cm-content": {
|
|
5158
5186
|
margin: 0,
|
|
5159
5187
|
flexGrow: 2,
|
|
5188
|
+
flexShrink: 0,
|
|
5160
5189
|
minHeight: "100%",
|
|
5161
5190
|
display: "block",
|
|
5162
5191
|
whiteSpace: "pre",
|
|
@@ -5172,7 +5201,8 @@ const baseTheme$1 = /*@__PURE__*/buildTheme("." + baseThemeID, {
|
|
|
5172
5201
|
whiteSpace_fallback: "pre-wrap",
|
|
5173
5202
|
whiteSpace: "break-spaces",
|
|
5174
5203
|
wordBreak: "break-word",
|
|
5175
|
-
overflowWrap: "anywhere"
|
|
5204
|
+
overflowWrap: "anywhere",
|
|
5205
|
+
flexShrink: 1
|
|
5176
5206
|
},
|
|
5177
5207
|
"&light .cm-content": { caretColor: "black" },
|
|
5178
5208
|
"&dark .cm-content": { caretColor: "white" },
|
|
@@ -5210,8 +5240,8 @@ const baseTheme$1 = /*@__PURE__*/buildTheme("." + baseThemeID, {
|
|
|
5210
5240
|
// Two animations defined so that we can switch between them to
|
|
5211
5241
|
// restart the animation without forcing another style
|
|
5212
5242
|
// recomputation.
|
|
5213
|
-
"@keyframes cm-blink": { "0%": {}, "50%": {
|
|
5214
|
-
"@keyframes cm-blink2": { "0%": {}, "50%": {
|
|
5243
|
+
"@keyframes cm-blink": { "0%": {}, "50%": { opacity: 0 }, "100%": {} },
|
|
5244
|
+
"@keyframes cm-blink2": { "0%": {}, "50%": { opacity: 0 }, "100%": {} },
|
|
5215
5245
|
".cm-cursor, .cm-dropCursor": {
|
|
5216
5246
|
position: "absolute",
|
|
5217
5247
|
borderLeft: "1.2px solid black",
|
|
@@ -5488,12 +5518,12 @@ class DOMObserver {
|
|
|
5488
5518
|
this.flush(false);
|
|
5489
5519
|
}
|
|
5490
5520
|
readSelectionRange() {
|
|
5491
|
-
let { root } = this.view
|
|
5521
|
+
let { root } = this.view;
|
|
5492
5522
|
// The Selection object is broken in shadow roots in Safari. See
|
|
5493
|
-
// https://github.com/codemirror/
|
|
5523
|
+
// https://github.com/codemirror/dev/issues/414
|
|
5494
5524
|
let range = browser.safari && root.nodeType == 11 && deepActiveElement() == this.view.contentDOM &&
|
|
5495
|
-
safariSelectionRangeHack(this.view) ||
|
|
5496
|
-
if (this.selectionRange.eq(range))
|
|
5525
|
+
safariSelectionRangeHack(this.view) || getSelection(root);
|
|
5526
|
+
if (!range || this.selectionRange.eq(range))
|
|
5497
5527
|
return false;
|
|
5498
5528
|
this.selectionRange.setRange(range);
|
|
5499
5529
|
return this.selectionChanged = true;
|
|
@@ -6878,11 +6908,11 @@ function modifiers(name, event, shift) {
|
|
|
6878
6908
|
name = "Shift-" + name;
|
|
6879
6909
|
return name;
|
|
6880
6910
|
}
|
|
6881
|
-
const handleKeyEvents = /*@__PURE__*/EditorView.domEventHandlers({
|
|
6911
|
+
const handleKeyEvents = /*@__PURE__*/Prec.default(/*@__PURE__*/EditorView.domEventHandlers({
|
|
6882
6912
|
keydown(event, view) {
|
|
6883
6913
|
return runHandlers(getKeymap(view.state), event, view, "editor");
|
|
6884
6914
|
}
|
|
6885
|
-
});
|
|
6915
|
+
}));
|
|
6886
6916
|
/**
|
|
6887
6917
|
Facet used for registering keymaps.
|
|
6888
6918
|
|
|
@@ -6959,7 +6989,8 @@ function buildKeymap(bindings, platform = currentPlatform) {
|
|
|
6959
6989
|
return bound;
|
|
6960
6990
|
}
|
|
6961
6991
|
function runHandlers(map, event, view, scope) {
|
|
6962
|
-
let name = keyName(event)
|
|
6992
|
+
let name = keyName(event);
|
|
6993
|
+
let charCode = codePointAt(name, 0), isChar = codePointSize(charCode) == name.length && name != " ";
|
|
6963
6994
|
let prefix = "", fallthrough = false;
|
|
6964
6995
|
if (storedPrefix && storedPrefix.view == view && storedPrefix.scope == scope) {
|
|
6965
6996
|
prefix = storedPrefix.prefix + " ";
|
|
@@ -6980,10 +7011,13 @@ function runHandlers(map, event, view, scope) {
|
|
|
6980
7011
|
if (scopeObj) {
|
|
6981
7012
|
if (runFor(scopeObj[prefix + modifiers(name, event, !isChar)]))
|
|
6982
7013
|
return true;
|
|
6983
|
-
if (isChar && (event.shiftKey || event.altKey || event.metaKey) &&
|
|
7014
|
+
if (isChar && (event.shiftKey || event.altKey || event.metaKey || charCode > 127) &&
|
|
6984
7015
|
(baseName = base[event.keyCode]) && baseName != name) {
|
|
6985
7016
|
if (runFor(scopeObj[prefix + modifiers(baseName, event, true)]))
|
|
6986
7017
|
return true;
|
|
7018
|
+
else if (event.shiftKey && shift[event.keyCode] != baseName &&
|
|
7019
|
+
runFor(scopeObj[prefix + modifiers(shift[event.keyCode], event, false)]))
|
|
7020
|
+
return true;
|
|
6987
7021
|
}
|
|
6988
7022
|
else if (isChar && event.shiftKey) {
|
|
6989
7023
|
if (runFor(scopeObj[prefix + modifiers(name, event, true)]))
|