prosemirror-view 1.31.7 → 1.31.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +10 -0
- package/dist/index.cjs +53 -38
- package/dist/index.d.cts +11 -9
- package/dist/index.d.ts +11 -9
- package/dist/index.js +52 -31
- package/package.json +1 -1
- package/src/capturekeys.ts +16 -12
- package/src/decoration.ts +13 -8
- package/src/viewdesc.ts +20 -13
package/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,13 @@
|
|
|
1
|
+
## 1.31.8 (2023-09-12)
|
|
2
|
+
|
|
3
|
+
### Bug fixes
|
|
4
|
+
|
|
5
|
+
Fix a bug that broke arrow motion near uneditable nodes on Chrome in some situations.
|
|
6
|
+
|
|
7
|
+
Fix an issue that broke backspace at the end of a textblock that ended in a newline on Chrome.
|
|
8
|
+
|
|
9
|
+
Fix a crash in the way inline decorations that ended right after a node end position were drawn.
|
|
10
|
+
|
|
1
11
|
## 1.31.7 (2023-07-28)
|
|
2
12
|
|
|
3
13
|
### Bug fixes
|
package/dist/index.cjs
CHANGED
|
@@ -32,10 +32,6 @@ function _defineProperties(target, props) { for (var i = 0; i < props.length; i+
|
|
|
32
32
|
|
|
33
33
|
function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
|
|
34
34
|
|
|
35
|
-
Object.defineProperty(exports, '__esModule', {
|
|
36
|
-
value: true
|
|
37
|
-
});
|
|
38
|
-
|
|
39
35
|
var prosemirrorState = require('prosemirror-state');
|
|
40
36
|
|
|
41
37
|
var prosemirrorModel = require('prosemirror-model');
|
|
@@ -2190,9 +2186,13 @@ var ViewTreeUpdater = function () {
|
|
|
2190
2186
|
return true;
|
|
2191
2187
|
} else if (!locked && (updated = this.recreateWrapper(next, node, outerDeco, innerDeco, view, pos))) {
|
|
2192
2188
|
this.top.children[this.index] = updated;
|
|
2193
|
-
|
|
2194
|
-
updated.
|
|
2195
|
-
|
|
2189
|
+
|
|
2190
|
+
if (updated.contentDOM) {
|
|
2191
|
+
updated.dirty = CONTENT_DIRTY;
|
|
2192
|
+
updated.updateChildren(view, pos + 1);
|
|
2193
|
+
updated.dirty = NOT_DIRTY;
|
|
2194
|
+
}
|
|
2195
|
+
|
|
2196
2196
|
this.changed = true;
|
|
2197
2197
|
this.index++;
|
|
2198
2198
|
return true;
|
|
@@ -2209,25 +2209,27 @@ var ViewTreeUpdater = function () {
|
|
|
2209
2209
|
value: function recreateWrapper(next, node, outerDeco, innerDeco, view, pos) {
|
|
2210
2210
|
if (next.dirty || node.isAtom || !next.children.length || !next.node.content.eq(node.content)) return null;
|
|
2211
2211
|
var wrapper = NodeViewDesc.create(this.top, node, outerDeco, innerDeco, view, pos);
|
|
2212
|
-
if (!wrapper.contentDOM) return null;
|
|
2213
|
-
wrapper.children = next.children;
|
|
2214
|
-
next.children = [];
|
|
2215
|
-
next.destroy();
|
|
2216
2212
|
|
|
2217
|
-
|
|
2218
|
-
|
|
2213
|
+
if (wrapper.contentDOM) {
|
|
2214
|
+
wrapper.children = next.children;
|
|
2215
|
+
next.children = [];
|
|
2216
|
+
|
|
2217
|
+
var _iterator = _createForOfIteratorHelper(wrapper.children),
|
|
2218
|
+
_step;
|
|
2219
2219
|
|
|
2220
|
-
|
|
2221
|
-
|
|
2222
|
-
|
|
2223
|
-
|
|
2220
|
+
try {
|
|
2221
|
+
for (_iterator.s(); !(_step = _iterator.n()).done;) {
|
|
2222
|
+
var ch = _step.value;
|
|
2223
|
+
ch.parent = wrapper;
|
|
2224
|
+
}
|
|
2225
|
+
} catch (err) {
|
|
2226
|
+
_iterator.e(err);
|
|
2227
|
+
} finally {
|
|
2228
|
+
_iterator.f();
|
|
2224
2229
|
}
|
|
2225
|
-
} catch (err) {
|
|
2226
|
-
_iterator.e(err);
|
|
2227
|
-
} finally {
|
|
2228
|
-
_iterator.f();
|
|
2229
2230
|
}
|
|
2230
2231
|
|
|
2232
|
+
next.destroy();
|
|
2231
2233
|
return wrapper;
|
|
2232
2234
|
}
|
|
2233
2235
|
}, {
|
|
@@ -2364,14 +2366,18 @@ function iterDeco(parent, deco, onWidget, onNode) {
|
|
|
2364
2366
|
restNode = null;
|
|
2365
2367
|
|
|
2366
2368
|
for (var parentIndex = 0;;) {
|
|
2367
|
-
|
|
2368
|
-
|
|
2369
|
-
|
|
2369
|
+
var widget = void 0,
|
|
2370
|
+
widgets = void 0;
|
|
2371
|
+
|
|
2372
|
+
while (decoIndex < locals.length && locals[decoIndex].to == offset) {
|
|
2373
|
+
var next = locals[decoIndex++];
|
|
2370
2374
|
|
|
2371
|
-
|
|
2372
|
-
(widgets || (widgets = [widget])).push(
|
|
2375
|
+
if (next.widget) {
|
|
2376
|
+
if (!widget) widget = next;else (widgets || (widgets = [widget])).push(next);
|
|
2373
2377
|
}
|
|
2378
|
+
}
|
|
2374
2379
|
|
|
2380
|
+
if (widget) {
|
|
2375
2381
|
if (widgets) {
|
|
2376
2382
|
widgets.sort(compareSide);
|
|
2377
2383
|
|
|
@@ -2773,10 +2779,10 @@ function nodeLen(node) {
|
|
|
2773
2779
|
return node.nodeType == 3 ? node.nodeValue.length : node.childNodes.length;
|
|
2774
2780
|
}
|
|
2775
2781
|
|
|
2776
|
-
function isIgnorable(dom) {
|
|
2782
|
+
function isIgnorable(dom, dir) {
|
|
2777
2783
|
if (dom.contentEditable == "false") return true;
|
|
2778
2784
|
var desc = dom.pmViewDesc;
|
|
2779
|
-
return desc && desc.size == 0 && (dom.nextSibling || dom.nodeName != "BR");
|
|
2785
|
+
return desc && desc.size == 0 && (dir < 0 || dom.nextSibling || dom.nodeName != "BR");
|
|
2780
2786
|
}
|
|
2781
2787
|
|
|
2782
2788
|
function skipIgnoredNodes(view, dir) {
|
|
@@ -2791,7 +2797,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2791
2797
|
var moveNode,
|
|
2792
2798
|
moveOffset,
|
|
2793
2799
|
force = false;
|
|
2794
|
-
if (gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset])) force = true;
|
|
2800
|
+
if (gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset], -1)) force = true;
|
|
2795
2801
|
|
|
2796
2802
|
for (;;) {
|
|
2797
2803
|
if (offset > 0) {
|
|
@@ -2800,7 +2806,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2800
2806
|
} else {
|
|
2801
2807
|
var before = node.childNodes[offset - 1];
|
|
2802
2808
|
|
|
2803
|
-
if (isIgnorable(before)) {
|
|
2809
|
+
if (isIgnorable(before, -1)) {
|
|
2804
2810
|
moveNode = node;
|
|
2805
2811
|
moveOffset = --offset;
|
|
2806
2812
|
} else if (before.nodeType == 3) {
|
|
@@ -2813,7 +2819,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2813
2819
|
} else {
|
|
2814
2820
|
var prev = node.previousSibling;
|
|
2815
2821
|
|
|
2816
|
-
while (prev && isIgnorable(prev)) {
|
|
2822
|
+
while (prev && isIgnorable(prev, -1)) {
|
|
2817
2823
|
moveNode = node.parentNode;
|
|
2818
2824
|
moveOffset = domIndex(prev);
|
|
2819
2825
|
prev = prev.previousSibling;
|
|
@@ -2846,7 +2852,7 @@ function skipIgnoredNodesAfter(view) {
|
|
|
2846
2852
|
if (node.nodeType != 1) break;
|
|
2847
2853
|
var after = node.childNodes[offset];
|
|
2848
2854
|
|
|
2849
|
-
if (isIgnorable(after)) {
|
|
2855
|
+
if (isIgnorable(after, 1)) {
|
|
2850
2856
|
moveNode = node;
|
|
2851
2857
|
moveOffset = ++offset;
|
|
2852
2858
|
} else break;
|
|
@@ -2855,7 +2861,7 @@ function skipIgnoredNodesAfter(view) {
|
|
|
2855
2861
|
} else {
|
|
2856
2862
|
var next = node.nextSibling;
|
|
2857
2863
|
|
|
2858
|
-
while (next && isIgnorable(next)) {
|
|
2864
|
+
while (next && isIgnorable(next, 1)) {
|
|
2859
2865
|
moveNode = next.parentNode;
|
|
2860
2866
|
moveOffset = domIndex(next) + 1;
|
|
2861
2867
|
next = next.nextSibling;
|
|
@@ -2888,8 +2894,10 @@ function textNodeAfter(node, offset) {
|
|
|
2888
2894
|
}
|
|
2889
2895
|
|
|
2890
2896
|
while (node && offset < node.childNodes.length) {
|
|
2891
|
-
|
|
2892
|
-
if (
|
|
2897
|
+
var next = node.childNodes[offset];
|
|
2898
|
+
if (next.nodeType == 3) return next;
|
|
2899
|
+
if (next.nodeType == 1 && next.contentEditable == "false") break;
|
|
2900
|
+
node = next;
|
|
2893
2901
|
offset = 0;
|
|
2894
2902
|
}
|
|
2895
2903
|
}
|
|
@@ -2901,8 +2909,10 @@ function textNodeBefore(node, offset) {
|
|
|
2901
2909
|
}
|
|
2902
2910
|
|
|
2903
2911
|
while (node && offset) {
|
|
2904
|
-
|
|
2905
|
-
if (
|
|
2912
|
+
var next = node.childNodes[offset - 1];
|
|
2913
|
+
if (next.nodeType == 3) return next;
|
|
2914
|
+
if (next.nodeType == 1 && next.contentEditable == "false") break;
|
|
2915
|
+
node = next;
|
|
2906
2916
|
offset = node.childNodes.length;
|
|
2907
2917
|
}
|
|
2908
2918
|
}
|
|
@@ -3059,7 +3069,7 @@ function captureKeyDown(view, event) {
|
|
|
3059
3069
|
} else if (code == 38 || mac && code == 80 && mods == "c") {
|
|
3060
3070
|
return selectVertically(view, -1, mods) || skipIgnoredNodes(view, -1);
|
|
3061
3071
|
} else if (code == 40 || mac && code == 78 && mods == "c") {
|
|
3062
|
-
return safariDownArrowBug(view) || selectVertically(view, 1, mods) ||
|
|
3072
|
+
return safariDownArrowBug(view) || selectVertically(view, 1, mods) || skipIgnoredNodes(view, 1);
|
|
3063
3073
|
} else if (mods == (mac ? "m" : "c") && (code == 66 || code == 73 || code == 89 || code == 90)) {
|
|
3064
3074
|
return true;
|
|
3065
3075
|
}
|
|
@@ -4296,6 +4306,11 @@ var Decoration = function () {
|
|
|
4296
4306
|
get: function get() {
|
|
4297
4307
|
return this.type instanceof InlineType;
|
|
4298
4308
|
}
|
|
4309
|
+
}, {
|
|
4310
|
+
key: "widget",
|
|
4311
|
+
get: function get() {
|
|
4312
|
+
return this.type instanceof WidgetType;
|
|
4313
|
+
}
|
|
4299
4314
|
}], [{
|
|
4300
4315
|
key: "widget",
|
|
4301
4316
|
value: function widget(pos, toDOM, spec) {
|
package/dist/index.d.cts
CHANGED
|
@@ -2,9 +2,9 @@ import { EditorState, Transaction, Selection, Plugin } from 'prosemirror-state';
|
|
|
2
2
|
import { Mark, Node, ParseRule, Slice, ResolvedPos, DOMParser, DOMSerializer } from 'prosemirror-model';
|
|
3
3
|
import { Mapping } from 'prosemirror-transform';
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
type DOMNode = InstanceType<typeof window.Node>;
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
type WidgetConstructor = ((view: EditorView, getPos: () => number | undefined) => DOMNode) | DOMNode;
|
|
8
8
|
/**
|
|
9
9
|
Decoration objects can be provided to the view through the
|
|
10
10
|
[`decorations` prop](https://prosemirror.net/docs/ref/#view.EditorProps.decorations). They come in
|
|
@@ -125,7 +125,7 @@ A set of attributes to add to a decorated node. Most properties
|
|
|
125
125
|
simply directly correspond to DOM attributes of the same name,
|
|
126
126
|
which will be set to the property's value. These are exceptions:
|
|
127
127
|
*/
|
|
128
|
-
|
|
128
|
+
type DecorationAttrs = {
|
|
129
129
|
/**
|
|
130
130
|
When non-null, the target node is wrapped in a DOM element of
|
|
131
131
|
this type (and the other attributes are applied to this element).
|
|
@@ -166,7 +166,8 @@ updates create a new value.
|
|
|
166
166
|
declare class DecorationSet implements DecorationSource {
|
|
167
167
|
/**
|
|
168
168
|
Create a set of decorations, using the structure of the given
|
|
169
|
-
document.
|
|
169
|
+
document. This will consume (modify) the `decorations` array, so
|
|
170
|
+
you must make a copy if you want need to preserve that.
|
|
170
171
|
*/
|
|
171
172
|
static create(doc: Node, decorations: Decoration[]): DecorationSet;
|
|
172
173
|
/**
|
|
@@ -193,8 +194,9 @@ declare class DecorationSet implements DecorationSource {
|
|
|
193
194
|
}): DecorationSet;
|
|
194
195
|
/**
|
|
195
196
|
Add the given array of decorations to the ones in the set,
|
|
196
|
-
producing a new set.
|
|
197
|
-
create the appropriate tree
|
|
197
|
+
producing a new set. Consumes the `decorations` array. Needs
|
|
198
|
+
access to the current document to create the appropriate tree
|
|
199
|
+
structure.
|
|
198
200
|
*/
|
|
199
201
|
add(doc: Node, decorations: Decoration[]): DecorationSet;
|
|
200
202
|
private addInner;
|
|
@@ -356,7 +358,7 @@ declare class NodeViewDesc extends ViewDesc {
|
|
|
356
358
|
parseRule(): ParseRule | null;
|
|
357
359
|
matchesNode(node: Node, outerDeco: readonly Decoration[], innerDeco: DecorationSource): boolean;
|
|
358
360
|
get size(): number;
|
|
359
|
-
get border():
|
|
361
|
+
get border(): 0 | 1;
|
|
360
362
|
updateChildren(view: EditorView, pos: number): void;
|
|
361
363
|
localCompositionInfo(view: EditorView, pos: number): {
|
|
362
364
|
node: Text;
|
|
@@ -604,12 +606,12 @@ declare class EditorView {
|
|
|
604
606
|
The type of function [provided](https://prosemirror.net/docs/ref/#view.EditorProps.nodeViews) to
|
|
605
607
|
create [node views](https://prosemirror.net/docs/ref/#view.NodeView).
|
|
606
608
|
*/
|
|
607
|
-
|
|
609
|
+
type NodeViewConstructor = (node: Node, view: EditorView, getPos: () => number | undefined, decorations: readonly Decoration[], innerDecorations: DecorationSource) => NodeView;
|
|
608
610
|
/**
|
|
609
611
|
The function types [used](https://prosemirror.net/docs/ref/#view.EditorProps.markViews) to create
|
|
610
612
|
mark views.
|
|
611
613
|
*/
|
|
612
|
-
|
|
614
|
+
type MarkViewConstructor = (mark: Mark, view: EditorView, inline: boolean) => {
|
|
613
615
|
dom: HTMLElement;
|
|
614
616
|
contentDOM?: HTMLElement;
|
|
615
617
|
};
|
package/dist/index.d.ts
CHANGED
|
@@ -2,9 +2,9 @@ import { EditorState, Transaction, Selection, Plugin } from 'prosemirror-state';
|
|
|
2
2
|
import { Mark, Node, ParseRule, Slice, ResolvedPos, DOMParser, DOMSerializer } from 'prosemirror-model';
|
|
3
3
|
import { Mapping } from 'prosemirror-transform';
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
type DOMNode = InstanceType<typeof window.Node>;
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
type WidgetConstructor = ((view: EditorView, getPos: () => number | undefined) => DOMNode) | DOMNode;
|
|
8
8
|
/**
|
|
9
9
|
Decoration objects can be provided to the view through the
|
|
10
10
|
[`decorations` prop](https://prosemirror.net/docs/ref/#view.EditorProps.decorations). They come in
|
|
@@ -125,7 +125,7 @@ A set of attributes to add to a decorated node. Most properties
|
|
|
125
125
|
simply directly correspond to DOM attributes of the same name,
|
|
126
126
|
which will be set to the property's value. These are exceptions:
|
|
127
127
|
*/
|
|
128
|
-
|
|
128
|
+
type DecorationAttrs = {
|
|
129
129
|
/**
|
|
130
130
|
When non-null, the target node is wrapped in a DOM element of
|
|
131
131
|
this type (and the other attributes are applied to this element).
|
|
@@ -166,7 +166,8 @@ updates create a new value.
|
|
|
166
166
|
declare class DecorationSet implements DecorationSource {
|
|
167
167
|
/**
|
|
168
168
|
Create a set of decorations, using the structure of the given
|
|
169
|
-
document.
|
|
169
|
+
document. This will consume (modify) the `decorations` array, so
|
|
170
|
+
you must make a copy if you want need to preserve that.
|
|
170
171
|
*/
|
|
171
172
|
static create(doc: Node, decorations: Decoration[]): DecorationSet;
|
|
172
173
|
/**
|
|
@@ -193,8 +194,9 @@ declare class DecorationSet implements DecorationSource {
|
|
|
193
194
|
}): DecorationSet;
|
|
194
195
|
/**
|
|
195
196
|
Add the given array of decorations to the ones in the set,
|
|
196
|
-
producing a new set.
|
|
197
|
-
create the appropriate tree
|
|
197
|
+
producing a new set. Consumes the `decorations` array. Needs
|
|
198
|
+
access to the current document to create the appropriate tree
|
|
199
|
+
structure.
|
|
198
200
|
*/
|
|
199
201
|
add(doc: Node, decorations: Decoration[]): DecorationSet;
|
|
200
202
|
private addInner;
|
|
@@ -356,7 +358,7 @@ declare class NodeViewDesc extends ViewDesc {
|
|
|
356
358
|
parseRule(): ParseRule | null;
|
|
357
359
|
matchesNode(node: Node, outerDeco: readonly Decoration[], innerDeco: DecorationSource): boolean;
|
|
358
360
|
get size(): number;
|
|
359
|
-
get border():
|
|
361
|
+
get border(): 0 | 1;
|
|
360
362
|
updateChildren(view: EditorView, pos: number): void;
|
|
361
363
|
localCompositionInfo(view: EditorView, pos: number): {
|
|
362
364
|
node: Text;
|
|
@@ -604,12 +606,12 @@ declare class EditorView {
|
|
|
604
606
|
The type of function [provided](https://prosemirror.net/docs/ref/#view.EditorProps.nodeViews) to
|
|
605
607
|
create [node views](https://prosemirror.net/docs/ref/#view.NodeView).
|
|
606
608
|
*/
|
|
607
|
-
|
|
609
|
+
type NodeViewConstructor = (node: Node, view: EditorView, getPos: () => number | undefined, decorations: readonly Decoration[], innerDecorations: DecorationSource) => NodeView;
|
|
608
610
|
/**
|
|
609
611
|
The function types [used](https://prosemirror.net/docs/ref/#view.EditorProps.markViews) to create
|
|
610
612
|
mark views.
|
|
611
613
|
*/
|
|
612
|
-
|
|
614
|
+
type MarkViewConstructor = (mark: Mark, view: EditorView, inline: boolean) => {
|
|
613
615
|
dom: HTMLElement;
|
|
614
616
|
contentDOM?: HTMLElement;
|
|
615
617
|
};
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { TextSelection, NodeSelection,
|
|
1
|
+
import { TextSelection, NodeSelection, AllSelection, Selection } from 'prosemirror-state';
|
|
2
2
|
import { DOMSerializer, Fragment, Mark, Slice, DOMParser } from 'prosemirror-model';
|
|
3
3
|
import { dropPoint } from 'prosemirror-transform';
|
|
4
4
|
|
|
@@ -1810,9 +1810,11 @@ class ViewTreeUpdater {
|
|
|
1810
1810
|
}
|
|
1811
1811
|
else if (!locked && (updated = this.recreateWrapper(next, node, outerDeco, innerDeco, view, pos))) {
|
|
1812
1812
|
this.top.children[this.index] = updated;
|
|
1813
|
-
updated.
|
|
1814
|
-
|
|
1815
|
-
|
|
1813
|
+
if (updated.contentDOM) {
|
|
1814
|
+
updated.dirty = CONTENT_DIRTY;
|
|
1815
|
+
updated.updateChildren(view, pos + 1);
|
|
1816
|
+
updated.dirty = NOT_DIRTY;
|
|
1817
|
+
}
|
|
1816
1818
|
this.changed = true;
|
|
1817
1819
|
this.index++;
|
|
1818
1820
|
return true;
|
|
@@ -1829,13 +1831,13 @@ class ViewTreeUpdater {
|
|
|
1829
1831
|
!next.node.content.eq(node.content))
|
|
1830
1832
|
return null;
|
|
1831
1833
|
let wrapper = NodeViewDesc.create(this.top, node, outerDeco, innerDeco, view, pos);
|
|
1832
|
-
if (
|
|
1833
|
-
|
|
1834
|
-
|
|
1835
|
-
|
|
1834
|
+
if (wrapper.contentDOM) {
|
|
1835
|
+
wrapper.children = next.children;
|
|
1836
|
+
next.children = [];
|
|
1837
|
+
for (let ch of wrapper.children)
|
|
1838
|
+
ch.parent = wrapper;
|
|
1839
|
+
}
|
|
1836
1840
|
next.destroy();
|
|
1837
|
-
for (let ch of wrapper.children)
|
|
1838
|
-
ch.parent = wrapper;
|
|
1839
1841
|
return wrapper;
|
|
1840
1842
|
}
|
|
1841
1843
|
// Insert the node as a newly created node desc.
|
|
@@ -1963,10 +1965,17 @@ function iterDeco(parent, deco, onWidget, onNode) {
|
|
|
1963
1965
|
}
|
|
1964
1966
|
let decoIndex = 0, active = [], restNode = null;
|
|
1965
1967
|
for (let parentIndex = 0;;) {
|
|
1966
|
-
|
|
1967
|
-
|
|
1968
|
-
|
|
1969
|
-
|
|
1968
|
+
let widget, widgets;
|
|
1969
|
+
while (decoIndex < locals.length && locals[decoIndex].to == offset) {
|
|
1970
|
+
let next = locals[decoIndex++];
|
|
1971
|
+
if (next.widget) {
|
|
1972
|
+
if (!widget)
|
|
1973
|
+
widget = next;
|
|
1974
|
+
else
|
|
1975
|
+
(widgets || (widgets = [widget])).push(next);
|
|
1976
|
+
}
|
|
1977
|
+
}
|
|
1978
|
+
if (widget) {
|
|
1970
1979
|
if (widgets) {
|
|
1971
1980
|
widgets.sort(compareSide);
|
|
1972
1981
|
for (let i = 0; i < widgets.length; i++)
|
|
@@ -2355,11 +2364,11 @@ function selectHorizontally(view, dir, mods) {
|
|
|
2355
2364
|
function nodeLen(node) {
|
|
2356
2365
|
return node.nodeType == 3 ? node.nodeValue.length : node.childNodes.length;
|
|
2357
2366
|
}
|
|
2358
|
-
function isIgnorable(dom) {
|
|
2367
|
+
function isIgnorable(dom, dir) {
|
|
2359
2368
|
if (dom.contentEditable == "false")
|
|
2360
2369
|
return true;
|
|
2361
2370
|
let desc = dom.pmViewDesc;
|
|
2362
|
-
return desc && desc.size == 0 && (dom.nextSibling || dom.nodeName != "BR");
|
|
2371
|
+
return desc && desc.size == 0 && (dir < 0 || dom.nextSibling || dom.nodeName != "BR");
|
|
2363
2372
|
}
|
|
2364
2373
|
function skipIgnoredNodes(view, dir) {
|
|
2365
2374
|
return dir < 0 ? skipIgnoredNodesBefore(view) : skipIgnoredNodesAfter(view);
|
|
@@ -2375,7 +2384,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2375
2384
|
// Gecko will do odd things when the selection is directly in front
|
|
2376
2385
|
// of a non-editable node, so in that case, move it into the next
|
|
2377
2386
|
// node if possible. Issue prosemirror/prosemirror#832.
|
|
2378
|
-
if (gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset]))
|
|
2387
|
+
if (gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset], -1))
|
|
2379
2388
|
force = true;
|
|
2380
2389
|
for (;;) {
|
|
2381
2390
|
if (offset > 0) {
|
|
@@ -2384,7 +2393,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2384
2393
|
}
|
|
2385
2394
|
else {
|
|
2386
2395
|
let before = node.childNodes[offset - 1];
|
|
2387
|
-
if (isIgnorable(before)) {
|
|
2396
|
+
if (isIgnorable(before, -1)) {
|
|
2388
2397
|
moveNode = node;
|
|
2389
2398
|
moveOffset = --offset;
|
|
2390
2399
|
}
|
|
@@ -2401,7 +2410,7 @@ function skipIgnoredNodesBefore(view) {
|
|
|
2401
2410
|
}
|
|
2402
2411
|
else {
|
|
2403
2412
|
let prev = node.previousSibling;
|
|
2404
|
-
while (prev && isIgnorable(prev)) {
|
|
2413
|
+
while (prev && isIgnorable(prev, -1)) {
|
|
2405
2414
|
moveNode = node.parentNode;
|
|
2406
2415
|
moveOffset = domIndex(prev);
|
|
2407
2416
|
prev = prev.previousSibling;
|
|
@@ -2437,7 +2446,7 @@ function skipIgnoredNodesAfter(view) {
|
|
|
2437
2446
|
if (node.nodeType != 1)
|
|
2438
2447
|
break;
|
|
2439
2448
|
let after = node.childNodes[offset];
|
|
2440
|
-
if (isIgnorable(after)) {
|
|
2449
|
+
if (isIgnorable(after, 1)) {
|
|
2441
2450
|
moveNode = node;
|
|
2442
2451
|
moveOffset = ++offset;
|
|
2443
2452
|
}
|
|
@@ -2449,7 +2458,7 @@ function skipIgnoredNodesAfter(view) {
|
|
|
2449
2458
|
}
|
|
2450
2459
|
else {
|
|
2451
2460
|
let next = node.nextSibling;
|
|
2452
|
-
while (next && isIgnorable(next)) {
|
|
2461
|
+
while (next && isIgnorable(next, 1)) {
|
|
2453
2462
|
moveNode = next.parentNode;
|
|
2454
2463
|
moveOffset = domIndex(next) + 1;
|
|
2455
2464
|
next = next.nextSibling;
|
|
@@ -2480,9 +2489,12 @@ function textNodeAfter(node, offset) {
|
|
|
2480
2489
|
node = node.parentNode;
|
|
2481
2490
|
}
|
|
2482
2491
|
while (node && offset < node.childNodes.length) {
|
|
2483
|
-
|
|
2484
|
-
if (
|
|
2485
|
-
return
|
|
2492
|
+
let next = node.childNodes[offset];
|
|
2493
|
+
if (next.nodeType == 3)
|
|
2494
|
+
return next;
|
|
2495
|
+
if (next.nodeType == 1 && next.contentEditable == "false")
|
|
2496
|
+
break;
|
|
2497
|
+
node = next;
|
|
2486
2498
|
offset = 0;
|
|
2487
2499
|
}
|
|
2488
2500
|
}
|
|
@@ -2492,9 +2504,12 @@ function textNodeBefore(node, offset) {
|
|
|
2492
2504
|
node = node.parentNode;
|
|
2493
2505
|
}
|
|
2494
2506
|
while (node && offset) {
|
|
2495
|
-
|
|
2496
|
-
if (
|
|
2497
|
-
return
|
|
2507
|
+
let next = node.childNodes[offset - 1];
|
|
2508
|
+
if (next.nodeType == 3)
|
|
2509
|
+
return next;
|
|
2510
|
+
if (next.nodeType == 1 && next.contentEditable == "false")
|
|
2511
|
+
break;
|
|
2512
|
+
node = next;
|
|
2498
2513
|
offset = node.childNodes.length;
|
|
2499
2514
|
}
|
|
2500
2515
|
}
|
|
@@ -2656,7 +2671,7 @@ function captureKeyDown(view, event) {
|
|
|
2656
2671
|
return selectVertically(view, -1, mods) || skipIgnoredNodes(view, -1);
|
|
2657
2672
|
}
|
|
2658
2673
|
else if (code == 40 || (mac && code == 78 && mods == "c")) { // Down arrow, Ctrl-n on Mac
|
|
2659
|
-
return safariDownArrowBug(view) || selectVertically(view, 1, mods) ||
|
|
2674
|
+
return safariDownArrowBug(view) || selectVertically(view, 1, mods) || skipIgnoredNodes(view, 1);
|
|
2660
2675
|
}
|
|
2661
2676
|
else if (mods == (mac ? "m" : "c") &&
|
|
2662
2677
|
(code == 66 || code == 73 || code == 89 || code == 90)) { // Mod-[biyz]
|
|
@@ -3814,6 +3829,10 @@ class Decoration {
|
|
|
3814
3829
|
@internal
|
|
3815
3830
|
*/
|
|
3816
3831
|
get inline() { return this.type instanceof InlineType; }
|
|
3832
|
+
/**
|
|
3833
|
+
@internal
|
|
3834
|
+
*/
|
|
3835
|
+
get widget() { return this.type instanceof WidgetType; }
|
|
3817
3836
|
}
|
|
3818
3837
|
const none = [], noSpec = {};
|
|
3819
3838
|
/**
|
|
@@ -3832,7 +3851,8 @@ class DecorationSet {
|
|
|
3832
3851
|
}
|
|
3833
3852
|
/**
|
|
3834
3853
|
Create a set of decorations, using the structure of the given
|
|
3835
|
-
document.
|
|
3854
|
+
document. This will consume (modify) the `decorations` array, so
|
|
3855
|
+
you must make a copy if you want need to preserve that.
|
|
3836
3856
|
*/
|
|
3837
3857
|
static create(doc, decorations) {
|
|
3838
3858
|
return decorations.length ? buildTree(decorations, doc, 0, noSpec) : empty;
|
|
@@ -3891,8 +3911,9 @@ class DecorationSet {
|
|
|
3891
3911
|
}
|
|
3892
3912
|
/**
|
|
3893
3913
|
Add the given array of decorations to the ones in the set,
|
|
3894
|
-
producing a new set.
|
|
3895
|
-
create the appropriate tree
|
|
3914
|
+
producing a new set. Consumes the `decorations` array. Needs
|
|
3915
|
+
access to the current document to create the appropriate tree
|
|
3916
|
+
structure.
|
|
3896
3917
|
*/
|
|
3897
3918
|
add(doc, decorations) {
|
|
3898
3919
|
if (!decorations.length)
|
package/package.json
CHANGED
package/src/capturekeys.ts
CHANGED
|
@@ -54,10 +54,10 @@ function nodeLen(node: Node) {
|
|
|
54
54
|
return node.nodeType == 3 ? node.nodeValue!.length : node.childNodes.length
|
|
55
55
|
}
|
|
56
56
|
|
|
57
|
-
function isIgnorable(dom: Node) {
|
|
57
|
+
function isIgnorable(dom: Node, dir: number) {
|
|
58
58
|
if ((dom as HTMLElement).contentEditable == "false") return true
|
|
59
59
|
let desc = dom.pmViewDesc
|
|
60
|
-
return desc && desc.size == 0 && (dom.nextSibling || dom.nodeName != "BR")
|
|
60
|
+
return desc && desc.size == 0 && (dir < 0 || dom.nextSibling || dom.nodeName != "BR")
|
|
61
61
|
}
|
|
62
62
|
|
|
63
63
|
function skipIgnoredNodes(view: EditorView, dir: number) {
|
|
@@ -74,14 +74,14 @@ function skipIgnoredNodesBefore(view: EditorView) {
|
|
|
74
74
|
// Gecko will do odd things when the selection is directly in front
|
|
75
75
|
// of a non-editable node, so in that case, move it into the next
|
|
76
76
|
// node if possible. Issue prosemirror/prosemirror#832.
|
|
77
|
-
if (browser.gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset])) force = true
|
|
77
|
+
if (browser.gecko && node.nodeType == 1 && offset < nodeLen(node) && isIgnorable(node.childNodes[offset], -1)) force = true
|
|
78
78
|
for (;;) {
|
|
79
79
|
if (offset > 0) {
|
|
80
80
|
if (node.nodeType != 1) {
|
|
81
81
|
break
|
|
82
82
|
} else {
|
|
83
83
|
let before = node.childNodes[offset - 1]
|
|
84
|
-
if (isIgnorable(before)) {
|
|
84
|
+
if (isIgnorable(before, -1)) {
|
|
85
85
|
moveNode = node
|
|
86
86
|
moveOffset = --offset
|
|
87
87
|
} else if (before.nodeType == 3) {
|
|
@@ -93,7 +93,7 @@ function skipIgnoredNodesBefore(view: EditorView) {
|
|
|
93
93
|
break
|
|
94
94
|
} else {
|
|
95
95
|
let prev = node.previousSibling
|
|
96
|
-
while (prev && isIgnorable(prev)) {
|
|
96
|
+
while (prev && isIgnorable(prev, -1)) {
|
|
97
97
|
moveNode = node.parentNode
|
|
98
98
|
moveOffset = domIndex(prev)
|
|
99
99
|
prev = prev.previousSibling
|
|
@@ -124,7 +124,7 @@ function skipIgnoredNodesAfter(view: EditorView) {
|
|
|
124
124
|
if (offset < len) {
|
|
125
125
|
if (node.nodeType != 1) break
|
|
126
126
|
let after = node.childNodes[offset]
|
|
127
|
-
if (isIgnorable(after)) {
|
|
127
|
+
if (isIgnorable(after, 1)) {
|
|
128
128
|
moveNode = node
|
|
129
129
|
moveOffset = ++offset
|
|
130
130
|
}
|
|
@@ -133,7 +133,7 @@ function skipIgnoredNodesAfter(view: EditorView) {
|
|
|
133
133
|
break
|
|
134
134
|
} else {
|
|
135
135
|
let next = node.nextSibling
|
|
136
|
-
while (next && isIgnorable(next)) {
|
|
136
|
+
while (next && isIgnorable(next, 1)) {
|
|
137
137
|
moveNode = next.parentNode
|
|
138
138
|
moveOffset = domIndex(next) + 1
|
|
139
139
|
next = next.nextSibling
|
|
@@ -163,8 +163,10 @@ function textNodeAfter(node: Node | null, offset: number): Text | undefined {
|
|
|
163
163
|
node = node.parentNode
|
|
164
164
|
}
|
|
165
165
|
while (node && offset < node.childNodes.length) {
|
|
166
|
-
|
|
167
|
-
if (
|
|
166
|
+
let next = node.childNodes[offset]
|
|
167
|
+
if (next.nodeType == 3) return next as Text
|
|
168
|
+
if (next.nodeType == 1 && (next as HTMLElement).contentEditable == "false") break
|
|
169
|
+
node = next
|
|
168
170
|
offset = 0
|
|
169
171
|
}
|
|
170
172
|
}
|
|
@@ -175,8 +177,10 @@ function textNodeBefore(node: Node | null, offset: number): Text | undefined {
|
|
|
175
177
|
node = node.parentNode
|
|
176
178
|
}
|
|
177
179
|
while (node && offset) {
|
|
178
|
-
|
|
179
|
-
if (
|
|
180
|
+
let next = node.childNodes[offset - 1]
|
|
181
|
+
if (next.nodeType == 3) return next as Text
|
|
182
|
+
if (next.nodeType == 1 && (next as HTMLElement).contentEditable == "false") break
|
|
183
|
+
node = next
|
|
180
184
|
offset = node.childNodes.length
|
|
181
185
|
}
|
|
182
186
|
}
|
|
@@ -327,7 +331,7 @@ export function captureKeyDown(view: EditorView, event: KeyboardEvent) {
|
|
|
327
331
|
} else if (code == 38 || (browser.mac && code == 80 && mods == "c")) { // Up arrow, Ctrl-p on Mac
|
|
328
332
|
return selectVertically(view, -1, mods) || skipIgnoredNodes(view, -1)
|
|
329
333
|
} else if (code == 40 || (browser.mac && code == 78 && mods == "c")) { // Down arrow, Ctrl-n on Mac
|
|
330
|
-
return safariDownArrowBug(view) || selectVertically(view, 1, mods) ||
|
|
334
|
+
return safariDownArrowBug(view) || selectVertically(view, 1, mods) || skipIgnoredNodes(view, 1)
|
|
331
335
|
} else if (mods == (browser.mac ? "m" : "c") &&
|
|
332
336
|
(code == 66 || code == 73 || code == 89 || code == 90)) { // Mod-[biyz]
|
|
333
337
|
return true
|
package/src/decoration.ts
CHANGED
|
@@ -223,6 +223,9 @@ export class Decoration {
|
|
|
223
223
|
|
|
224
224
|
/// @internal
|
|
225
225
|
get inline() { return this.type instanceof InlineType }
|
|
226
|
+
|
|
227
|
+
/// @internal
|
|
228
|
+
get widget() { return this.type instanceof WidgetType }
|
|
226
229
|
}
|
|
227
230
|
|
|
228
231
|
/// A set of attributes to add to a decorated node. Most properties
|
|
@@ -278,7 +281,8 @@ export class DecorationSet implements DecorationSource {
|
|
|
278
281
|
}
|
|
279
282
|
|
|
280
283
|
/// Create a set of decorations, using the structure of the given
|
|
281
|
-
/// document.
|
|
284
|
+
/// document. This will consume (modify) the `decorations` array, so
|
|
285
|
+
/// you must make a copy if you want need to preserve that.
|
|
282
286
|
static create(doc: Node, decorations: Decoration[]) {
|
|
283
287
|
return decorations.length ? buildTree(decorations, doc, 0, noSpec) : empty
|
|
284
288
|
}
|
|
@@ -302,7 +306,7 @@ export class DecorationSet implements DecorationSource {
|
|
|
302
306
|
result.push(span.copy(span.from + offset, span.to + offset))
|
|
303
307
|
}
|
|
304
308
|
for (let i = 0; i < this.children.length; i += 3) {
|
|
305
|
-
if (this.children[i] < end && this.children[i + 1] > start) {
|
|
309
|
+
if ((this.children[i] as number) < end && (this.children[i + 1] as number) > start) {
|
|
306
310
|
let childOff = (this.children[i] as number) + 1
|
|
307
311
|
;(this.children[i + 2] as DecorationSet).findInner(start - childOff, end - childOff,
|
|
308
312
|
result, offset + childOff, predicate)
|
|
@@ -340,8 +344,9 @@ export class DecorationSet implements DecorationSource {
|
|
|
340
344
|
}
|
|
341
345
|
|
|
342
346
|
/// Add the given array of decorations to the ones in the set,
|
|
343
|
-
/// producing a new set.
|
|
344
|
-
/// create the appropriate tree
|
|
347
|
+
/// producing a new set. Consumes the `decorations` array. Needs
|
|
348
|
+
/// access to the current document to create the appropriate tree
|
|
349
|
+
/// structure.
|
|
345
350
|
add(doc: Node, decorations: Decoration[]) {
|
|
346
351
|
if (!decorations.length) return this
|
|
347
352
|
if (this == empty) return DecorationSet.create(doc, decorations)
|
|
@@ -355,7 +360,7 @@ export class DecorationSet implements DecorationSource {
|
|
|
355
360
|
if (!(found = takeSpansForNode(decorations, childNode, baseOffset))) return
|
|
356
361
|
|
|
357
362
|
if (!children) children = this.children.slice()
|
|
358
|
-
while (childIndex < children.length && children[childIndex] < childOffset) childIndex += 3
|
|
363
|
+
while (childIndex < children.length && (children[childIndex] as number) < childOffset) childIndex += 3
|
|
359
364
|
if (children[childIndex] == childOffset)
|
|
360
365
|
children[childIndex + 2] = (children[childIndex + 2] as DecorationSet).addInner(childNode, found, baseOffset + 1)
|
|
361
366
|
else
|
|
@@ -414,7 +419,7 @@ export class DecorationSet implements DecorationSource {
|
|
|
414
419
|
if (node.isLeaf) return DecorationSet.empty
|
|
415
420
|
|
|
416
421
|
let child, local: Decoration[] | undefined
|
|
417
|
-
for (let i = 0; i < this.children.length; i += 3) if (this.children[i] >= offset) {
|
|
422
|
+
for (let i = 0; i < this.children.length; i += 3) if ((this.children[i] as number) >= offset) {
|
|
418
423
|
if (this.children[i] == offset) child = this.children[i + 2] as DecorationSet
|
|
419
424
|
break
|
|
420
425
|
}
|
|
@@ -576,7 +581,7 @@ function mapChildren(
|
|
|
576
581
|
// Find the child nodes that still correspond to a single node,
|
|
577
582
|
// recursively call mapInner on them and update their positions.
|
|
578
583
|
let mustRebuild = false
|
|
579
|
-
for (let i = 0; i < children.length; i += 3) if (children[i + 1] < 0) { // Touched nodes
|
|
584
|
+
for (let i = 0; i < children.length; i += 3) if ((children[i + 1] as number) < 0) { // Touched nodes
|
|
580
585
|
if (children[i + 1] == -2) {
|
|
581
586
|
mustRebuild = true
|
|
582
587
|
children[i + 1] = -1
|
|
@@ -613,7 +618,7 @@ function mapChildren(
|
|
|
613
618
|
offset, oldOffset, options)
|
|
614
619
|
let built = buildTree(decorations, node, 0, options)
|
|
615
620
|
newLocal = built.local as Decoration[]
|
|
616
|
-
for (let i = 0; i < children.length; i += 3) if (children[i + 1] < 0) {
|
|
621
|
+
for (let i = 0; i < children.length; i += 3) if ((children[i + 1] as number) < 0) {
|
|
617
622
|
children.splice(i, 3)
|
|
618
623
|
i -= 3
|
|
619
624
|
}
|
package/src/viewdesc.ts
CHANGED
|
@@ -387,7 +387,7 @@ export class ViewDesc {
|
|
|
387
387
|
brKludge = !!(offset && node.nodeValue![offset - 1] == "\n")
|
|
388
388
|
// Issue #1128
|
|
389
389
|
if (brKludge && offset == node.nodeValue!.length) {
|
|
390
|
-
|
|
390
|
+
for (let scan: DOMNode | null = node, after; scan; scan = scan.parentNode) {
|
|
391
391
|
if (after = scan.nextSibling) {
|
|
392
392
|
if (after.nodeName == "BR")
|
|
393
393
|
anchorDOM = headDOM = {node: after.parentNode!, offset: domIndex(after) + 1}
|
|
@@ -1244,9 +1244,11 @@ class ViewTreeUpdater {
|
|
|
1244
1244
|
return true
|
|
1245
1245
|
} else if (!locked && (updated = this.recreateWrapper(next, node, outerDeco, innerDeco, view, pos))) {
|
|
1246
1246
|
this.top.children[this.index] = updated
|
|
1247
|
-
updated.
|
|
1248
|
-
|
|
1249
|
-
|
|
1247
|
+
if (updated.contentDOM) {
|
|
1248
|
+
updated.dirty = CONTENT_DIRTY
|
|
1249
|
+
updated.updateChildren(view, pos + 1)
|
|
1250
|
+
updated.dirty = NOT_DIRTY
|
|
1251
|
+
}
|
|
1250
1252
|
this.changed = true
|
|
1251
1253
|
this.index++
|
|
1252
1254
|
return true
|
|
@@ -1264,12 +1266,12 @@ class ViewTreeUpdater {
|
|
|
1264
1266
|
if (next.dirty || node.isAtom || !next.children.length ||
|
|
1265
1267
|
!next.node.content.eq(node.content)) return null
|
|
1266
1268
|
let wrapper = NodeViewDesc.create(this.top, node, outerDeco, innerDeco, view, pos)
|
|
1267
|
-
if (
|
|
1268
|
-
|
|
1269
|
-
|
|
1269
|
+
if (wrapper.contentDOM) {
|
|
1270
|
+
wrapper.children = next.children
|
|
1271
|
+
next.children = []
|
|
1272
|
+
for (let ch of wrapper.children) ch.parent = wrapper
|
|
1273
|
+
}
|
|
1270
1274
|
next.destroy()
|
|
1271
|
-
for (let ch of wrapper.children) ch.parent = wrapper
|
|
1272
|
-
|
|
1273
1275
|
return wrapper
|
|
1274
1276
|
}
|
|
1275
1277
|
|
|
@@ -1403,10 +1405,15 @@ function iterDeco(
|
|
|
1403
1405
|
|
|
1404
1406
|
let decoIndex = 0, active = [], restNode = null
|
|
1405
1407
|
for (let parentIndex = 0;;) {
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1408
|
+
let widget, widgets
|
|
1409
|
+
while (decoIndex < locals.length && locals[decoIndex].to == offset) {
|
|
1410
|
+
let next = locals[decoIndex++]
|
|
1411
|
+
if (next.widget) {
|
|
1412
|
+
if (!widget) widget = next
|
|
1413
|
+
else (widgets || (widgets = [widget])).push(next)
|
|
1414
|
+
}
|
|
1415
|
+
}
|
|
1416
|
+
if (widget) {
|
|
1410
1417
|
if (widgets) {
|
|
1411
1418
|
widgets.sort(compareSide)
|
|
1412
1419
|
for (let i = 0; i < widgets.length; i++) onWidget(widgets[i], parentIndex, !!restNode)
|