@portabletext/editor 1.33.3 → 1.33.4

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.
Files changed (67) hide show
  1. package/lib/_chunks-cjs/behavior.core.cjs +11 -204
  2. package/lib/_chunks-cjs/behavior.core.cjs.map +1 -1
  3. package/lib/_chunks-cjs/behavior.markdown.cjs +7 -7
  4. package/lib/_chunks-cjs/behavior.markdown.cjs.map +1 -1
  5. package/lib/_chunks-cjs/plugin.event-listener.cjs +196 -25
  6. package/lib/_chunks-cjs/plugin.event-listener.cjs.map +1 -1
  7. package/lib/_chunks-cjs/selector.get-text-before.cjs +3 -3
  8. package/lib/_chunks-cjs/selector.get-text-before.cjs.map +1 -1
  9. package/lib/_chunks-cjs/selector.is-active-style.cjs +246 -0
  10. package/lib/_chunks-cjs/selector.is-active-style.cjs.map +1 -0
  11. package/lib/_chunks-cjs/selector.is-at-the-start-of-block.cjs +23 -198
  12. package/lib/_chunks-cjs/selector.is-at-the-start-of-block.cjs.map +1 -1
  13. package/lib/_chunks-cjs/util.block-offsets-to-selection.cjs +3 -3
  14. package/lib/_chunks-cjs/util.block-offsets-to-selection.cjs.map +1 -1
  15. package/lib/_chunks-cjs/util.reverse-selection.cjs +0 -135
  16. package/lib/_chunks-cjs/util.reverse-selection.cjs.map +1 -1
  17. package/lib/_chunks-cjs/util.slice-blocks.cjs +138 -1
  18. package/lib/_chunks-cjs/util.slice-blocks.cjs.map +1 -1
  19. package/lib/_chunks-es/behavior.core.js +9 -202
  20. package/lib/_chunks-es/behavior.core.js.map +1 -1
  21. package/lib/_chunks-es/behavior.markdown.js +1 -1
  22. package/lib/_chunks-es/plugin.event-listener.js +193 -23
  23. package/lib/_chunks-es/plugin.event-listener.js.map +1 -1
  24. package/lib/_chunks-es/selector.get-text-before.js +2 -1
  25. package/lib/_chunks-es/selector.get-text-before.js.map +1 -1
  26. package/lib/_chunks-es/selector.is-active-style.js +249 -0
  27. package/lib/_chunks-es/selector.is-active-style.js.map +1 -0
  28. package/lib/_chunks-es/selector.is-at-the-start-of-block.js +12 -187
  29. package/lib/_chunks-es/selector.is-at-the-start-of-block.js.map +1 -1
  30. package/lib/_chunks-es/util.block-offsets-to-selection.js +1 -1
  31. package/lib/_chunks-es/util.reverse-selection.js +1 -136
  32. package/lib/_chunks-es/util.reverse-selection.js.map +1 -1
  33. package/lib/_chunks-es/util.slice-blocks.js +140 -3
  34. package/lib/_chunks-es/util.slice-blocks.js.map +1 -1
  35. package/lib/index.d.cts +1 -115
  36. package/lib/index.d.ts +1 -115
  37. package/lib/plugins/index.cjs +11 -11
  38. package/lib/plugins/index.cjs.map +1 -1
  39. package/lib/plugins/index.d.cts +1 -115
  40. package/lib/plugins/index.d.ts +1 -115
  41. package/lib/plugins/index.js +1 -1
  42. package/lib/selectors/index.cjs +16 -21
  43. package/lib/selectors/index.cjs.map +1 -1
  44. package/lib/selectors/index.js +7 -11
  45. package/lib/selectors/index.js.map +1 -1
  46. package/lib/utils/index.cjs +13 -13
  47. package/lib/utils/index.cjs.map +1 -1
  48. package/lib/utils/index.js +3 -3
  49. package/package.json +1 -1
  50. package/src/behaviors/behavior.core.annotations.ts +0 -24
  51. package/src/behaviors/behavior.core.decorators.ts +0 -19
  52. package/src/behaviors/behavior.core.insert-break.ts +4 -4
  53. package/src/behaviors/behavior.core.lists.ts +0 -30
  54. package/src/behaviors/behavior.core.ts +2 -17
  55. package/src/behaviors/behavior.default.ts +198 -0
  56. package/src/behaviors/behavior.foundational.ts +12 -12
  57. package/src/converters/converter.text-html.serialize.test.ts +1 -1
  58. package/src/editor/editor-machine.ts +8 -8
  59. package/src/selectors/selector.get-selection-text.ts +14 -89
  60. package/src/utils/util.slice-blocks.ts +12 -1
  61. package/lib/_chunks-cjs/selector.get-trimmed-selection.cjs +0 -97
  62. package/lib/_chunks-cjs/selector.get-trimmed-selection.cjs.map +0 -1
  63. package/lib/_chunks-es/selector.get-trimmed-selection.js +0 -100
  64. package/lib/_chunks-es/selector.get-trimmed-selection.js.map +0 -1
  65. package/src/behaviors/behavior.core.deserialize.ts +0 -60
  66. package/src/behaviors/behavior.core.serialize.ts +0 -44
  67. package/src/behaviors/behavior.core.style.ts +0 -19
@@ -1,4 +1,5 @@
1
- import { getBlockStartPoint, reverseSelection, isKeyedSegment } from "./util.reverse-selection.js";
1
+ import { getBlockStartPoint, isKeyedSegment } from "./util.slice-blocks.js";
2
+ import { reverseSelection } from "./util.reverse-selection.js";
2
3
  import { getSelectionText } from "./selector.is-at-the-start-of-block.js";
3
4
  const getBlockTextBefore = ({
4
5
  context
@@ -1 +1 @@
1
- {"version":3,"file":"selector.get-text-before.js","sources":["../../src/selectors/selector.get-text-before.ts"],"sourcesContent":["import type {EditorSelector} from '../editor/editor-selector'\nimport {getBlockStartPoint} from '../utils/util.get-block-start-point'\nimport {isKeyedSegment} from '../utils/util.is-keyed-segment'\nimport {reverseSelection} from '../utils/util.reverse-selection'\nimport {getSelectionText} from './selector.get-selection-text'\n\n/**\n * @public\n */\nexport const getBlockTextBefore: EditorSelector<string> = ({context}) => {\n if (!context.selection) {\n return ''\n }\n\n const selection = context.selection.backward\n ? reverseSelection(context.selection)\n : context.selection\n const point = selection.anchor\n const key = isKeyedSegment(point.path[0]) ? point.path[0]._key : undefined\n\n const block = key\n ? context.value.find((block) => block._key === key)\n : undefined\n\n if (!block) {\n return ''\n }\n\n const startOfBlock = getBlockStartPoint({\n node: block,\n path: [{_key: block._key}],\n })\n\n return getSelectionText({\n context: {\n ...context,\n value: context.value,\n selection: {\n anchor: startOfBlock,\n focus: point,\n },\n },\n })\n}\n"],"names":["getBlockTextBefore","context","selection","point","backward","reverseSelection","anchor","key","isKeyedSegment","path","_key","undefined","block","value","find","startOfBlock","getBlockStartPoint","node","getSelectionText","focus"],"mappings":";;AASO,MAAMA,qBAA6CA,CAAC;AAAA,EAACC;AAAO,MAAM;AACvE,MAAI,CAACA,QAAQC;AACJ,WAAA;AAMT,QAAMC,SAHYF,QAAQC,UAAUE,WAChCC,iBAAiBJ,QAAQC,SAAS,IAClCD,QAAQC,WACYI,QAClBC,MAAMC,eAAeL,MAAMM,KAAK,CAAC,CAAC,IAAIN,MAAMM,KAAK,CAAC,EAAEC,OAAOC,QAE3DC,QAAQL,MACVN,QAAQY,MAAMC,KAAMF,CAAAA,WAAUA,OAAMF,SAASH,GAAG,IAChDI;AAEJ,MAAI,CAACC;AACI,WAAA;AAGT,QAAMG,eAAeC,mBAAmB;AAAA,IACtCC,MAAML;AAAAA,IACNH,MAAM,CAAC;AAAA,MAACC,MAAME,MAAMF;AAAAA,IAAK,CAAA;AAAA,EAAA,CAC1B;AAED,SAAOQ,iBAAiB;AAAA,IACtBjB,SAAS;AAAA,MACP,GAAGA;AAAAA,MACHY,OAAOZ,QAAQY;AAAAA,MACfX,WAAW;AAAA,QACTI,QAAQS;AAAAA,QACRI,OAAOhB;AAAAA,MAAAA;AAAAA,IACT;AAAA,EACF,CACD;AACH;"}
1
+ {"version":3,"file":"selector.get-text-before.js","sources":["../../src/selectors/selector.get-text-before.ts"],"sourcesContent":["import type {EditorSelector} from '../editor/editor-selector'\nimport {getBlockStartPoint} from '../utils/util.get-block-start-point'\nimport {isKeyedSegment} from '../utils/util.is-keyed-segment'\nimport {reverseSelection} from '../utils/util.reverse-selection'\nimport {getSelectionText} from './selector.get-selection-text'\n\n/**\n * @public\n */\nexport const getBlockTextBefore: EditorSelector<string> = ({context}) => {\n if (!context.selection) {\n return ''\n }\n\n const selection = context.selection.backward\n ? reverseSelection(context.selection)\n : context.selection\n const point = selection.anchor\n const key = isKeyedSegment(point.path[0]) ? point.path[0]._key : undefined\n\n const block = key\n ? context.value.find((block) => block._key === key)\n : undefined\n\n if (!block) {\n return ''\n }\n\n const startOfBlock = getBlockStartPoint({\n node: block,\n path: [{_key: block._key}],\n })\n\n return getSelectionText({\n context: {\n ...context,\n value: context.value,\n selection: {\n anchor: startOfBlock,\n focus: point,\n },\n },\n })\n}\n"],"names":["getBlockTextBefore","context","selection","point","backward","reverseSelection","anchor","key","isKeyedSegment","path","_key","undefined","block","value","find","startOfBlock","getBlockStartPoint","node","getSelectionText","focus"],"mappings":";;;AASO,MAAMA,qBAA6CA,CAAC;AAAA,EAACC;AAAO,MAAM;AACvE,MAAI,CAACA,QAAQC;AACJ,WAAA;AAMT,QAAMC,SAHYF,QAAQC,UAAUE,WAChCC,iBAAiBJ,QAAQC,SAAS,IAClCD,QAAQC,WACYI,QAClBC,MAAMC,eAAeL,MAAMM,KAAK,CAAC,CAAC,IAAIN,MAAMM,KAAK,CAAC,EAAEC,OAAOC,QAE3DC,QAAQL,MACVN,QAAQY,MAAMC,KAAMF,CAAAA,WAAUA,OAAMF,SAASH,GAAG,IAChDI;AAEJ,MAAI,CAACC;AACI,WAAA;AAGT,QAAMG,eAAeC,mBAAmB;AAAA,IACtCC,MAAML;AAAAA,IACNH,MAAM,CAAC;AAAA,MAACC,MAAME,MAAMF;AAAAA,IAAK,CAAA;AAAA,EAAA,CAC1B;AAED,SAAOQ,iBAAiB;AAAA,IACtBjB,SAAS;AAAA,MACP,GAAGA;AAAAA,MACHY,OAAOZ,QAAQY;AAAAA,MACfX,WAAW;AAAA,QACTI,QAAQS;AAAAA,QACRI,OAAOhB;AAAAA,MAAAA;AAAAA,IACT;AAAA,EACF,CACD;AACH;"}
@@ -0,0 +1,249 @@
1
+ import { isKeySegment, isPortableTextTextBlock, isPortableTextSpan } from "@sanity/types";
2
+ import { isEmptyTextBlock, isKeyedSegment } from "./util.slice-blocks.js";
3
+ import { getSelectedBlocks, createGuards, isSelectionCollapsed, getFocusTextBlock, getSelectionStartPoint, getSelectionEndPoint, getFocusSpan, isSelectionExpanded } from "./selector.is-at-the-start-of-block.js";
4
+ const getSelectedSpans = ({
5
+ context
6
+ }) => {
7
+ if (!context.selection)
8
+ return [];
9
+ const selectedSpans = [], startPoint = context.selection.backward ? context.selection.focus : context.selection.anchor, endPoint = context.selection.backward ? context.selection.anchor : context.selection.focus, startBlockKey = isKeySegment(startPoint.path[0]) ? startPoint.path[0]._key : void 0, endBlockKey = isKeySegment(endPoint.path[0]) ? endPoint.path[0]._key : void 0;
10
+ if (!startBlockKey || !endBlockKey)
11
+ return selectedSpans;
12
+ const startSpanKey = isKeySegment(startPoint.path[2]) ? startPoint.path[2]._key : void 0, endSpanKey = isKeySegment(endPoint.path[2]) ? endPoint.path[2]._key : void 0;
13
+ for (const block of context.value)
14
+ if (isPortableTextTextBlock(block)) {
15
+ if (block._key === startBlockKey) {
16
+ for (const child of block.children)
17
+ if (isPortableTextSpan(child)) {
18
+ if (startSpanKey && child._key === startSpanKey) {
19
+ if (startPoint.offset < child.text.length && selectedSpans.push({
20
+ node: child,
21
+ path: [{
22
+ _key: block._key
23
+ }, "children", {
24
+ _key: child._key
25
+ }]
26
+ }), startSpanKey === endSpanKey)
27
+ break;
28
+ continue;
29
+ }
30
+ if (endSpanKey && child._key === endSpanKey) {
31
+ endPoint.offset > 0 && selectedSpans.push({
32
+ node: child,
33
+ path: [{
34
+ _key: block._key
35
+ }, "children", {
36
+ _key: child._key
37
+ }]
38
+ });
39
+ break;
40
+ }
41
+ selectedSpans.length > 0 && selectedSpans.push({
42
+ node: child,
43
+ path: [{
44
+ _key: block._key
45
+ }, "children", {
46
+ _key: child._key
47
+ }]
48
+ });
49
+ }
50
+ if (startBlockKey === endBlockKey)
51
+ break;
52
+ continue;
53
+ }
54
+ if (block._key === endBlockKey) {
55
+ for (const child of block.children)
56
+ if (isPortableTextSpan(child)) {
57
+ if (endSpanKey && child._key === endSpanKey) {
58
+ endPoint.offset > 0 && selectedSpans.push({
59
+ node: child,
60
+ path: [{
61
+ _key: block._key
62
+ }, "children", {
63
+ _key: child._key
64
+ }]
65
+ });
66
+ break;
67
+ }
68
+ selectedSpans.push({
69
+ node: child,
70
+ path: [{
71
+ _key: block._key
72
+ }, "children", {
73
+ _key: child._key
74
+ }]
75
+ });
76
+ }
77
+ break;
78
+ }
79
+ if (selectedSpans.length > 0)
80
+ for (const child of block.children)
81
+ isPortableTextSpan(child) && selectedSpans.push({
82
+ node: child,
83
+ path: [{
84
+ _key: block._key
85
+ }, "children", {
86
+ _key: child._key
87
+ }]
88
+ });
89
+ }
90
+ return selectedSpans;
91
+ }, getActiveListItem = ({
92
+ context
93
+ }) => {
94
+ if (!context.selection)
95
+ return;
96
+ const guards = createGuards(context), selectedTextBlocks = getSelectedBlocks({
97
+ context
98
+ }).map((block) => block.node).filter(guards.isTextBlock), firstTextBlock = selectedTextBlocks.at(0);
99
+ if (!firstTextBlock)
100
+ return;
101
+ const firstListItem = firstTextBlock.listItem;
102
+ if (firstListItem && selectedTextBlocks.every((block) => block.listItem === firstListItem))
103
+ return firstListItem;
104
+ }, getActiveStyle = ({
105
+ context
106
+ }) => {
107
+ if (!context.selection)
108
+ return;
109
+ const guards = createGuards(context), selectedTextBlocks = getSelectedBlocks({
110
+ context
111
+ }).map((block) => block.node).filter(guards.isTextBlock), firstTextBlock = selectedTextBlocks.at(0);
112
+ if (!firstTextBlock)
113
+ return;
114
+ const firstStyle = firstTextBlock.style;
115
+ if (firstStyle && selectedTextBlocks.every((block) => block.style === firstStyle))
116
+ return firstStyle;
117
+ }, getTrimmedSelection = ({
118
+ context
119
+ }) => {
120
+ if (!context.selection)
121
+ return context.selection;
122
+ const startPoint = getSelectionStartPoint({
123
+ context
124
+ }), endPoint = getSelectionEndPoint({
125
+ context
126
+ });
127
+ if (!startPoint || !endPoint)
128
+ return context.selection;
129
+ const startBlockKey = isKeyedSegment(startPoint.path[0]) ? startPoint.path[0]._key : null, startChildKey = isKeyedSegment(startPoint.path[2]) ? startPoint.path[2]._key : null, endBlockKey = isKeyedSegment(endPoint.path[0]) ? endPoint.path[0]._key : null, endChildKey = isKeyedSegment(endPoint.path[2]) ? endPoint.path[2]._key : null;
130
+ if (!startBlockKey || !endBlockKey)
131
+ return context.selection;
132
+ let startBlockFound = !1, adjustedStartPoint, trimStartPoint = !1, adjustedEndPoint, trimEndPoint = !1, previousPotentialEndpoint;
133
+ for (const block of context.value)
134
+ if (!(block._key === startBlockKey && (startBlockFound = !0, isPortableTextTextBlock(block) && isEmptyTextBlock(block))) && startBlockFound && isPortableTextTextBlock(block)) {
135
+ if (block._key === endBlockKey && isEmptyTextBlock(block))
136
+ break;
137
+ for (const child of block.children) {
138
+ if (child._key === endChildKey && (!isPortableTextSpan(child) || endPoint.offset === 0)) {
139
+ adjustedEndPoint = previousPotentialEndpoint ? {
140
+ path: [{
141
+ _key: previousPotentialEndpoint.blockKey
142
+ }, "children", {
143
+ _key: previousPotentialEndpoint.span._key
144
+ }],
145
+ offset: previousPotentialEndpoint.span.text.length
146
+ } : void 0, trimEndPoint = !0;
147
+ break;
148
+ }
149
+ if (trimStartPoint) {
150
+ const lonelySpan = isPortableTextSpan(child) && block.children.length === 1;
151
+ (isPortableTextSpan(child) && child.text.length > 0 || lonelySpan) && (adjustedStartPoint = {
152
+ path: [{
153
+ _key: block._key
154
+ }, "children", {
155
+ _key: child._key
156
+ }],
157
+ offset: 0
158
+ }, previousPotentialEndpoint = {
159
+ blockKey: block._key,
160
+ span: child
161
+ }, trimStartPoint = !1);
162
+ continue;
163
+ }
164
+ if (child._key === startChildKey) {
165
+ if (!isPortableTextSpan(child)) {
166
+ trimStartPoint = !0;
167
+ continue;
168
+ }
169
+ if (startPoint.offset === child.text.length) {
170
+ trimStartPoint = !0, previousPotentialEndpoint = child.text.length > 0 ? {
171
+ blockKey: block._key,
172
+ span: child
173
+ } : previousPotentialEndpoint;
174
+ continue;
175
+ }
176
+ }
177
+ previousPotentialEndpoint = isPortableTextSpan(child) && child.text.length > 0 ? {
178
+ blockKey: block._key,
179
+ span: child
180
+ } : previousPotentialEndpoint;
181
+ }
182
+ if (block._key === endBlockKey)
183
+ break;
184
+ }
185
+ const trimmedSelection = context.selection.backward ? {
186
+ anchor: trimEndPoint && adjustedEndPoint ? adjustedEndPoint : endPoint,
187
+ focus: adjustedStartPoint ?? startPoint,
188
+ backward: !0
189
+ } : {
190
+ anchor: adjustedStartPoint ?? startPoint,
191
+ focus: trimEndPoint && adjustedEndPoint ? adjustedEndPoint : endPoint
192
+ };
193
+ if (isSelectionCollapsed({
194
+ context: {
195
+ ...context,
196
+ selection: trimmedSelection
197
+ }
198
+ })) {
199
+ const focusTextBlock = getFocusTextBlock({
200
+ context: {
201
+ ...context,
202
+ selection: trimmedSelection
203
+ }
204
+ });
205
+ if (focusTextBlock && !isEmptyTextBlock(focusTextBlock.node))
206
+ return null;
207
+ }
208
+ return trimmedSelection;
209
+ };
210
+ function isActiveAnnotation(annotation) {
211
+ return (snapshot) => {
212
+ if (!snapshot.context.selection)
213
+ return !1;
214
+ const selectedBlocks = getSelectedBlocks(snapshot), focusSpan = getFocusSpan(snapshot), selectedSpans = isSelectionExpanded(snapshot) ? getSelectedSpans(snapshot) : focusSpan ? [focusSpan] : [];
215
+ if (selectedSpans.length === 0 || selectedSpans.some((span) => !span.node.marks || span.node.marks?.length === 0))
216
+ return !1;
217
+ const selectionMarkDefs = selectedBlocks.flatMap((block) => isPortableTextTextBlock(block.node) ? block.node.markDefs ?? [] : []);
218
+ return selectedSpans.every((span) => (span.node.marks?.flatMap((mark) => {
219
+ const markDef = selectionMarkDefs.find((markDef2) => markDef2._key === mark);
220
+ return markDef ? [markDef._type] : [];
221
+ }) ?? []).includes(annotation));
222
+ };
223
+ }
224
+ function isActiveDecorator(decorator) {
225
+ return (snapshot) => {
226
+ if (isSelectionExpanded(snapshot)) {
227
+ const selectedSpans = getSelectedSpans(snapshot);
228
+ return selectedSpans.length > 0 && selectedSpans.every((span) => span.node.marks?.includes(decorator));
229
+ }
230
+ return snapshot.context.activeDecorators.includes(decorator);
231
+ };
232
+ }
233
+ function isActiveListItem(listItem) {
234
+ return (snapshot) => getActiveListItem(snapshot) === listItem;
235
+ }
236
+ function isActiveStyle(style) {
237
+ return (snapshot) => getActiveStyle(snapshot) === style;
238
+ }
239
+ export {
240
+ getActiveListItem,
241
+ getActiveStyle,
242
+ getSelectedSpans,
243
+ getTrimmedSelection,
244
+ isActiveAnnotation,
245
+ isActiveDecorator,
246
+ isActiveListItem,
247
+ isActiveStyle
248
+ };
249
+ //# sourceMappingURL=selector.is-active-style.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"selector.is-active-style.js","sources":["../../src/selectors/selector.get-selected-spans.ts","../../src/selectors/selector.get-active-list-item.ts","../../src/selectors/selector.get-active-style.ts","../../src/selectors/selector.get-trimmed-selection.ts","../../src/selectors/selector.is-active-annotation.ts","../../src/selectors/selector.is-active-decorator.ts","../../src/selectors/selector.is-active-list-item.ts","../../src/selectors/selector.is-active-style.ts"],"sourcesContent":["import {\n isKeySegment,\n isPortableTextSpan,\n isPortableTextTextBlock,\n type KeyedSegment,\n type PortableTextSpan,\n} from '@sanity/types'\nimport type {EditorSelector} from '../editor/editor-selector'\n\n/**\n * @public\n */\nexport const getSelectedSpans: EditorSelector<\n Array<{\n node: PortableTextSpan\n path: [KeyedSegment, 'children', KeyedSegment]\n }>\n> = ({context}) => {\n if (!context.selection) {\n return []\n }\n\n const selectedSpans: Array<{\n node: PortableTextSpan\n path: [KeyedSegment, 'children', KeyedSegment]\n }> = []\n\n const startPoint = context.selection.backward\n ? context.selection.focus\n : context.selection.anchor\n const endPoint = context.selection.backward\n ? context.selection.anchor\n : context.selection.focus\n\n const startBlockKey = isKeySegment(startPoint.path[0])\n ? startPoint.path[0]._key\n : undefined\n const endBlockKey = isKeySegment(endPoint.path[0])\n ? endPoint.path[0]._key\n : undefined\n\n if (!startBlockKey || !endBlockKey) {\n return selectedSpans\n }\n\n const startSpanKey = isKeySegment(startPoint.path[2])\n ? startPoint.path[2]._key\n : undefined\n const endSpanKey = isKeySegment(endPoint.path[2])\n ? endPoint.path[2]._key\n : undefined\n\n for (const block of context.value) {\n if (!isPortableTextTextBlock(block)) {\n continue\n }\n\n if (block._key === startBlockKey) {\n for (const child of block.children) {\n if (!isPortableTextSpan(child)) {\n continue\n }\n\n if (startSpanKey && child._key === startSpanKey) {\n if (startPoint.offset < child.text.length) {\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n\n if (startSpanKey === endSpanKey) {\n break\n }\n\n continue\n }\n\n if (endSpanKey && child._key === endSpanKey) {\n if (endPoint.offset > 0) {\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n break\n }\n\n if (selectedSpans.length > 0) {\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n }\n\n if (startBlockKey === endBlockKey) {\n break\n }\n\n continue\n }\n\n if (block._key === endBlockKey) {\n for (const child of block.children) {\n if (!isPortableTextSpan(child)) {\n continue\n }\n\n if (endSpanKey && child._key === endSpanKey) {\n if (endPoint.offset > 0) {\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n break\n }\n\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n\n break\n }\n\n if (selectedSpans.length > 0) {\n for (const child of block.children) {\n if (!isPortableTextSpan(child)) {\n continue\n }\n\n selectedSpans.push({\n node: child,\n path: [{_key: block._key}, 'children', {_key: child._key}],\n })\n }\n }\n }\n\n return selectedSpans\n}\n","import type {PortableTextListBlock} from '@sanity/types'\nimport {createGuards} from '../behavior-actions/behavior.guards'\nimport type {EditorSelector} from '../editor/editor-selector'\nimport {getSelectedBlocks} from './selectors'\n\n/**\n * @public\n */\nexport const getActiveListItem: EditorSelector<\n PortableTextListBlock['listItem'] | undefined\n> = ({context}) => {\n if (!context.selection) {\n return undefined\n }\n\n const guards = createGuards(context)\n const selectedBlocks = getSelectedBlocks({context}).map((block) => block.node)\n const selectedTextBlocks = selectedBlocks.filter(guards.isTextBlock)\n\n const firstTextBlock = selectedTextBlocks.at(0)\n\n if (!firstTextBlock) {\n return undefined\n }\n\n const firstListItem = firstTextBlock.listItem\n\n if (!firstListItem) {\n return undefined\n }\n\n if (selectedTextBlocks.every((block) => block.listItem === firstListItem)) {\n return firstListItem\n }\n\n return undefined\n}\n","import type {PortableTextTextBlock} from '@sanity/types'\nimport {createGuards} from '../behavior-actions/behavior.guards'\nimport type {EditorSelector} from '../editor/editor-selector'\nimport {getSelectedBlocks} from './selectors'\n\n/**\n * @public\n */\nexport const getActiveStyle: EditorSelector<PortableTextTextBlock['style']> = ({\n context,\n}) => {\n if (!context.selection) {\n return undefined\n }\n\n const guards = createGuards(context)\n const selectedBlocks = getSelectedBlocks({context}).map((block) => block.node)\n const selectedTextBlocks = selectedBlocks.filter(guards.isTextBlock)\n\n const firstTextBlock = selectedTextBlocks.at(0)\n\n if (!firstTextBlock) {\n return undefined\n }\n\n const firstStyle = firstTextBlock.style\n\n if (!firstStyle) {\n return undefined\n }\n\n if (selectedTextBlocks.every((block) => block.style === firstStyle)) {\n return firstStyle\n }\n\n return undefined\n}\n","import {\n isPortableTextSpan,\n isPortableTextTextBlock,\n type PortableTextSpan,\n} from '@sanity/types'\nimport type {EditorSelector} from '../editor/editor-selector'\nimport type {EditorSelection, EditorSelectionPoint} from '../types/editor'\nimport {isEmptyTextBlock, isKeyedSegment} from '../utils'\nimport {getSelectionEndPoint} from './selector.get-selection-end-point'\nimport {getSelectionStartPoint} from './selector.get-selection-start-point'\nimport {isSelectionCollapsed} from './selector.is-selection-collapsed'\nimport {getFocusTextBlock} from './selectors'\n\n/**\n * @public\n */\nexport const getTrimmedSelection: EditorSelector<EditorSelection> = ({\n context,\n}) => {\n if (!context.selection) {\n return context.selection\n }\n\n const startPoint = getSelectionStartPoint({context})\n const endPoint = getSelectionEndPoint({context})\n\n if (!startPoint || !endPoint) {\n return context.selection\n }\n\n const startBlockKey = isKeyedSegment(startPoint.path[0])\n ? startPoint.path[0]._key\n : null\n const startChildKey = isKeyedSegment(startPoint.path[2])\n ? startPoint.path[2]._key\n : null\n const endBlockKey = isKeyedSegment(endPoint.path[0])\n ? endPoint.path[0]._key\n : null\n const endChildKey = isKeyedSegment(endPoint.path[2])\n ? endPoint.path[2]._key\n : null\n\n if (!startBlockKey || !endBlockKey) {\n return context.selection\n }\n\n let startBlockFound = false\n let adjustedStartPoint: EditorSelectionPoint | undefined\n let trimStartPoint = false\n let adjustedEndPoint: EditorSelectionPoint | undefined\n let trimEndPoint = false\n let previousPotentialEndpoint:\n | {blockKey: string; span: PortableTextSpan}\n | undefined\n\n for (const block of context.value) {\n if (block._key === startBlockKey) {\n startBlockFound = true\n\n if (isPortableTextTextBlock(block) && isEmptyTextBlock(block)) {\n continue\n }\n }\n\n if (!startBlockFound) {\n continue\n }\n\n if (!isPortableTextTextBlock(block)) {\n continue\n }\n\n if (block._key === endBlockKey && isEmptyTextBlock(block)) {\n break\n }\n\n for (const child of block.children) {\n if (child._key === endChildKey) {\n if (!isPortableTextSpan(child) || endPoint.offset === 0) {\n adjustedEndPoint = previousPotentialEndpoint\n ? {\n path: [\n {_key: previousPotentialEndpoint.blockKey},\n 'children',\n {_key: previousPotentialEndpoint.span._key},\n ],\n offset: previousPotentialEndpoint.span.text.length,\n }\n : undefined\n\n trimEndPoint = true\n break\n }\n }\n\n if (trimStartPoint) {\n const lonelySpan =\n isPortableTextSpan(child) && block.children.length === 1\n\n if (\n (isPortableTextSpan(child) && child.text.length > 0) ||\n lonelySpan\n ) {\n adjustedStartPoint = {\n path: [{_key: block._key}, 'children', {_key: child._key}],\n offset: 0,\n }\n previousPotentialEndpoint = {blockKey: block._key, span: child}\n trimStartPoint = false\n }\n\n continue\n }\n\n if (child._key === startChildKey) {\n if (!isPortableTextSpan(child)) {\n trimStartPoint = true\n continue\n }\n\n if (startPoint.offset === child.text.length) {\n trimStartPoint = true\n previousPotentialEndpoint =\n child.text.length > 0\n ? {blockKey: block._key, span: child}\n : previousPotentialEndpoint\n continue\n }\n }\n\n previousPotentialEndpoint =\n isPortableTextSpan(child) && child.text.length > 0\n ? {blockKey: block._key, span: child}\n : previousPotentialEndpoint\n }\n\n if (block._key === endBlockKey) {\n break\n }\n }\n\n const trimmedSelection = context.selection.backward\n ? {\n anchor: trimEndPoint && adjustedEndPoint ? adjustedEndPoint : endPoint,\n focus: adjustedStartPoint ?? startPoint,\n backward: true,\n }\n : {\n anchor: adjustedStartPoint ?? startPoint,\n focus: trimEndPoint && adjustedEndPoint ? adjustedEndPoint : endPoint,\n }\n\n if (\n isSelectionCollapsed({\n context: {\n ...context,\n selection: trimmedSelection,\n },\n })\n ) {\n const focusTextBlock = getFocusTextBlock({\n context: {\n ...context,\n selection: trimmedSelection,\n },\n })\n\n if (focusTextBlock && !isEmptyTextBlock(focusTextBlock.node)) {\n return null\n }\n }\n\n return trimmedSelection\n}\n","import {isPortableTextTextBlock} from '@sanity/types'\nimport type {EditorSelector} from '../editor/editor-selector'\nimport {getSelectedSpans} from './selector.get-selected-spans'\nimport {isSelectionExpanded} from './selector.is-selection-expanded'\nimport {getFocusSpan, getSelectedBlocks} from './selectors'\n\n/**\n * @public\n */\nexport function isActiveAnnotation(\n annotation: string,\n): EditorSelector<boolean> {\n return (snapshot) => {\n if (!snapshot.context.selection) {\n return false\n }\n\n const selectedBlocks = getSelectedBlocks(snapshot)\n const focusSpan = getFocusSpan(snapshot)\n\n const selectedSpans = isSelectionExpanded(snapshot)\n ? getSelectedSpans(snapshot)\n : focusSpan\n ? [focusSpan]\n : []\n\n if (selectedSpans.length === 0) {\n return false\n }\n\n if (\n selectedSpans.some(\n (span) => !span.node.marks || span.node.marks?.length === 0,\n )\n ) {\n return false\n }\n\n const selectionMarkDefs = selectedBlocks.flatMap((block) =>\n isPortableTextTextBlock(block.node) ? (block.node.markDefs ?? []) : [],\n )\n\n return selectedSpans.every((span) => {\n const spanMarkDefs =\n span.node.marks?.flatMap((mark) => {\n const markDef = selectionMarkDefs.find(\n (markDef) => markDef._key === mark,\n )\n\n return markDef ? [markDef._type] : []\n }) ?? []\n\n return spanMarkDefs.includes(annotation)\n })\n }\n}\n","import type {EditorSelector} from '../editor/editor-selector'\nimport {getSelectedSpans} from './selector.get-selected-spans'\nimport {isSelectionExpanded} from './selector.is-selection-expanded'\n\n/**\n * @public\n */\nexport function isActiveDecorator(decorator: string): EditorSelector<boolean> {\n return (snapshot) => {\n if (isSelectionExpanded(snapshot)) {\n const selectedSpans = getSelectedSpans(snapshot)\n\n return (\n selectedSpans.length > 0 &&\n selectedSpans.every((span) => span.node.marks?.includes(decorator))\n )\n }\n\n return snapshot.context.activeDecorators.includes(decorator)\n }\n}\n","import type {EditorSelector} from '../editor/editor-selector'\nimport {getActiveListItem} from './selector.get-active-list-item'\n\n/**\n * @public\n */\nexport function isActiveListItem(listItem: string): EditorSelector<boolean> {\n return (snapshot) => {\n const activeListItem = getActiveListItem(snapshot)\n\n return activeListItem === listItem\n }\n}\n","import type {EditorSelector} from '../editor/editor-selector'\nimport {getActiveStyle} from './selector.get-active-style'\n\n/**\n * @public\n */\nexport function isActiveStyle(style: string): EditorSelector<boolean> {\n return (snapshot) => {\n const activeStyle = getActiveStyle(snapshot)\n\n return activeStyle === style\n }\n}\n"],"names":["getSelectedSpans","context","selection","selectedSpans","startPoint","backward","focus","anchor","endPoint","startBlockKey","isKeySegment","path","_key","undefined","endBlockKey","startSpanKey","endSpanKey","block","value","isPortableTextTextBlock","child","children","isPortableTextSpan","offset","text","length","push","node","getActiveListItem","guards","createGuards","selectedTextBlocks","getSelectedBlocks","map","filter","isTextBlock","firstTextBlock","at","firstListItem","listItem","every","getActiveStyle","firstStyle","style","getTrimmedSelection","getSelectionStartPoint","getSelectionEndPoint","isKeyedSegment","startChildKey","endChildKey","startBlockFound","adjustedStartPoint","trimStartPoint","adjustedEndPoint","trimEndPoint","previousPotentialEndpoint","isEmptyTextBlock","blockKey","span","lonelySpan","trimmedSelection","isSelectionCollapsed","focusTextBlock","getFocusTextBlock","isActiveAnnotation","annotation","snapshot","selectedBlocks","focusSpan","getFocusSpan","isSelectionExpanded","some","marks","selectionMarkDefs","flatMap","markDefs","mark","markDef","find","_type","includes","isActiveDecorator","decorator","activeDecorators","isActiveListItem","isActiveStyle"],"mappings":"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"}
@@ -1,4 +1,4 @@
1
- import { isSpan, reverseSelection, isKeyedSegment, spanSelectionPointToBlockOffset, getBlockStartPoint, getBlockEndPoint, blockOffsetToSpanSelectionPoint, isEqualSelectionPoints } from "./util.reverse-selection.js";
1
+ import { isSpan, sliceBlocks, spanSelectionPointToBlockOffset, getBlockStartPoint, getBlockEndPoint, blockOffsetToSpanSelectionPoint, isEqualSelectionPoints } from "./util.slice-blocks.js";
2
2
  import { isPortableTextListBlock, isPortableTextTextBlock, isKeySegment, isPortableTextSpan } from "@sanity/types";
3
3
  function createGuards({
4
4
  schema
@@ -14,94 +14,7 @@ function createGuards({
14
14
  isTextBlock
15
15
  };
16
16
  }
17
- const getSelectedSpans = ({
18
- context
19
- }) => {
20
- if (!context.selection)
21
- return [];
22
- const selectedSpans = [], startPoint = context.selection.backward ? context.selection.focus : context.selection.anchor, endPoint = context.selection.backward ? context.selection.anchor : context.selection.focus, startBlockKey = isKeySegment(startPoint.path[0]) ? startPoint.path[0]._key : void 0, endBlockKey = isKeySegment(endPoint.path[0]) ? endPoint.path[0]._key : void 0;
23
- if (!startBlockKey || !endBlockKey)
24
- return selectedSpans;
25
- const startSpanKey = isKeySegment(startPoint.path[2]) ? startPoint.path[2]._key : void 0, endSpanKey = isKeySegment(endPoint.path[2]) ? endPoint.path[2]._key : void 0;
26
- for (const block of context.value)
27
- if (isPortableTextTextBlock(block)) {
28
- if (block._key === startBlockKey) {
29
- for (const child of block.children)
30
- if (isPortableTextSpan(child)) {
31
- if (startSpanKey && child._key === startSpanKey) {
32
- if (startPoint.offset < child.text.length && selectedSpans.push({
33
- node: child,
34
- path: [{
35
- _key: block._key
36
- }, "children", {
37
- _key: child._key
38
- }]
39
- }), startSpanKey === endSpanKey)
40
- break;
41
- continue;
42
- }
43
- if (endSpanKey && child._key === endSpanKey) {
44
- endPoint.offset > 0 && selectedSpans.push({
45
- node: child,
46
- path: [{
47
- _key: block._key
48
- }, "children", {
49
- _key: child._key
50
- }]
51
- });
52
- break;
53
- }
54
- selectedSpans.length > 0 && selectedSpans.push({
55
- node: child,
56
- path: [{
57
- _key: block._key
58
- }, "children", {
59
- _key: child._key
60
- }]
61
- });
62
- }
63
- if (startBlockKey === endBlockKey)
64
- break;
65
- continue;
66
- }
67
- if (block._key === endBlockKey) {
68
- for (const child of block.children)
69
- if (isPortableTextSpan(child)) {
70
- if (endSpanKey && child._key === endSpanKey) {
71
- endPoint.offset > 0 && selectedSpans.push({
72
- node: child,
73
- path: [{
74
- _key: block._key
75
- }, "children", {
76
- _key: child._key
77
- }]
78
- });
79
- break;
80
- }
81
- selectedSpans.push({
82
- node: child,
83
- path: [{
84
- _key: block._key
85
- }, "children", {
86
- _key: child._key
87
- }]
88
- });
89
- }
90
- break;
91
- }
92
- if (selectedSpans.length > 0)
93
- for (const child of block.children)
94
- isPortableTextSpan(child) && selectedSpans.push({
95
- node: child,
96
- path: [{
97
- _key: block._key
98
- }, "children", {
99
- _key: child._key
100
- }]
101
- });
102
- }
103
- return selectedSpans;
104
- }, getFocusBlock = ({
17
+ const getFocusBlock = ({
105
18
  context
106
19
  }) => {
107
20
  const key = context.selection && isKeySegment(context.selection.focus.path[0]) ? context.selection.focus.path[0]._key : void 0, node = key ? context.value.find((block) => block._key === key) : void 0;
@@ -297,32 +210,6 @@ const getSelectedSpans = ({
297
210
  }
298
211
  if (foundSelectionEndBlock && nextBlock)
299
212
  return nextBlock;
300
- }, getActiveListItem = ({
301
- context
302
- }) => {
303
- if (!context.selection)
304
- return;
305
- const guards = createGuards(context), selectedTextBlocks = getSelectedBlocks({
306
- context
307
- }).map((block) => block.node).filter(guards.isTextBlock), firstTextBlock = selectedTextBlocks.at(0);
308
- if (!firstTextBlock)
309
- return;
310
- const firstListItem = firstTextBlock.listItem;
311
- if (firstListItem && selectedTextBlocks.every((block) => block.listItem === firstListItem))
312
- return firstListItem;
313
- }, getActiveStyle = ({
314
- context
315
- }) => {
316
- if (!context.selection)
317
- return;
318
- const guards = createGuards(context), selectedTextBlocks = getSelectedBlocks({
319
- context
320
- }).map((block) => block.node).filter(guards.isTextBlock), firstTextBlock = selectedTextBlocks.at(0);
321
- if (!firstTextBlock)
322
- return;
323
- const firstStyle = firstTextBlock.style;
324
- if (firstStyle && selectedTextBlocks.every((block) => block.style === firstStyle))
325
- return firstStyle;
326
213
  }, getSelectionEndPoint = ({
327
214
  context
328
215
  }) => {
@@ -382,43 +269,16 @@ const getSelectedSpans = ({
382
269
  });
383
270
  }
384
271
  return inlineObject;
385
- }, getSelectionText = ({
272
+ }, getSelectedSlice = ({
386
273
  context
387
- }) => {
388
- let text = "";
389
- const {
390
- value,
391
- selection
392
- } = context;
393
- if (!value || !selection)
394
- return text;
395
- const forwardSelection = selection.backward ? reverseSelection(selection) : selection;
396
- if (!forwardSelection)
397
- return text;
398
- const startBlockKey = isKeyedSegment(forwardSelection.anchor.path[0]) ? forwardSelection.anchor.path[0]._key : void 0, endBlockKey = isKeyedSegment(forwardSelection.focus.path[0]) ? forwardSelection.focus.path[0]._key : void 0, startChildKey = isKeyedSegment(forwardSelection.anchor.path[2]) ? forwardSelection.anchor.path[2]._key : void 0, endChildKey = isKeyedSegment(forwardSelection.focus.path[2]) ? forwardSelection.focus.path[2]._key : void 0;
399
- let startFound = !1;
400
- if (!startBlockKey || !endBlockKey)
401
- return text;
402
- for (const block of value) {
403
- if (block._key === startBlockKey) {
404
- if (!isPortableTextTextBlock(block))
405
- continue;
406
- for (const child of block.children)
407
- if (child._key === startChildKey && (startFound = !0), !!startFound && (isPortableTextSpan(child) && startChildKey && (child._key === startChildKey && child._key === endChildKey ? text = text + child.text.slice(forwardSelection.anchor.offset, forwardSelection.focus.offset) : child._key === startChildKey ? text = text + child.text.slice(forwardSelection.anchor.offset) : child._key === endChildKey ? text = text + child.text.slice(0, forwardSelection.focus.offset) : text = text + child.text), child._key === endChildKey))
408
- break;
409
- continue;
410
- }
411
- if (block._key === endBlockKey) {
412
- if (!isPortableTextTextBlock(block))
413
- continue;
414
- for (const child of block.children)
415
- if (isPortableTextSpan(child) && endChildKey && (text = text + child.text.slice(0, forwardSelection.focus.offset)), child._key === endChildKey)
416
- break;
417
- break;
418
- }
419
- }
420
- return text;
421
- }, isSelectionCollapsed = ({
274
+ }) => sliceBlocks({
275
+ blocks: context.value,
276
+ selection: context.selection
277
+ }), getSelectionText = ({
278
+ context
279
+ }) => getSelectedSlice({
280
+ context
281
+ }).reduce((text, block) => isPortableTextTextBlock(block) ? text + block.children.reduce((text2, child) => isPortableTextSpan(child) ? text2 + child.text : text2, "") : text, ""), isSelectionCollapsed = ({
422
282
  context
423
283
  }) => context.selection ? JSON.stringify(context.selection.anchor.path) === JSON.stringify(context.selection.focus.path) && context.selection?.anchor.offset === context.selection?.focus.offset : !1, isSelectionExpanded = ({
424
284
  context
@@ -498,35 +358,6 @@ const getSelectedSpans = ({
498
358
  }
499
359
  }) ? caretWordSelection : null;
500
360
  };
501
- function isActiveAnnotation(annotation) {
502
- return (snapshot) => {
503
- if (!snapshot.context.selection)
504
- return !1;
505
- const selectedBlocks = getSelectedBlocks(snapshot), focusSpan = getFocusSpan(snapshot), selectedSpans = isSelectionExpanded(snapshot) ? getSelectedSpans(snapshot) : focusSpan ? [focusSpan] : [];
506
- if (selectedSpans.length === 0 || selectedSpans.some((span) => !span.node.marks || span.node.marks?.length === 0))
507
- return !1;
508
- const selectionMarkDefs = selectedBlocks.flatMap((block) => isPortableTextTextBlock(block.node) ? block.node.markDefs ?? [] : []);
509
- return selectedSpans.every((span) => (span.node.marks?.flatMap((mark) => {
510
- const markDef = selectionMarkDefs.find((markDef2) => markDef2._key === mark);
511
- return markDef ? [markDef._type] : [];
512
- }) ?? []).includes(annotation));
513
- };
514
- }
515
- function isActiveDecorator(decorator) {
516
- return (snapshot) => {
517
- if (isSelectionExpanded(snapshot)) {
518
- const selectedSpans = getSelectedSpans(snapshot);
519
- return selectedSpans.length > 0 && selectedSpans.every((span) => span.node.marks?.includes(decorator));
520
- }
521
- return snapshot.context.activeDecorators.includes(decorator);
522
- };
523
- }
524
- function isActiveListItem(listItem) {
525
- return (snapshot) => getActiveListItem(snapshot) === listItem;
526
- }
527
- function isActiveStyle(style) {
528
- return (snapshot) => getActiveStyle(snapshot) === style;
529
- }
530
361
  function isAtTheEndOfBlock(block) {
531
362
  return ({
532
363
  context
@@ -553,8 +384,6 @@ function isAtTheStartOfBlock(block) {
553
384
  }
554
385
  export {
555
386
  createGuards,
556
- getActiveListItem,
557
- getActiveStyle,
558
387
  getCaretWordSelection,
559
388
  getFirstBlock,
560
389
  getFocusBlock,
@@ -569,16 +398,12 @@ export {
569
398
  getPreviousBlock,
570
399
  getPreviousInlineObject,
571
400
  getSelectedBlocks,
572
- getSelectedSpans,
401
+ getSelectedSlice,
573
402
  getSelectionEndBlock,
574
403
  getSelectionEndPoint,
575
404
  getSelectionStartBlock,
576
405
  getSelectionStartPoint,
577
406
  getSelectionText,
578
- isActiveAnnotation,
579
- isActiveDecorator,
580
- isActiveListItem,
581
- isActiveStyle,
582
407
  isAtTheEndOfBlock,
583
408
  isAtTheStartOfBlock,
584
409
  isSelectionCollapsed,