@portabletext/editor 1.15.1 → 1.15.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/lib/_chunks-cjs/behavior.core.cjs +496 -0
- package/lib/_chunks-cjs/behavior.core.cjs.map +1 -0
- package/lib/_chunks-cjs/selector.get-text-before.cjs +0 -231
- package/lib/_chunks-cjs/selector.get-text-before.cjs.map +1 -1
- package/lib/_chunks-cjs/selectors.cjs +234 -0
- package/lib/_chunks-cjs/selectors.cjs.map +1 -0
- package/lib/_chunks-es/behavior.core.js +498 -0
- package/lib/_chunks-es/behavior.core.js.map +1 -0
- package/lib/_chunks-es/selector.get-text-before.js +2 -233
- package/lib/_chunks-es/selector.get-text-before.js.map +1 -1
- package/lib/_chunks-es/selectors.js +235 -0
- package/lib/_chunks-es/selectors.js.map +1 -0
- package/lib/behaviors/index.cjs +460 -0
- package/lib/behaviors/index.cjs.map +1 -0
- package/lib/behaviors/index.d.cts +869 -0
- package/lib/behaviors/index.d.ts +869 -0
- package/lib/behaviors/index.js +464 -0
- package/lib/behaviors/index.js.map +1 -0
- package/lib/index.cjs +51 -1035
- package/lib/index.cjs.map +1 -1
- package/lib/index.d.cts +146 -669
- package/lib/index.d.ts +146 -669
- package/lib/index.js +44 -1027
- package/lib/index.js.map +1 -1
- package/lib/selectors/index.cjs +16 -16
- package/lib/selectors/index.cjs.map +1 -1
- package/lib/selectors/index.d.cts +8 -12
- package/lib/selectors/index.d.ts +8 -12
- package/lib/selectors/index.js +3 -2
- package/lib/selectors/index.js.map +1 -1
- package/package.json +11 -5
- package/src/{editor/behavior → behavior-actions}/behavior.action-utils.insert-block.ts +4 -6
- package/src/{editor/behavior → behavior-actions}/behavior.action.insert-block-object.ts +1 -1
- package/src/{editor/behavior → behavior-actions}/behavior.action.insert-break.ts +1 -1
- package/src/{editor/behavior → behavior-actions}/behavior.action.insert-inline-object.ts +1 -1
- package/src/{editor/behavior → behavior-actions}/behavior.action.list-item.ts +2 -2
- package/src/{editor/behavior → behavior-actions}/behavior.action.text-block.set.ts +1 -1
- package/src/{editor/behavior → behavior-actions}/behavior.action.text-block.unset.ts +1 -1
- package/src/{editor/behavior → behavior-actions}/behavior.actions.ts +20 -20
- package/src/{editor/behavior → behavior-actions}/behavior.guards.ts +2 -6
- package/src/{editor/behavior → behaviors}/behavior.code-editor.ts +4 -4
- package/src/{editor/behavior → behaviors}/behavior.core.block-objects.ts +6 -6
- package/src/{editor/behavior → behaviors}/behavior.core.decorators.ts +6 -16
- package/src/{editor/behavior → behaviors}/behavior.core.lists.ts +17 -17
- package/src/{editor/behavior → behaviors}/behavior.links.ts +5 -5
- package/src/{editor/behavior → behaviors}/behavior.markdown.ts +25 -43
- package/src/{editor/behavior → behaviors}/behavior.types.ts +39 -46
- package/src/behaviors/index.ts +29 -0
- package/src/editor/PortableTextEditor.tsx +2 -2
- package/src/{utils/getPortableTextMemberSchemaTypes.ts → editor/create-editor-schema.ts} +3 -3
- package/src/editor/create-editor.ts +28 -48
- package/src/editor/define-schema.ts +8 -3
- package/src/editor/editor-machine.ts +21 -36
- package/src/editor/editor-selector.ts +1 -13
- package/src/editor/editor-snapshot.ts +4 -6
- package/src/editor/plugins/createWithEditableAPI.ts +3 -3
- package/src/editor/plugins/createWithPortableTextMarkModel.ts +1 -1
- package/src/editor/utils/utils.block-offset.ts +1 -1
- package/src/index.ts +14 -31
- package/src/selectors/index.ts +2 -4
- package/src/selectors/selector.get-active-list-item.ts +1 -1
- package/src/selectors/selectors.ts +1 -1
- package/src/type-utils.ts +17 -0
- package/src/utils/__tests__/operationToPatches.test.ts +3 -3
- package/src/utils/__tests__/patchToOperations.test.ts +3 -3
- package/src/utils/__tests__/values.test.ts +2 -2
- /package/src/{editor/behavior → behavior-actions}/behavior.action.insert-span.ts +0 -0
- /package/src/{editor/behavior → behavior-actions}/behavior.action.style.ts +0 -0
- /package/src/{editor/behavior → behaviors}/behavior.core.ts +0 -0
|
@@ -0,0 +1,496 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var types = require("@sanity/types"), selectors = require("./selectors.cjs");
|
|
3
|
+
function blockOffsetToSpanSelectionPoint({
|
|
4
|
+
value,
|
|
5
|
+
blockOffset
|
|
6
|
+
}) {
|
|
7
|
+
let offsetLeft = blockOffset.offset, selectionPoint;
|
|
8
|
+
for (const block of value)
|
|
9
|
+
if (block._key === blockOffset.path[0]._key && types.isPortableTextTextBlock(block)) {
|
|
10
|
+
for (const child of block.children)
|
|
11
|
+
if (types.isPortableTextSpan(child)) {
|
|
12
|
+
if (offsetLeft === 0) {
|
|
13
|
+
selectionPoint = {
|
|
14
|
+
path: [...blockOffset.path, "children", {
|
|
15
|
+
_key: child._key
|
|
16
|
+
}],
|
|
17
|
+
offset: 0
|
|
18
|
+
};
|
|
19
|
+
break;
|
|
20
|
+
}
|
|
21
|
+
if (offsetLeft <= child.text.length) {
|
|
22
|
+
selectionPoint = {
|
|
23
|
+
path: [...blockOffset.path, "children", {
|
|
24
|
+
_key: child._key
|
|
25
|
+
}],
|
|
26
|
+
offset: offsetLeft
|
|
27
|
+
};
|
|
28
|
+
break;
|
|
29
|
+
}
|
|
30
|
+
offsetLeft -= child.text.length;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
return selectionPoint;
|
|
34
|
+
}
|
|
35
|
+
function spanSelectionPointToBlockOffset({
|
|
36
|
+
value,
|
|
37
|
+
selectionPoint
|
|
38
|
+
}) {
|
|
39
|
+
let offset = 0;
|
|
40
|
+
for (const block of value)
|
|
41
|
+
if (block._key === selectionPoint.path[0]._key && types.isPortableTextTextBlock(block)) {
|
|
42
|
+
for (const child of block.children)
|
|
43
|
+
if (types.isPortableTextSpan(child)) {
|
|
44
|
+
if (child._key === selectionPoint.path[2]._key)
|
|
45
|
+
return {
|
|
46
|
+
path: [{
|
|
47
|
+
_key: block._key
|
|
48
|
+
}],
|
|
49
|
+
offset: offset + selectionPoint.offset
|
|
50
|
+
};
|
|
51
|
+
offset += child.text.length;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
function isEmptyTextBlock(block) {
|
|
56
|
+
if (!types.isPortableTextTextBlock(block))
|
|
57
|
+
return !1;
|
|
58
|
+
const onlyText = block.children.every(types.isPortableTextSpan), blockText = getTextBlockText(block);
|
|
59
|
+
return onlyText && blockText === "";
|
|
60
|
+
}
|
|
61
|
+
function getTextBlockText(block) {
|
|
62
|
+
return block.children.map((child) => {
|
|
63
|
+
var _a;
|
|
64
|
+
return (_a = child.text) != null ? _a : "";
|
|
65
|
+
}).join("");
|
|
66
|
+
}
|
|
67
|
+
const IS_MAC = typeof window < "u" && /Mac|iPod|iPhone|iPad/.test(window.navigator.userAgent), modifiers = {
|
|
68
|
+
alt: "altKey",
|
|
69
|
+
control: "ctrlKey",
|
|
70
|
+
meta: "metaKey",
|
|
71
|
+
shift: "shiftKey"
|
|
72
|
+
}, aliases = {
|
|
73
|
+
add: "+",
|
|
74
|
+
break: "pause",
|
|
75
|
+
cmd: "meta",
|
|
76
|
+
command: "meta",
|
|
77
|
+
ctl: "control",
|
|
78
|
+
ctrl: "control",
|
|
79
|
+
del: "delete",
|
|
80
|
+
down: "arrowdown",
|
|
81
|
+
esc: "escape",
|
|
82
|
+
ins: "insert",
|
|
83
|
+
left: "arrowleft",
|
|
84
|
+
mod: IS_MAC ? "meta" : "control",
|
|
85
|
+
opt: "alt",
|
|
86
|
+
option: "alt",
|
|
87
|
+
return: "enter",
|
|
88
|
+
right: "arrowright",
|
|
89
|
+
space: " ",
|
|
90
|
+
spacebar: " ",
|
|
91
|
+
up: "arrowup",
|
|
92
|
+
win: "meta",
|
|
93
|
+
windows: "meta"
|
|
94
|
+
}, keyCodes = {
|
|
95
|
+
backspace: 8,
|
|
96
|
+
tab: 9,
|
|
97
|
+
enter: 13,
|
|
98
|
+
shift: 16,
|
|
99
|
+
control: 17,
|
|
100
|
+
alt: 18,
|
|
101
|
+
pause: 19,
|
|
102
|
+
capslock: 20,
|
|
103
|
+
escape: 27,
|
|
104
|
+
" ": 32,
|
|
105
|
+
pageup: 33,
|
|
106
|
+
pagedown: 34,
|
|
107
|
+
end: 35,
|
|
108
|
+
home: 36,
|
|
109
|
+
arrowleft: 37,
|
|
110
|
+
arrowup: 38,
|
|
111
|
+
arrowright: 39,
|
|
112
|
+
arrowdown: 40,
|
|
113
|
+
insert: 45,
|
|
114
|
+
delete: 46,
|
|
115
|
+
meta: 91,
|
|
116
|
+
numlock: 144,
|
|
117
|
+
scrolllock: 145,
|
|
118
|
+
";": 186,
|
|
119
|
+
"=": 187,
|
|
120
|
+
",": 188,
|
|
121
|
+
"-": 189,
|
|
122
|
+
".": 190,
|
|
123
|
+
"/": 191,
|
|
124
|
+
"`": 192,
|
|
125
|
+
"[": 219,
|
|
126
|
+
"\\": 220,
|
|
127
|
+
"]": 221,
|
|
128
|
+
"'": 222,
|
|
129
|
+
f1: 112,
|
|
130
|
+
f2: 113,
|
|
131
|
+
f3: 114,
|
|
132
|
+
f4: 115,
|
|
133
|
+
f5: 116,
|
|
134
|
+
f6: 117,
|
|
135
|
+
f7: 118,
|
|
136
|
+
f8: 119,
|
|
137
|
+
f9: 120,
|
|
138
|
+
f10: 121,
|
|
139
|
+
f11: 122,
|
|
140
|
+
f12: 123,
|
|
141
|
+
f13: 124,
|
|
142
|
+
f14: 125,
|
|
143
|
+
f15: 126,
|
|
144
|
+
f16: 127,
|
|
145
|
+
f17: 128,
|
|
146
|
+
f18: 129,
|
|
147
|
+
f19: 130,
|
|
148
|
+
f20: 131
|
|
149
|
+
};
|
|
150
|
+
function isHotkey(hotkey, event) {
|
|
151
|
+
return compareHotkey(parseHotkey(hotkey), event);
|
|
152
|
+
}
|
|
153
|
+
function parseHotkey(hotkey) {
|
|
154
|
+
const parsedHotkey = {
|
|
155
|
+
altKey: !1,
|
|
156
|
+
ctrlKey: !1,
|
|
157
|
+
metaKey: !1,
|
|
158
|
+
shiftKey: !1
|
|
159
|
+
}, hotkeySegments = hotkey.replace("++", "+add").split("+");
|
|
160
|
+
for (const rawHotkeySegment of hotkeySegments) {
|
|
161
|
+
const optional = rawHotkeySegment.endsWith("?") && rawHotkeySegment.length > 1, hotkeySegment = optional ? rawHotkeySegment.slice(0, -1) : rawHotkeySegment, keyName = toKeyName(hotkeySegment), modifier = modifiers[keyName], alias = aliases[hotkeySegment], code = keyCodes[keyName];
|
|
162
|
+
if (hotkeySegment.length > 1 && modifier === void 0 && alias === void 0 && code === void 0)
|
|
163
|
+
throw new TypeError(`Unknown modifier: "${hotkeySegment}"`);
|
|
164
|
+
(hotkeySegments.length === 1 || modifier === void 0) && (parsedHotkey.key = keyName, parsedHotkey.keyCode = toKeyCode(hotkeySegment)), modifier !== void 0 && (parsedHotkey[modifier] = optional ? null : !0);
|
|
165
|
+
}
|
|
166
|
+
return parsedHotkey;
|
|
167
|
+
}
|
|
168
|
+
function compareHotkey(parsedHotkey, event) {
|
|
169
|
+
return (parsedHotkey.altKey == null || parsedHotkey.altKey === event.altKey) && (parsedHotkey.ctrlKey == null || parsedHotkey.ctrlKey === event.ctrlKey) && (parsedHotkey.metaKey == null || parsedHotkey.metaKey === event.metaKey) && (parsedHotkey.shiftKey == null || parsedHotkey.shiftKey === event.shiftKey) ? parsedHotkey.keyCode !== void 0 && event.keyCode !== void 0 ? parsedHotkey.keyCode === 91 && event.keyCode === 93 ? !0 : parsedHotkey.keyCode === event.keyCode : parsedHotkey.keyCode === event.keyCode || parsedHotkey.key === event.key.toLowerCase() : !1;
|
|
170
|
+
}
|
|
171
|
+
function toKeyCode(name) {
|
|
172
|
+
var _a;
|
|
173
|
+
const keyName = toKeyName(name);
|
|
174
|
+
return (_a = keyCodes[keyName]) != null ? _a : keyName.toUpperCase().charCodeAt(0);
|
|
175
|
+
}
|
|
176
|
+
function toKeyName(name) {
|
|
177
|
+
var _a;
|
|
178
|
+
const keyName = name.toLowerCase();
|
|
179
|
+
return (_a = aliases[keyName]) != null ? _a : keyName;
|
|
180
|
+
}
|
|
181
|
+
function defineBehavior(behavior) {
|
|
182
|
+
return behavior;
|
|
183
|
+
}
|
|
184
|
+
const arrowDownOnLonelyBlockObject = {
|
|
185
|
+
on: "key.down",
|
|
186
|
+
guard: ({
|
|
187
|
+
context,
|
|
188
|
+
event
|
|
189
|
+
}) => {
|
|
190
|
+
const isArrowDown = isHotkey("ArrowDown", event.keyboardEvent), focusBlockObject = selectors.getFocusBlockObject({
|
|
191
|
+
context
|
|
192
|
+
}), nextBlock = selectors.getNextBlock({
|
|
193
|
+
context
|
|
194
|
+
});
|
|
195
|
+
return isArrowDown && focusBlockObject && !nextBlock;
|
|
196
|
+
},
|
|
197
|
+
actions: [() => [{
|
|
198
|
+
type: "insert.text block",
|
|
199
|
+
placement: "after"
|
|
200
|
+
}]]
|
|
201
|
+
}, arrowUpOnLonelyBlockObject = {
|
|
202
|
+
on: "key.down",
|
|
203
|
+
guard: ({
|
|
204
|
+
context,
|
|
205
|
+
event
|
|
206
|
+
}) => {
|
|
207
|
+
const isArrowUp = isHotkey("ArrowUp", event.keyboardEvent), focusBlockObject = selectors.getFocusBlockObject({
|
|
208
|
+
context
|
|
209
|
+
}), previousBlock = selectors.getPreviousBlock({
|
|
210
|
+
context
|
|
211
|
+
});
|
|
212
|
+
return isArrowUp && focusBlockObject && !previousBlock;
|
|
213
|
+
},
|
|
214
|
+
actions: [() => [{
|
|
215
|
+
type: "insert.text block",
|
|
216
|
+
placement: "before"
|
|
217
|
+
}, {
|
|
218
|
+
type: "select.previous block"
|
|
219
|
+
}]]
|
|
220
|
+
}, breakingBlockObject = {
|
|
221
|
+
on: "insert.break",
|
|
222
|
+
guard: ({
|
|
223
|
+
context
|
|
224
|
+
}) => {
|
|
225
|
+
const focusBlockObject = selectors.getFocusBlockObject({
|
|
226
|
+
context
|
|
227
|
+
});
|
|
228
|
+
return selectors.selectionIsCollapsed({
|
|
229
|
+
context
|
|
230
|
+
}) && focusBlockObject !== void 0;
|
|
231
|
+
},
|
|
232
|
+
actions: [() => [{
|
|
233
|
+
type: "insert.text block",
|
|
234
|
+
placement: "after"
|
|
235
|
+
}]]
|
|
236
|
+
}, deletingEmptyTextBlockAfterBlockObject = {
|
|
237
|
+
on: "delete.backward",
|
|
238
|
+
guard: ({
|
|
239
|
+
context
|
|
240
|
+
}) => {
|
|
241
|
+
const focusTextBlock = selectors.getFocusTextBlock({
|
|
242
|
+
context
|
|
243
|
+
}), selectionCollapsed = selectors.selectionIsCollapsed({
|
|
244
|
+
context
|
|
245
|
+
}), previousBlock = selectors.getPreviousBlock({
|
|
246
|
+
context
|
|
247
|
+
});
|
|
248
|
+
return !focusTextBlock || !selectionCollapsed || !previousBlock ? !1 : isEmptyTextBlock(focusTextBlock.node) && !types.isPortableTextTextBlock(previousBlock.node) ? {
|
|
249
|
+
focusTextBlock,
|
|
250
|
+
previousBlock
|
|
251
|
+
} : !1;
|
|
252
|
+
},
|
|
253
|
+
actions: [(_, {
|
|
254
|
+
focusTextBlock,
|
|
255
|
+
previousBlock
|
|
256
|
+
}) => [{
|
|
257
|
+
type: "delete.block",
|
|
258
|
+
blockPath: focusTextBlock.path
|
|
259
|
+
}, {
|
|
260
|
+
type: "select",
|
|
261
|
+
selection: {
|
|
262
|
+
anchor: {
|
|
263
|
+
path: previousBlock.path,
|
|
264
|
+
offset: 0
|
|
265
|
+
},
|
|
266
|
+
focus: {
|
|
267
|
+
path: previousBlock.path,
|
|
268
|
+
offset: 0
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
}]]
|
|
272
|
+
}, deletingEmptyTextBlockBeforeBlockObject = {
|
|
273
|
+
on: "delete.forward",
|
|
274
|
+
guard: ({
|
|
275
|
+
context
|
|
276
|
+
}) => {
|
|
277
|
+
const focusTextBlock = selectors.getFocusTextBlock({
|
|
278
|
+
context
|
|
279
|
+
}), selectionCollapsed = selectors.selectionIsCollapsed({
|
|
280
|
+
context
|
|
281
|
+
}), nextBlock = selectors.getNextBlock({
|
|
282
|
+
context
|
|
283
|
+
});
|
|
284
|
+
return !focusTextBlock || !selectionCollapsed || !nextBlock ? !1 : isEmptyTextBlock(focusTextBlock.node) && !types.isPortableTextTextBlock(nextBlock.node) ? {
|
|
285
|
+
focusTextBlock,
|
|
286
|
+
nextBlock
|
|
287
|
+
} : !1;
|
|
288
|
+
},
|
|
289
|
+
actions: [(_, {
|
|
290
|
+
focusTextBlock,
|
|
291
|
+
nextBlock
|
|
292
|
+
}) => [{
|
|
293
|
+
type: "delete.block",
|
|
294
|
+
blockPath: focusTextBlock.path
|
|
295
|
+
}, {
|
|
296
|
+
type: "select",
|
|
297
|
+
selection: {
|
|
298
|
+
anchor: {
|
|
299
|
+
path: nextBlock.path,
|
|
300
|
+
offset: 0
|
|
301
|
+
},
|
|
302
|
+
focus: {
|
|
303
|
+
path: nextBlock.path,
|
|
304
|
+
offset: 0
|
|
305
|
+
}
|
|
306
|
+
}
|
|
307
|
+
}]]
|
|
308
|
+
}, coreBlockObjectBehaviors = {
|
|
309
|
+
arrowDownOnLonelyBlockObject,
|
|
310
|
+
arrowUpOnLonelyBlockObject,
|
|
311
|
+
breakingBlockObject,
|
|
312
|
+
deletingEmptyTextBlockAfterBlockObject,
|
|
313
|
+
deletingEmptyTextBlockBeforeBlockObject
|
|
314
|
+
}, decoratorAdd = {
|
|
315
|
+
on: "decorator.add",
|
|
316
|
+
actions: [({
|
|
317
|
+
event
|
|
318
|
+
}) => [event, {
|
|
319
|
+
type: "reselect"
|
|
320
|
+
}]]
|
|
321
|
+
}, decoratorRemove = {
|
|
322
|
+
on: "decorator.remove",
|
|
323
|
+
guard: ({
|
|
324
|
+
event
|
|
325
|
+
}) => ({
|
|
326
|
+
decorator: event.decorator
|
|
327
|
+
}),
|
|
328
|
+
actions: [({
|
|
329
|
+
event
|
|
330
|
+
}) => [event, {
|
|
331
|
+
type: "reselect"
|
|
332
|
+
}]]
|
|
333
|
+
}, decoratorToggle = {
|
|
334
|
+
on: "decorator.toggle",
|
|
335
|
+
guard: ({
|
|
336
|
+
event
|
|
337
|
+
}) => ({
|
|
338
|
+
decorator: event.decorator
|
|
339
|
+
}),
|
|
340
|
+
actions: [({
|
|
341
|
+
event
|
|
342
|
+
}) => [event, {
|
|
343
|
+
type: "reselect"
|
|
344
|
+
}]]
|
|
345
|
+
}, coreDecoratorBehaviors = {
|
|
346
|
+
decoratorAdd,
|
|
347
|
+
decoratorRemove,
|
|
348
|
+
decoratorToggle
|
|
349
|
+
}, MAX_LIST_LEVEL = 10, clearListOnBackspace = {
|
|
350
|
+
on: "delete.backward",
|
|
351
|
+
guard: ({
|
|
352
|
+
context
|
|
353
|
+
}) => {
|
|
354
|
+
var _a;
|
|
355
|
+
const selectionCollapsed = selectors.selectionIsCollapsed({
|
|
356
|
+
context
|
|
357
|
+
}), focusTextBlock = selectors.getFocusTextBlock({
|
|
358
|
+
context
|
|
359
|
+
}), focusSpan = selectors.getFocusSpan({
|
|
360
|
+
context
|
|
361
|
+
});
|
|
362
|
+
return !selectionCollapsed || !focusTextBlock || !focusSpan ? !1 : focusTextBlock.node.children[0]._key === focusSpan.node._key && ((_a = context.selection) == null ? void 0 : _a.focus.offset) === 0 && focusTextBlock.node.level === 1 ? {
|
|
363
|
+
focusTextBlock
|
|
364
|
+
} : !1;
|
|
365
|
+
},
|
|
366
|
+
actions: [(_, {
|
|
367
|
+
focusTextBlock
|
|
368
|
+
}) => [{
|
|
369
|
+
type: "text block.unset",
|
|
370
|
+
props: ["listItem", "level"],
|
|
371
|
+
at: focusTextBlock.path
|
|
372
|
+
}]]
|
|
373
|
+
}, unindentListOnBackspace = {
|
|
374
|
+
on: "delete.backward",
|
|
375
|
+
guard: ({
|
|
376
|
+
context
|
|
377
|
+
}) => {
|
|
378
|
+
var _a;
|
|
379
|
+
const selectionCollapsed = selectors.selectionIsCollapsed({
|
|
380
|
+
context
|
|
381
|
+
}), focusTextBlock = selectors.getFocusTextBlock({
|
|
382
|
+
context
|
|
383
|
+
}), focusSpan = selectors.getFocusSpan({
|
|
384
|
+
context
|
|
385
|
+
});
|
|
386
|
+
return !selectionCollapsed || !focusTextBlock || !focusSpan ? !1 : focusTextBlock.node.children[0]._key === focusSpan.node._key && ((_a = context.selection) == null ? void 0 : _a.focus.offset) === 0 && focusTextBlock.node.level !== void 0 && focusTextBlock.node.level > 1 ? {
|
|
387
|
+
focusTextBlock,
|
|
388
|
+
level: focusTextBlock.node.level - 1
|
|
389
|
+
} : !1;
|
|
390
|
+
},
|
|
391
|
+
actions: [(_, {
|
|
392
|
+
focusTextBlock,
|
|
393
|
+
level
|
|
394
|
+
}) => [{
|
|
395
|
+
type: "text block.set",
|
|
396
|
+
level,
|
|
397
|
+
at: focusTextBlock.path
|
|
398
|
+
}]]
|
|
399
|
+
}, clearListOnEnter = {
|
|
400
|
+
on: "insert.break",
|
|
401
|
+
guard: ({
|
|
402
|
+
context
|
|
403
|
+
}) => {
|
|
404
|
+
const selectionCollapsed = selectors.selectionIsCollapsed({
|
|
405
|
+
context
|
|
406
|
+
}), focusListBlock = selectors.getFocusListBlock({
|
|
407
|
+
context
|
|
408
|
+
});
|
|
409
|
+
return !selectionCollapsed || !focusListBlock || !isEmptyTextBlock(focusListBlock.node) ? !1 : {
|
|
410
|
+
focusListBlock
|
|
411
|
+
};
|
|
412
|
+
},
|
|
413
|
+
actions: [(_, {
|
|
414
|
+
focusListBlock
|
|
415
|
+
}) => [{
|
|
416
|
+
type: "text block.unset",
|
|
417
|
+
props: ["listItem", "level"],
|
|
418
|
+
at: focusListBlock.path
|
|
419
|
+
}]]
|
|
420
|
+
}, indentListOnTab = {
|
|
421
|
+
on: "key.down",
|
|
422
|
+
guard: ({
|
|
423
|
+
context,
|
|
424
|
+
event
|
|
425
|
+
}) => {
|
|
426
|
+
if (!isHotkey("Tab", event.keyboardEvent))
|
|
427
|
+
return !1;
|
|
428
|
+
const selectedBlocks = selectors.getSelectedBlocks({
|
|
429
|
+
context
|
|
430
|
+
}), guards = selectors.createGuards(context), selectedListBlocks = selectedBlocks.flatMap((block) => guards.isListBlock(block.node) ? [{
|
|
431
|
+
node: block.node,
|
|
432
|
+
path: block.path
|
|
433
|
+
}] : []);
|
|
434
|
+
return selectedListBlocks.length === selectedBlocks.length ? {
|
|
435
|
+
selectedListBlocks
|
|
436
|
+
} : !1;
|
|
437
|
+
},
|
|
438
|
+
actions: [(_, {
|
|
439
|
+
selectedListBlocks
|
|
440
|
+
}) => selectedListBlocks.map((selectedListBlock) => ({
|
|
441
|
+
type: "text block.set",
|
|
442
|
+
level: Math.min(MAX_LIST_LEVEL, Math.max(1, selectedListBlock.node.level + 1)),
|
|
443
|
+
at: selectedListBlock.path
|
|
444
|
+
}))]
|
|
445
|
+
}, unindentListOnShiftTab = {
|
|
446
|
+
on: "key.down",
|
|
447
|
+
guard: ({
|
|
448
|
+
context,
|
|
449
|
+
event
|
|
450
|
+
}) => {
|
|
451
|
+
if (!isHotkey("Shift+Tab", event.keyboardEvent))
|
|
452
|
+
return !1;
|
|
453
|
+
const selectedBlocks = selectors.getSelectedBlocks({
|
|
454
|
+
context
|
|
455
|
+
}), guards = selectors.createGuards(context), selectedListBlocks = selectedBlocks.flatMap((block) => guards.isListBlock(block.node) ? [{
|
|
456
|
+
node: block.node,
|
|
457
|
+
path: block.path
|
|
458
|
+
}] : []);
|
|
459
|
+
return selectedListBlocks.length === selectedBlocks.length ? {
|
|
460
|
+
selectedListBlocks
|
|
461
|
+
} : !1;
|
|
462
|
+
},
|
|
463
|
+
actions: [(_, {
|
|
464
|
+
selectedListBlocks
|
|
465
|
+
}) => selectedListBlocks.map((selectedListBlock) => ({
|
|
466
|
+
type: "text block.set",
|
|
467
|
+
level: Math.min(MAX_LIST_LEVEL, Math.max(1, selectedListBlock.node.level - 1)),
|
|
468
|
+
at: selectedListBlock.path
|
|
469
|
+
}))]
|
|
470
|
+
}, coreListBehaviors = {
|
|
471
|
+
clearListOnBackspace,
|
|
472
|
+
unindentListOnBackspace,
|
|
473
|
+
clearListOnEnter,
|
|
474
|
+
indentListOnTab,
|
|
475
|
+
unindentListOnShiftTab
|
|
476
|
+
}, softReturn = {
|
|
477
|
+
on: "insert.soft break",
|
|
478
|
+
actions: [() => [{
|
|
479
|
+
type: "insert.text",
|
|
480
|
+
text: `
|
|
481
|
+
`
|
|
482
|
+
}]]
|
|
483
|
+
}, coreBehaviors = [softReturn, coreDecoratorBehaviors.decoratorAdd, coreDecoratorBehaviors.decoratorRemove, coreDecoratorBehaviors.decoratorToggle, coreBlockObjectBehaviors.arrowDownOnLonelyBlockObject, coreBlockObjectBehaviors.arrowUpOnLonelyBlockObject, coreBlockObjectBehaviors.breakingBlockObject, coreBlockObjectBehaviors.deletingEmptyTextBlockAfterBlockObject, coreBlockObjectBehaviors.deletingEmptyTextBlockBeforeBlockObject, coreListBehaviors.clearListOnBackspace, coreListBehaviors.unindentListOnBackspace, coreListBehaviors.clearListOnEnter, coreListBehaviors.indentListOnTab, coreListBehaviors.unindentListOnShiftTab], coreBehavior = {
|
|
484
|
+
softReturn,
|
|
485
|
+
decorators: coreDecoratorBehaviors,
|
|
486
|
+
blockObjects: coreBlockObjectBehaviors,
|
|
487
|
+
lists: coreListBehaviors
|
|
488
|
+
};
|
|
489
|
+
exports.blockOffsetToSpanSelectionPoint = blockOffsetToSpanSelectionPoint;
|
|
490
|
+
exports.coreBehavior = coreBehavior;
|
|
491
|
+
exports.coreBehaviors = coreBehaviors;
|
|
492
|
+
exports.defineBehavior = defineBehavior;
|
|
493
|
+
exports.getTextBlockText = getTextBlockText;
|
|
494
|
+
exports.isHotkey = isHotkey;
|
|
495
|
+
exports.spanSelectionPointToBlockOffset = spanSelectionPointToBlockOffset;
|
|
496
|
+
//# sourceMappingURL=behavior.core.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"behavior.core.cjs","sources":["../../src/editor/utils/utils.block-offset.ts","../../src/editor/utils/utils.ts","../../src/utils/is-hotkey.ts","../../src/behaviors/behavior.types.ts","../../src/behaviors/behavior.core.block-objects.ts","../../src/behaviors/behavior.core.decorators.ts","../../src/behaviors/behavior.core.lists.ts","../../src/behaviors/behavior.core.ts"],"sourcesContent":["import {\n isPortableTextSpan,\n isPortableTextTextBlock,\n type KeyedSegment,\n type PortableTextBlock,\n} from '@sanity/types'\nimport type {BlockOffset} from '../../behaviors/behavior.types'\n\nexport function blockOffsetToSpanSelectionPoint({\n value,\n blockOffset,\n}: {\n value: Array<PortableTextBlock>\n blockOffset: BlockOffset\n}) {\n let offsetLeft = blockOffset.offset\n let selectionPoint:\n | {path: [KeyedSegment, 'children', KeyedSegment]; offset: number}\n | undefined\n\n for (const block of value) {\n if (block._key !== blockOffset.path[0]._key) {\n continue\n }\n\n if (!isPortableTextTextBlock(block)) {\n continue\n }\n\n for (const child of block.children) {\n if (!isPortableTextSpan(child)) {\n continue\n }\n\n if (offsetLeft === 0) {\n selectionPoint = {\n path: [...blockOffset.path, 'children', {_key: child._key}],\n offset: 0,\n }\n break\n }\n\n if (offsetLeft <= child.text.length) {\n selectionPoint = {\n path: [...blockOffset.path, 'children', {_key: child._key}],\n offset: offsetLeft,\n }\n break\n }\n\n offsetLeft -= child.text.length\n }\n }\n\n return selectionPoint\n}\n\nexport function spanSelectionPointToBlockOffset({\n value,\n selectionPoint,\n}: {\n value: Array<PortableTextBlock>\n selectionPoint: {\n path: [KeyedSegment, 'children', KeyedSegment]\n offset: number\n }\n}): BlockOffset | undefined {\n let offset = 0\n\n for (const block of value) {\n if (block._key !== selectionPoint.path[0]._key) {\n continue\n }\n\n if (!isPortableTextTextBlock(block)) {\n continue\n }\n\n for (const child of block.children) {\n if (!isPortableTextSpan(child)) {\n continue\n }\n\n if (child._key === selectionPoint.path[2]._key) {\n return {\n path: [{_key: block._key}],\n offset: offset + selectionPoint.offset,\n }\n }\n\n offset += child.text.length\n }\n }\n}\n","import {\n isPortableTextSpan,\n isPortableTextTextBlock,\n type PortableTextBlock,\n type PortableTextTextBlock,\n} from '@sanity/types'\n\nexport function isEmptyTextBlock(block: PortableTextBlock) {\n if (!isPortableTextTextBlock(block)) {\n return false\n }\n\n const onlyText = block.children.every(isPortableTextSpan)\n const blockText = getTextBlockText(block)\n\n return onlyText && blockText === ''\n}\n\nexport function getTextBlockText(block: PortableTextTextBlock) {\n return block.children.map((child) => child.text ?? '').join('')\n}\n","export interface KeyboardEventLike {\n key: string\n keyCode?: number\n altKey: boolean\n ctrlKey: boolean\n metaKey: boolean\n shiftKey: boolean\n}\n\ninterface HotKey {\n keyCode?: number | undefined\n key?: string | undefined\n altKey: boolean | null\n ctrlKey: boolean | null\n metaKey: boolean | null\n shiftKey: boolean | null\n}\n\nconst IS_MAC =\n typeof window !== 'undefined' &&\n /Mac|iPod|iPhone|iPad/.test(window.navigator.userAgent)\n\ntype Modifier = 'altKey' | 'ctrlKey' | 'metaKey' | 'shiftKey'\n\nconst modifiers: Record<string, Modifier | undefined> = {\n alt: 'altKey',\n control: 'ctrlKey',\n meta: 'metaKey',\n shift: 'shiftKey',\n}\n\nconst aliases: Record<string, string | undefined> = {\n add: '+',\n break: 'pause',\n cmd: 'meta',\n command: 'meta',\n ctl: 'control',\n ctrl: 'control',\n del: 'delete',\n down: 'arrowdown',\n esc: 'escape',\n ins: 'insert',\n left: 'arrowleft',\n mod: IS_MAC ? 'meta' : 'control',\n opt: 'alt',\n option: 'alt',\n return: 'enter',\n right: 'arrowright',\n space: ' ',\n spacebar: ' ',\n up: 'arrowup',\n win: 'meta',\n windows: 'meta',\n}\n\nconst keyCodes: Record<string, number | undefined> = {\n 'backspace': 8,\n 'tab': 9,\n 'enter': 13,\n 'shift': 16,\n 'control': 17,\n 'alt': 18,\n 'pause': 19,\n 'capslock': 20,\n 'escape': 27,\n ' ': 32,\n 'pageup': 33,\n 'pagedown': 34,\n 'end': 35,\n 'home': 36,\n 'arrowleft': 37,\n 'arrowup': 38,\n 'arrowright': 39,\n 'arrowdown': 40,\n 'insert': 45,\n 'delete': 46,\n 'meta': 91,\n 'numlock': 144,\n 'scrolllock': 145,\n ';': 186,\n '=': 187,\n ',': 188,\n '-': 189,\n '.': 190,\n '/': 191,\n '`': 192,\n '[': 219,\n '\\\\': 220,\n ']': 221,\n \"'\": 222,\n 'f1': 112,\n 'f2': 113,\n 'f3': 114,\n 'f4': 115,\n 'f5': 116,\n 'f6': 117,\n 'f7': 118,\n 'f8': 119,\n 'f9': 120,\n 'f10': 121,\n 'f11': 122,\n 'f12': 123,\n 'f13': 124,\n 'f14': 125,\n 'f15': 126,\n 'f16': 127,\n 'f17': 128,\n 'f18': 129,\n 'f19': 130,\n 'f20': 131,\n}\n\nexport function isHotkey(hotkey: string, event: KeyboardEventLike): boolean {\n return compareHotkey(parseHotkey(hotkey), event)\n}\n\nfunction parseHotkey(hotkey: string): HotKey {\n // Ensure that all the modifiers are set to false unless the hotkey has them.\n const parsedHotkey: HotKey = {\n altKey: false,\n ctrlKey: false,\n metaKey: false,\n shiftKey: false,\n }\n\n // Special case to handle the `+` key since we use it as a separator.\n const hotkeySegments = hotkey.replace('++', '+add').split('+')\n\n for (const rawHotkeySegment of hotkeySegments) {\n const optional =\n rawHotkeySegment.endsWith('?') && rawHotkeySegment.length > 1\n const hotkeySegment = optional\n ? rawHotkeySegment.slice(0, -1)\n : rawHotkeySegment\n const keyName = toKeyName(hotkeySegment)\n const modifier = modifiers[keyName]\n const alias = aliases[hotkeySegment]\n const code = keyCodes[keyName]\n\n if (\n hotkeySegment.length > 1 &&\n modifier === undefined &&\n alias === undefined &&\n code === undefined\n ) {\n throw new TypeError(`Unknown modifier: \"${hotkeySegment}\"`)\n }\n\n if (hotkeySegments.length === 1 || modifier === undefined) {\n parsedHotkey.key = keyName\n parsedHotkey.keyCode = toKeyCode(hotkeySegment)\n }\n\n if (modifier !== undefined) {\n parsedHotkey[modifier] = optional ? null : true\n }\n }\n\n return parsedHotkey\n}\n\nfunction compareHotkey(\n parsedHotkey: HotKey,\n event: KeyboardEventLike,\n): boolean {\n const matchingModifiers =\n (parsedHotkey.altKey != null\n ? parsedHotkey.altKey === event.altKey\n : true) &&\n (parsedHotkey.ctrlKey != null\n ? parsedHotkey.ctrlKey === event.ctrlKey\n : true) &&\n (parsedHotkey.metaKey != null\n ? parsedHotkey.metaKey === event.metaKey\n : true) &&\n (parsedHotkey.shiftKey != null\n ? parsedHotkey.shiftKey === event.shiftKey\n : true)\n\n if (!matchingModifiers) {\n return false\n }\n\n if (parsedHotkey.keyCode !== undefined && event.keyCode !== undefined) {\n if (parsedHotkey.keyCode === 91 && event.keyCode === 93) {\n return true\n }\n\n return parsedHotkey.keyCode === event.keyCode\n }\n\n return (\n parsedHotkey.keyCode === event.keyCode ||\n parsedHotkey.key === event.key.toLowerCase()\n )\n}\n\nfunction toKeyCode(name: string): number {\n const keyName = toKeyName(name)\n const keyCode = keyCodes[keyName] ?? keyName.toUpperCase().charCodeAt(0)\n\n return keyCode\n}\n\nfunction toKeyName(name: string): string {\n const keyName = name.toLowerCase()\n\n return aliases[keyName] ?? keyName\n}\n","import type {KeyedSegment, PortableTextTextBlock} from '@sanity/types'\nimport type {TextUnit} from 'slate'\nimport type {TextInsertTextOptions} from 'slate/dist/interfaces/transforms/text'\nimport type {EditorContext} from '../editor/editor-snapshot'\nimport type {PickFromUnion} from '../type-utils'\nimport type {EditorSelection, PortableTextSlateEditor} from '../types/editor'\n\n/**\n * @alpha\n */\nexport type SyntheticBehaviorEvent =\n | {\n type: 'annotation.add'\n annotation: {\n name: string\n value: {[prop: string]: unknown}\n }\n }\n | {\n type: 'annotation.remove'\n annotation: {\n name: string\n }\n }\n | {\n type: 'annotation.toggle'\n annotation: {\n name: string\n value: {[prop: string]: unknown}\n }\n }\n | {\n type: 'blur'\n }\n | {\n type: 'decorator.add'\n decorator: string\n }\n | {\n type: 'decorator.remove'\n decorator: string\n }\n | {\n type: 'decorator.toggle'\n decorator: string\n }\n | {\n type: 'delete.backward'\n unit: TextUnit\n }\n | {\n type: 'delete.forward'\n unit: TextUnit\n }\n | {\n type: 'focus'\n }\n | {\n type: 'insert.block object'\n placement: 'auto' | 'after' | 'before'\n blockObject: {\n name: string\n value?: {[prop: string]: unknown}\n }\n }\n | {\n type: 'insert.inline object'\n inlineObject: {\n name: string\n value?: {[prop: string]: unknown}\n }\n }\n | {\n type: 'insert.break'\n }\n | {\n type: 'insert.soft break'\n }\n | {\n type: 'insert.text'\n text: string\n options?: TextInsertTextOptions\n }\n | {\n type: 'list item.toggle'\n listItem: string\n }\n | {\n type: 'style.toggle'\n style: string\n }\n\n/**\n * @alpha\n */\nexport type NativeBehaviorEvent =\n | {\n type: 'copy'\n data: DataTransfer\n }\n | {\n type: 'key.down'\n keyboardEvent: Pick<\n KeyboardEvent,\n 'key' | 'code' | 'altKey' | 'ctrlKey' | 'metaKey' | 'shiftKey'\n >\n }\n | {\n type: 'key.up'\n keyboardEvent: Pick<\n KeyboardEvent,\n 'key' | 'code' | 'altKey' | 'ctrlKey' | 'metaKey' | 'shiftKey'\n >\n }\n | {\n type: 'paste'\n data: DataTransfer\n }\n\n/**\n * @alpha\n */\nexport type BehaviorActionIntend =\n | SyntheticBehaviorEvent\n | {\n type: 'insert.span'\n text: string\n annotations?: Array<{\n name: string\n value: {[prop: string]: unknown}\n }>\n decorators?: Array<string>\n }\n | {\n type: 'insert.text block'\n placement: 'auto' | 'after' | 'before'\n textBlock?: {\n children?: PortableTextTextBlock['children']\n }\n }\n | {\n type: 'list item.add'\n listItem: string\n }\n | {\n type: 'list item.remove'\n listItem: string\n }\n | {\n type: 'move.block'\n at: [KeyedSegment]\n to: [KeyedSegment]\n }\n | {\n type: 'move.block down'\n at: [KeyedSegment]\n }\n | {\n type: 'move.block up'\n at: [KeyedSegment]\n }\n | {\n type: 'noop'\n }\n | {\n type: 'delete.block'\n blockPath: [KeyedSegment]\n }\n | {\n type: 'delete.text'\n anchor: BlockOffset\n focus: BlockOffset\n }\n | {\n type: 'effect'\n effect: () => void\n }\n | {\n type: 'reselect'\n }\n | {\n type: 'select'\n selection: EditorSelection\n }\n | {\n type: 'select.previous block'\n }\n | {\n type: 'select.next block'\n }\n | {\n type: 'style.add'\n style: string\n }\n | {\n type: 'style.remove'\n style: string\n }\n | {\n type: 'text block.set'\n at: [KeyedSegment]\n level?: number\n listItem?: string\n style?: string\n }\n | {\n type: 'text block.unset'\n at: [KeyedSegment]\n props: Array<'level' | 'listItem' | 'style'>\n }\n\n/**\n * @alpha\n */\nexport type BehaviorAction = BehaviorActionIntend & {\n editor: PortableTextSlateEditor\n}\n\n/**\n * @alpha\n */\nexport type BehaviorEvent = SyntheticBehaviorEvent | NativeBehaviorEvent\n\n/**\n * @alpha\n */\nexport type Behavior<\n TBehaviorEventType extends BehaviorEvent['type'] = BehaviorEvent['type'],\n TGuardResponse = true,\n> = {\n /**\n * The internal editor event that triggers this behavior.\n */\n on: TBehaviorEventType\n /**\n * Predicate function that determines if the behavior should be executed.\n * Returning a non-nullable value from the guard will pass the value to the\n * actions and execute them.\n */\n guard?: BehaviorGuard<\n PickFromUnion<BehaviorEvent, 'type', TBehaviorEventType>,\n TGuardResponse\n >\n /**\n * Array of behavior action sets.\n */\n actions: Array<BehaviorActionIntendSet<TBehaviorEventType, TGuardResponse>>\n}\n\n/**\n * @alpha\n */\nexport type BehaviorGuard<\n TBehaviorEvent extends BehaviorEvent,\n TGuardResponse,\n> = ({\n context,\n event,\n}: {\n context: EditorContext\n event: TBehaviorEvent\n}) => TGuardResponse | false\n\n/**\n * @alpha\n */\nexport type BehaviorActionIntendSet<\n TBehaviorEventType extends BehaviorEvent['type'] = BehaviorEvent['type'],\n TGuardResponse = true,\n> = (\n {\n context,\n event,\n }: {\n context: EditorContext\n event: PickFromUnion<BehaviorEvent, 'type', TBehaviorEventType>\n },\n guardResponse: TGuardResponse,\n) => Array<BehaviorActionIntend>\n\n/**\n * @alpha\n */\nexport function defineBehavior<\n TAnyBehaviorEventType extends BehaviorEvent['type'],\n TGuardResponse = true,\n>(behavior: Behavior<TAnyBehaviorEventType, TGuardResponse>): Behavior {\n return behavior as unknown as Behavior\n}\n\n/**\n * @alpha\n */\nexport type BlockOffset = {\n path: [KeyedSegment]\n offset: number\n}\n","import {isPortableTextTextBlock} from '@sanity/types'\nimport {isEmptyTextBlock} from '../editor/utils/utils'\nimport {\n getFocusBlockObject,\n getFocusTextBlock,\n getNextBlock,\n getPreviousBlock,\n selectionIsCollapsed,\n} from '../selectors/selectors'\nimport {isHotkey} from '../utils/is-hotkey'\nimport {defineBehavior} from './behavior.types'\n\nconst arrowDownOnLonelyBlockObject = defineBehavior({\n on: 'key.down',\n guard: ({context, event}) => {\n const isArrowDown = isHotkey('ArrowDown', event.keyboardEvent)\n const focusBlockObject = getFocusBlockObject({context})\n const nextBlock = getNextBlock({context})\n\n return isArrowDown && focusBlockObject && !nextBlock\n },\n actions: [() => [{type: 'insert.text block', placement: 'after'}]],\n})\n\nconst arrowUpOnLonelyBlockObject = defineBehavior({\n on: 'key.down',\n guard: ({context, event}) => {\n const isArrowUp = isHotkey('ArrowUp', event.keyboardEvent)\n const focusBlockObject = getFocusBlockObject({context})\n const previousBlock = getPreviousBlock({context})\n\n return isArrowUp && focusBlockObject && !previousBlock\n },\n actions: [\n () => [\n {type: 'insert.text block', placement: 'before'},\n {type: 'select.previous block'},\n ],\n ],\n})\n\nconst breakingBlockObject = defineBehavior({\n on: 'insert.break',\n guard: ({context}) => {\n const focusBlockObject = getFocusBlockObject({context})\n const collapsedSelection = selectionIsCollapsed({context})\n\n return collapsedSelection && focusBlockObject !== undefined\n },\n actions: [() => [{type: 'insert.text block', placement: 'after'}]],\n})\n\nconst deletingEmptyTextBlockAfterBlockObject = defineBehavior({\n on: 'delete.backward',\n guard: ({context}) => {\n const focusTextBlock = getFocusTextBlock({context})\n const selectionCollapsed = selectionIsCollapsed({context})\n const previousBlock = getPreviousBlock({context})\n\n if (!focusTextBlock || !selectionCollapsed || !previousBlock) {\n return false\n }\n\n if (\n isEmptyTextBlock(focusTextBlock.node) &&\n !isPortableTextTextBlock(previousBlock.node)\n ) {\n return {focusTextBlock, previousBlock}\n }\n\n return false\n },\n actions: [\n (_, {focusTextBlock, previousBlock}) => [\n {\n type: 'delete.block',\n blockPath: focusTextBlock.path,\n },\n {\n type: 'select',\n selection: {\n anchor: {path: previousBlock.path, offset: 0},\n focus: {path: previousBlock.path, offset: 0},\n },\n },\n ],\n ],\n})\n\nconst deletingEmptyTextBlockBeforeBlockObject = defineBehavior({\n on: 'delete.forward',\n guard: ({context}) => {\n const focusTextBlock = getFocusTextBlock({context})\n const selectionCollapsed = selectionIsCollapsed({context})\n const nextBlock = getNextBlock({context})\n\n if (!focusTextBlock || !selectionCollapsed || !nextBlock) {\n return false\n }\n\n if (\n isEmptyTextBlock(focusTextBlock.node) &&\n !isPortableTextTextBlock(nextBlock.node)\n ) {\n return {focusTextBlock, nextBlock}\n }\n\n return false\n },\n actions: [\n (_, {focusTextBlock, nextBlock}) => [\n {\n type: 'delete.block',\n blockPath: focusTextBlock.path,\n },\n {\n type: 'select',\n selection: {\n anchor: {path: nextBlock.path, offset: 0},\n focus: {path: nextBlock.path, offset: 0},\n },\n },\n ],\n ],\n})\n\nexport const coreBlockObjectBehaviors = {\n arrowDownOnLonelyBlockObject,\n arrowUpOnLonelyBlockObject,\n breakingBlockObject,\n deletingEmptyTextBlockAfterBlockObject,\n deletingEmptyTextBlockBeforeBlockObject,\n}\n","import {defineBehavior} from './behavior.types'\n\nconst decoratorAdd = defineBehavior({\n on: 'decorator.add',\n actions: [\n ({event}) => [\n event,\n {\n type: 'reselect',\n },\n ],\n ],\n})\n\nconst decoratorRemove = defineBehavior({\n on: 'decorator.remove',\n guard: ({event}) => ({decorator: event.decorator}),\n actions: [\n ({event}) => [\n event,\n {\n type: 'reselect',\n },\n ],\n ],\n})\n\nconst decoratorToggle = defineBehavior({\n on: 'decorator.toggle',\n guard: ({event}) => ({decorator: event.decorator}),\n actions: [\n ({event}) => [\n event,\n {\n type: 'reselect',\n },\n ],\n ],\n})\n\nexport const coreDecoratorBehaviors = {\n decoratorAdd,\n decoratorRemove,\n decoratorToggle,\n}\n","import {createGuards} from '../behavior-actions/behavior.guards'\nimport {isEmptyTextBlock} from '../editor/utils/utils'\nimport {\n getFocusListBlock,\n getFocusSpan,\n getFocusTextBlock,\n getSelectedBlocks,\n selectionIsCollapsed,\n} from '../selectors/selectors'\nimport {isHotkey} from '../utils/is-hotkey'\nimport {defineBehavior} from './behavior.types'\n\nconst MAX_LIST_LEVEL = 10\n\nconst clearListOnBackspace = defineBehavior({\n on: 'delete.backward',\n guard: ({context}) => {\n const selectionCollapsed = selectionIsCollapsed({context})\n const focusTextBlock = getFocusTextBlock({context})\n const focusSpan = getFocusSpan({context})\n\n if (!selectionCollapsed || !focusTextBlock || !focusSpan) {\n return false\n }\n\n const atTheBeginningOfBLock =\n focusTextBlock.node.children[0]._key === focusSpan.node._key &&\n context.selection?.focus.offset === 0\n\n if (atTheBeginningOfBLock && focusTextBlock.node.level === 1) {\n return {focusTextBlock}\n }\n\n return false\n },\n actions: [\n (_, {focusTextBlock}) => [\n {\n type: 'text block.unset',\n props: ['listItem', 'level'],\n at: focusTextBlock.path,\n },\n ],\n ],\n})\n\nconst unindentListOnBackspace = defineBehavior({\n on: 'delete.backward',\n guard: ({context}) => {\n const selectionCollapsed = selectionIsCollapsed({context})\n const focusTextBlock = getFocusTextBlock({context})\n const focusSpan = getFocusSpan({context})\n\n if (!selectionCollapsed || !focusTextBlock || !focusSpan) {\n return false\n }\n\n const atTheBeginningOfBLock =\n focusTextBlock.node.children[0]._key === focusSpan.node._key &&\n context.selection?.focus.offset === 0\n\n if (\n atTheBeginningOfBLock &&\n focusTextBlock.node.level !== undefined &&\n focusTextBlock.node.level > 1\n ) {\n return {focusTextBlock, level: focusTextBlock.node.level - 1}\n }\n\n return false\n },\n actions: [\n (_, {focusTextBlock, level}) => [\n {\n type: 'text block.set',\n level,\n at: focusTextBlock.path,\n },\n ],\n ],\n})\n\nconst clearListOnEnter = defineBehavior({\n on: 'insert.break',\n guard: ({context}) => {\n const selectionCollapsed = selectionIsCollapsed({context})\n const focusListBlock = getFocusListBlock({context})\n\n if (\n !selectionCollapsed ||\n !focusListBlock ||\n !isEmptyTextBlock(focusListBlock.node)\n ) {\n return false\n }\n\n return {focusListBlock}\n },\n actions: [\n (_, {focusListBlock}) => [\n {\n type: 'text block.unset',\n props: ['listItem', 'level'],\n at: focusListBlock.path,\n },\n ],\n ],\n})\n\nconst indentListOnTab = defineBehavior({\n on: 'key.down',\n guard: ({context, event}) => {\n const isTab = isHotkey('Tab', event.keyboardEvent)\n\n if (!isTab) {\n return false\n }\n\n const selectedBlocks = getSelectedBlocks({context})\n const guards = createGuards(context)\n const selectedListBlocks = selectedBlocks.flatMap((block) =>\n guards.isListBlock(block.node)\n ? [\n {\n node: block.node,\n path: block.path,\n },\n ]\n : [],\n )\n\n if (selectedListBlocks.length === selectedBlocks.length) {\n return {selectedListBlocks}\n }\n\n return false\n },\n actions: [\n (_, {selectedListBlocks}) =>\n selectedListBlocks.map((selectedListBlock) => ({\n type: 'text block.set',\n level: Math.min(\n MAX_LIST_LEVEL,\n Math.max(1, selectedListBlock.node.level + 1),\n ),\n at: selectedListBlock.path,\n })),\n ],\n})\n\nconst unindentListOnShiftTab = defineBehavior({\n on: 'key.down',\n guard: ({context, event}) => {\n const isShiftTab = isHotkey('Shift+Tab', event.keyboardEvent)\n\n if (!isShiftTab) {\n return false\n }\n\n const selectedBlocks = getSelectedBlocks({context})\n const guards = createGuards(context)\n const selectedListBlocks = selectedBlocks.flatMap((block) =>\n guards.isListBlock(block.node)\n ? [\n {\n node: block.node,\n path: block.path,\n },\n ]\n : [],\n )\n\n if (selectedListBlocks.length === selectedBlocks.length) {\n return {selectedListBlocks}\n }\n\n return false\n },\n actions: [\n (_, {selectedListBlocks}) =>\n selectedListBlocks.map((selectedListBlock) => ({\n type: 'text block.set',\n level: Math.min(\n MAX_LIST_LEVEL,\n Math.max(1, selectedListBlock.node.level - 1),\n ),\n at: selectedListBlock.path,\n })),\n ],\n})\n\nexport const coreListBehaviors = {\n clearListOnBackspace,\n unindentListOnBackspace,\n clearListOnEnter,\n indentListOnTab,\n unindentListOnShiftTab,\n}\n","import {coreBlockObjectBehaviors} from './behavior.core.block-objects'\nimport {coreDecoratorBehaviors} from './behavior.core.decorators'\nimport {coreListBehaviors} from './behavior.core.lists'\nimport {defineBehavior} from './behavior.types'\n\nconst softReturn = defineBehavior({\n on: 'insert.soft break',\n actions: [() => [{type: 'insert.text', text: '\\n'}]],\n})\n\n/**\n * @alpha\n */\nexport const coreBehaviors = [\n softReturn,\n coreDecoratorBehaviors.decoratorAdd,\n coreDecoratorBehaviors.decoratorRemove,\n coreDecoratorBehaviors.decoratorToggle,\n coreBlockObjectBehaviors.arrowDownOnLonelyBlockObject,\n coreBlockObjectBehaviors.arrowUpOnLonelyBlockObject,\n coreBlockObjectBehaviors.breakingBlockObject,\n coreBlockObjectBehaviors.deletingEmptyTextBlockAfterBlockObject,\n coreBlockObjectBehaviors.deletingEmptyTextBlockBeforeBlockObject,\n coreListBehaviors.clearListOnBackspace,\n coreListBehaviors.unindentListOnBackspace,\n coreListBehaviors.clearListOnEnter,\n coreListBehaviors.indentListOnTab,\n coreListBehaviors.unindentListOnShiftTab,\n]\n\n/**\n * @alpha\n */\nexport const coreBehavior = {\n softReturn,\n decorators: coreDecoratorBehaviors,\n blockObjects: coreBlockObjectBehaviors,\n lists: coreListBehaviors,\n}\n"],"names":["blockOffsetToSpanSelectionPoint","value","blockOffset","offsetLeft","offset","selectionPoint","block","_key","path","isPortableTextTextBlock","child","children","isPortableTextSpan","text","length","spanSelectionPointToBlockOffset","isEmptyTextBlock","onlyText","every","blockText","getTextBlockText","map","join","IS_MAC","window","test","navigator","userAgent","modifiers","alt","control","meta","shift","aliases","add","break","cmd","command","ctl","ctrl","del","down","esc","ins","left","mod","opt","option","return","right","space","spacebar","up","win","windows","keyCodes","isHotkey","hotkey","event","compareHotkey","parseHotkey","parsedHotkey","altKey","ctrlKey","metaKey","shiftKey","hotkeySegments","replace","split","rawHotkeySegment","optional","endsWith","hotkeySegment","slice","keyName","toKeyName","modifier","alias","code","undefined","TypeError","key","keyCode","toKeyCode","toLowerCase","name","toUpperCase","charCodeAt","defineBehavior","behavior","arrowDownOnLonelyBlockObject","on","guard","context","isArrowDown","keyboardEvent","focusBlockObject","getFocusBlockObject","nextBlock","getNextBlock","actions","type","placement","arrowUpOnLonelyBlockObject","isArrowUp","previousBlock","getPreviousBlock","breakingBlockObject","selectionIsCollapsed","deletingEmptyTextBlockAfterBlockObject","focusTextBlock","getFocusTextBlock","selectionCollapsed","node","_","blockPath","selection","anchor","focus","deletingEmptyTextBlockBeforeBlockObject","coreBlockObjectBehaviors","decoratorAdd","decoratorRemove","decorator","decoratorToggle","coreDecoratorBehaviors","MAX_LIST_LEVEL","clearListOnBackspace","focusSpan","getFocusSpan","level","props","at","unindentListOnBackspace","clearListOnEnter","focusListBlock","getFocusListBlock","indentListOnTab","selectedBlocks","getSelectedBlocks","guards","createGuards","selectedListBlocks","flatMap","isListBlock","selectedListBlock","Math","min","max","unindentListOnShiftTab","coreListBehaviors","softReturn","coreBehaviors","coreBehavior","decorators","blockObjects","lists"],"mappings":"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"}
|