From 28808d0dfd8004c862d88fbc9dea148f12fdc824 Mon Sep 17 00:00:00 2001 From: zbeyens Date: Tue, 24 Jan 2023 03:31:55 +0100 Subject: [PATCH 1/7] fix --- .../createEditorProtocolPlugin.spec.tsx | 99 +++++++++++++++++++ .../src/plugins/createEditorProtocolPlugin.ts | 74 ++++++++++++++ 2 files changed, 173 insertions(+) create mode 100644 packages/core/src/plugins/createEditorProtocolPlugin.spec.tsx create mode 100644 packages/core/src/plugins/createEditorProtocolPlugin.ts diff --git a/packages/core/src/plugins/createEditorProtocolPlugin.spec.tsx b/packages/core/src/plugins/createEditorProtocolPlugin.spec.tsx new file mode 100644 index 0000000000..029662ed77 --- /dev/null +++ b/packages/core/src/plugins/createEditorProtocolPlugin.spec.tsx @@ -0,0 +1,99 @@ +/** @jsx jsx */ + +import { jsx } from '@udecode/plate-test-utils'; +import { createPlateEditor } from '../utils/index'; + +jsx; + +// https://github.com/udecode/editor-protocol/issues/81 +describe('delete marked text at block start', () => { + it('delete backward in a marked text at offset 1, it should remove the mark', () => { + const input = ( + + + + a + bc + + + + ) as any; + + const output = ( + + + abc + + + ) as any; + + const editor = createPlateEditor({ + editor: input, + }); + + editor.deleteBackward('character'); + editor.insertText('a'); + + expect(editor.children).toEqual(output.children); + }); + + it('when delete forward at start of a marked block, it should remove the mark', () => { + const input = ( + + + + + abc + + + + ) as any; + + const output = ( + + + abc + + + ) as any; + + const editor = createPlateEditor({ + editor: input, + }); + + editor.deleteForward('character'); + editor.insertText('a'); + + expect(editor.children).toEqual(output.children); + }); + + it('when delete fragment with anchor or focus at start of a marked block, should remove the mark', () => { + const input = ( + + + + bc + + + + ) as any; + + const output = ( + + + b + c + + + ) as any; + + const editor = createPlateEditor({ + editor: input, + }); + + editor.deleteBackward('character'); + editor.insertText('b'); + + expect(editor.children).toEqual(output.children); + }); +}); diff --git a/packages/core/src/plugins/createEditorProtocolPlugin.ts b/packages/core/src/plugins/createEditorProtocolPlugin.ts new file mode 100644 index 0000000000..afe90111a1 --- /dev/null +++ b/packages/core/src/plugins/createEditorProtocolPlugin.ts @@ -0,0 +1,74 @@ +import { getBlockAbove, isSelectionAtBlockStart } from '../queries/index'; +import { getMarks, isExpanded, isStartPoint, Value } from '../slate/index'; +import { removeMark } from '../transforms/index'; +import { PlateEditor } from '../types/index'; +import { createPluginFactory } from '../utils/plate/createPluginFactory'; + +export const KEY_EDITOR_PROTOCOL = 'editorProtocol'; + +export const withEditorProtocol = < + V extends Value = Value, + E extends PlateEditor = PlateEditor +>( + editor: E +) => { + const { deleteBackward, deleteForward, deleteFragment } = editor; + + const resetMarks = () => { + // move to isSelectionAtBlockStart + const path = getBlockAbove(editor)?.[1]; + if (!path) return; + + let isAtBlockStart = isStartPoint(editor, editor.selection?.focus, path); + isAtBlockStart = + isAtBlockStart || + (isExpanded(editor.selection) && + isStartPoint(editor, editor.selection?.anchor, path)); + + if (isAtBlockStart) { + const marks = getMarks(editor); + + if (marks) { + // remove all marks + removeMark(editor, { + key: Object.keys(marks) as any, + }); + } + } + }; + + editor.deleteBackward = (unit) => { + deleteBackward(unit); + + resetMarks(); + }; + + editor.deleteForward = (unit) => { + deleteForward(unit); + + resetMarks(); + }; + + editor.deleteFragment = (direction) => { + deleteFragment(direction); + + if (isSelectionAtBlockStart(editor)) { + const marks = getMarks(editor); + + if (marks) { + // remove all marks + removeMark(editor, { + key: Object.keys(marks) as any, + }); + } + } + resetMarks(); + }; + + return editor; +}; + +export const createEditorProtocolPlugin = createPluginFactory({ + key: KEY_EDITOR_PROTOCOL, + withOverrides: withEditorProtocol, +}); From dff1cc69facc1716a52d50a2a9a40b51da6949a4 Mon Sep 17 00:00:00 2001 From: zbeyens Date: Tue, 24 Jan 2023 03:32:23 +0100 Subject: [PATCH 2/7] fix --- .../core/src/hooks/plate/usePlateEffects.ts | 1 + packages/core/src/plugins/index.ts | 1 + packages/core/src/plugins/withPlate.spec.ts | 2 ++ packages/core/src/queries/getMark.ts | 10 +++------- packages/core/src/queries/isMarkActive.ts | 5 ++--- packages/core/src/slate/editor/addMark.ts | 13 ++++-------- packages/core/src/slate/editor/getMarks.ts | 2 +- .../core/src/slate/editor/removeEditorMark.ts | 7 +++---- packages/core/src/slate/text/TText.ts | 2 +- packages/core/src/transforms/index.ts | 1 + packages/core/src/transforms/removeMark.ts | 15 ++++++-------- .../src/transforms/removeSelectionMark.ts | 1 + packages/core/src/transforms/setMarks.ts | 12 +++++------ packages/core/src/transforms/toggleMark.ts | 20 +++++++------------ .../core/src/types/plugin/ToggleMarkPlugin.ts | 9 +++------ .../core/src/utils/plate/setPlatePlugins.ts | 10 ++++++++++ packages/nodes/table/src/withDeleteTable.ts | 4 ++-- .../ColorPickerToolbarDropdown.tsx | 2 +- 18 files changed, 55 insertions(+), 62 deletions(-) create mode 100644 packages/core/src/transforms/removeSelectionMark.ts diff --git a/packages/core/src/hooks/plate/usePlateEffects.ts b/packages/core/src/hooks/plate/usePlateEffects.ts index 75bcda2904..ecb523d643 100644 --- a/packages/core/src/hooks/plate/usePlateEffects.ts +++ b/packages/core/src/hooks/plate/usePlateEffects.ts @@ -24,6 +24,7 @@ export type UsePlateEffectsProps< | { deserializeAst?: boolean; deserializeHtml?: boolean; + editorProtocol?: boolean; eventEditor?: boolean; inlineVoid?: boolean; insertData?: boolean; diff --git a/packages/core/src/plugins/index.ts b/packages/core/src/plugins/index.ts index a7dc9643ac..9de4792fe3 100644 --- a/packages/core/src/plugins/index.ts +++ b/packages/core/src/plugins/index.ts @@ -3,6 +3,7 @@ */ export * from './createDeserializeAstPlugin'; +export * from './createEditorProtocolPlugin'; export * from './createEventEditorPlugin'; export * from './createHistoryPlugin'; export * from './createInlineVoidPlugin'; diff --git a/packages/core/src/plugins/withPlate.spec.ts b/packages/core/src/plugins/withPlate.spec.ts index fe94c5c227..01596ab652 100644 --- a/packages/core/src/plugins/withPlate.spec.ts +++ b/packages/core/src/plugins/withPlate.spec.ts @@ -5,6 +5,7 @@ import { getPlugin } from '../utils/plate/getPlugin'; import { createTEditor } from '../utils/slate/createTEditor'; import { KEY_DESERIALIZE_HTML } from './html-deserializer/createDeserializeHtmlPlugin'; import { KEY_DESERIALIZE_AST } from './createDeserializeAstPlugin'; +import { KEY_EDITOR_PROTOCOL } from './createEditorProtocolPlugin'; import { KEY_EVENT_EDITOR } from './createEventEditorPlugin'; import { KEY_INLINE_VOID } from './createInlineVoidPlugin'; import { KEY_INSERT_DATA } from './createInsertDataPlugin'; @@ -22,6 +23,7 @@ const coreKeys = [ KEY_PREV_SELECTION, KEY_DESERIALIZE_HTML, KEY_DESERIALIZE_AST, + KEY_EDITOR_PROTOCOL, ]; describe('withPlate', () => { diff --git a/packages/core/src/queries/getMark.ts b/packages/core/src/queries/getMark.ts index f14f833ef8..d428edcd59 100644 --- a/packages/core/src/queries/getMark.ts +++ b/packages/core/src/queries/getMark.ts @@ -1,17 +1,13 @@ import { getMarks } from '../slate/editor/getMarks'; import { TEditor, Value } from '../slate/editor/TEditor'; -import { EMarks } from '../slate/text/TText'; /** - * Get selected mark by type. + * Get selection mark value by key. */ -export const getMark = >( - editor: TEditor, - type: K -) => { +export const getMark = (editor: TEditor, key: string) => { if (!editor) return; const marks = getMarks(editor); - return marks?.[type] as K | undefined; + return marks?.[key] as unknown; }; diff --git a/packages/core/src/queries/isMarkActive.ts b/packages/core/src/queries/isMarkActive.ts index e4a5655160..8b38986ebd 100644 --- a/packages/core/src/queries/isMarkActive.ts +++ b/packages/core/src/queries/isMarkActive.ts @@ -1,14 +1,13 @@ import { TEditor, Value } from '../slate/editor/TEditor'; -import { EMarks } from '../slate/text/TText'; import { isDefined } from '../utils/misc/type-utils'; import { getMark } from './getMark'; /** * Is the mark defined in the selection. */ -export const isMarkActive = >( +export const isMarkActive = ( editor: TEditor, - type: K + type: string ) => { return isDefined(getMark(editor, type)); }; diff --git a/packages/core/src/slate/editor/addMark.ts b/packages/core/src/slate/editor/addMark.ts index 614ef939b0..576688ae8c 100644 --- a/packages/core/src/slate/editor/addMark.ts +++ b/packages/core/src/slate/editor/addMark.ts @@ -1,5 +1,4 @@ import { Editor } from 'slate'; -import { EMarks } from '../text/TText'; import { TEditor, Value } from './TEditor'; /** @@ -8,12 +7,8 @@ import { TEditor, Value } from './TEditor'; * If the selection is currently collapsed, the marks will be added to the * `editor.marks` property instead, and applied when text is inserted next. */ -export const addMark = < - V extends Value, - M extends EMarks, - K extends keyof M & string ->( +export const addMark = ( editor: TEditor, - key: {} extends M ? string : K, - value: {} extends M ? unknown : M[K] -): void => Editor.addMark(editor as any, key, value); + key: string, + value: any +) => Editor.addMark(editor as any, key, value); diff --git a/packages/core/src/slate/editor/getMarks.ts b/packages/core/src/slate/editor/getMarks.ts index f70a6d454a..144532fba8 100644 --- a/packages/core/src/slate/editor/getMarks.ts +++ b/packages/core/src/slate/editor/getMarks.ts @@ -6,4 +6,4 @@ import { TEditor, Value } from './TEditor'; * Get the marks that would be added to text at the current selection. */ export const getMarks = (editor: TEditor) => - Editor.marks(editor as any) as Partial> | null; + Editor.marks(editor as any) as EMarks | null; diff --git a/packages/core/src/slate/editor/removeEditorMark.ts b/packages/core/src/slate/editor/removeEditorMark.ts index eaa263fc87..c1f33d1023 100644 --- a/packages/core/src/slate/editor/removeEditorMark.ts +++ b/packages/core/src/slate/editor/removeEditorMark.ts @@ -1,5 +1,4 @@ import { Editor } from 'slate'; -import { EMarks } from '../text/TText'; import { TEditor, Value } from './TEditor'; /** @@ -9,7 +8,7 @@ import { TEditor, Value } from './TEditor'; * If the selection is currently collapsed, the removal will be stored on * `editor.marks` and applied to the text inserted next. */ -export const removeEditorMark = >( +export const removeEditorMark = ( editor: TEditor, - key: {} extends M ? string : keyof M & string -): void => Editor.removeMark(editor as any, key); + key: string +) => Editor.removeMark(editor as any, key); diff --git a/packages/core/src/slate/text/TText.ts b/packages/core/src/slate/text/TText.ts index b39e2d225c..dfd85dea76 100644 --- a/packages/core/src/slate/text/TText.ts +++ b/packages/core/src/slate/text/TText.ts @@ -1,5 +1,5 @@ +import { Simplify, UnionToIntersection } from '../../types/index'; import { UnknownObject } from '../../types/misc/AnyObject'; -import { Simplify, UnionToIntersection } from '../../types/misc/types'; import { TEditor, Value } from '../editor/TEditor'; import { TElement } from '../element/TElement'; import { TNode, TNodeProps } from '../node/TNode'; diff --git a/packages/core/src/transforms/index.ts b/packages/core/src/transforms/index.ts index b807d5b697..870d19fdb6 100644 --- a/packages/core/src/transforms/index.ts +++ b/packages/core/src/transforms/index.ts @@ -8,6 +8,7 @@ export * from './insertEmptyElement'; export * from './moveChildren'; export * from './removeMark'; export * from './removeNodeChildren'; +export * from './removeSelectionMark'; export * from './replaceNodeChildren'; export * from './resetEditorChildren'; export * from './selectEditor'; diff --git a/packages/core/src/transforms/removeMark.ts b/packages/core/src/transforms/removeMark.ts index 3dad12d54b..9342616fc3 100644 --- a/packages/core/src/transforms/removeMark.ts +++ b/packages/core/src/transforms/removeMark.ts @@ -3,18 +3,15 @@ import { Range } from 'slate'; import { getMarks } from '../slate/editor/getMarks'; import { TEditor, Value } from '../slate/editor/TEditor'; import { isText } from '../slate/text/isText'; -import { EMarks } from '../slate/text/TText'; import { SetNodesOptions } from '../slate/transforms/setNodes'; import { unsetNodes } from '../slate/transforms/unsetNodes'; -export interface RemoveMarkOptions< - V extends Value = Value, - K extends keyof EMarks = keyof EMarks -> extends Omit, 'match' | 'split'> { +export interface RemoveMarkOptions + extends Omit, 'match' | 'split'> { /** * Mark or the array of marks that will be removed */ - key: K | K[]; + key: string | string[]; /** * When location is not a Range, @@ -32,9 +29,9 @@ export interface RemoveMarkOptions< /** * Remove mark and trigger `onChange` if collapsed selection. */ -export const removeMark = >( +export const removeMark = ( editor: TEditor, - { key, at, shouldChange = true, ...rest }: RemoveMarkOptions + { key, at, shouldChange = true, ...rest }: RemoveMarkOptions ) => { const selection = at ?? editor.selection; key = castArray(key); @@ -48,7 +45,7 @@ export const removeMark = >( ...rest, }); } else if (editor.selection) { - const marks: Partial> = { ...(getMarks(editor) || {}) }; + const marks = getMarks(editor) ?? {}; key.forEach((k) => { delete marks[k]; }); diff --git a/packages/core/src/transforms/removeSelectionMark.ts b/packages/core/src/transforms/removeSelectionMark.ts new file mode 100644 index 0000000000..666602c822 --- /dev/null +++ b/packages/core/src/transforms/removeSelectionMark.ts @@ -0,0 +1 @@ +export const removeSelectionMark = () => {}; diff --git a/packages/core/src/transforms/setMarks.ts b/packages/core/src/transforms/setMarks.ts index 743403f21a..e7ebc6501f 100644 --- a/packages/core/src/transforms/setMarks.ts +++ b/packages/core/src/transforms/setMarks.ts @@ -1,23 +1,23 @@ import castArray from 'lodash/castArray'; import { TEditor, Value } from '../slate/editor/TEditor'; import { withoutNormalizing } from '../slate/editor/withoutNormalizing'; -import { EMarks } from '../slate/text/TText'; +import { EMarks } from '../slate/index'; import { removeMark } from './removeMark'; /** * Set marks to selected text. */ -export const setMarks = >( +export const setMarks = ( editor: TEditor, - marks: Record, - clear: K | K[] = [] + marks: EMarks, + clear: string | string[] = [] ) => { if (!editor.selection) return; withoutNormalizing(editor, () => { - const clears: K[] = castArray(clear); + const clears = castArray(clear); removeMark(editor, { key: clears }); - removeMark(editor, { key: Object.keys(marks) as K[] }); + removeMark(editor, { key: Object.keys(marks) }); Object.keys(marks).forEach((key) => { editor.addMark(key, marks[key]); diff --git a/packages/core/src/transforms/toggleMark.ts b/packages/core/src/transforms/toggleMark.ts index acad87dd68..75ee6dcb98 100644 --- a/packages/core/src/transforms/toggleMark.ts +++ b/packages/core/src/transforms/toggleMark.ts @@ -2,15 +2,12 @@ import castArray from 'lodash/castArray'; import { isMarkActive } from '../queries/isMarkActive'; import { TEditor, Value } from '../slate/editor/TEditor'; import { withoutNormalizing } from '../slate/editor/withoutNormalizing'; -import { EMarks } from '../slate/text/TText'; import { ToggleMarkPlugin } from '../types/plugin/ToggleMarkPlugin'; import { removeMark } from './removeMark'; -export interface ToggleMarkOptions< - V extends Value = Value, - K extends keyof EMarks = keyof EMarks -> extends Pick, 'clear'> { - key: K; +export interface ToggleMarkOptions + extends Pick, 'clear'> { + key: string; } /** @@ -19,12 +16,9 @@ export interface ToggleMarkOptions< * @param key mark to toggle * @param clear marks to clear when adding mark */ -export const toggleMark = < - V extends Value = Value, - K extends keyof EMarks = keyof EMarks ->( +export const toggleMark = ( editor: TEditor, - { key, clear }: ToggleMarkOptions + { key, clear }: ToggleMarkOptions ) => { if (!editor.selection) return; @@ -37,10 +31,10 @@ export const toggleMark = < } if (clear) { - const clears: K[] = castArray(clear); + const clears = castArray(clear); removeMark(editor, { key: clears }); } - editor.addMark(key as string, true); + editor.addMark(key, true); }); }; diff --git a/packages/core/src/types/plugin/ToggleMarkPlugin.ts b/packages/core/src/types/plugin/ToggleMarkPlugin.ts index d9147bc78f..512e741d4b 100644 --- a/packages/core/src/types/plugin/ToggleMarkPlugin.ts +++ b/packages/core/src/types/plugin/ToggleMarkPlugin.ts @@ -1,13 +1,10 @@ import { Value } from '../../slate/editor/TEditor'; -import { EMarks } from '../../slate/text/TText'; import { HotkeyPlugin } from './HotkeyPlugin'; -export interface ToggleMarkPlugin< - V extends Value = Value, - K extends keyof EMarks = keyof EMarks -> extends HotkeyPlugin { +export interface ToggleMarkPlugin + extends HotkeyPlugin { /** * Node properties to delete. */ - clear?: K | K[]; + clear?: string | string[]; } diff --git a/packages/core/src/utils/plate/setPlatePlugins.ts b/packages/core/src/utils/plate/setPlatePlugins.ts index e44e415860..2f611a41e9 100644 --- a/packages/core/src/utils/plate/setPlatePlugins.ts +++ b/packages/core/src/utils/plate/setPlatePlugins.ts @@ -3,6 +3,10 @@ import { createDeserializeAstPlugin, KEY_DESERIALIZE_AST, } from '../../plugins/createDeserializeAstPlugin'; +import { + createEditorProtocolPlugin, + KEY_EDITOR_PROTOCOL, +} from '../../plugins/createEditorProtocolPlugin'; import { createEventEditorPlugin, KEY_EVENT_EDITOR, @@ -103,6 +107,12 @@ export const setPlatePlugins = < createDeserializeAstPlugin() ); } + if (typeof dcp !== 'object' || !dcp?.editorProtocol) { + plugins.push( + (editor?.pluginsByKey?.[KEY_EDITOR_PROTOCOL] as any) ?? + createEditorProtocolPlugin() + ); + } } plugins = [...plugins, ..._plugins] as any; diff --git a/packages/nodes/table/src/withDeleteTable.ts b/packages/nodes/table/src/withDeleteTable.ts index 8b5d461413..3ab2840b29 100644 --- a/packages/nodes/table/src/withDeleteTable.ts +++ b/packages/nodes/table/src/withDeleteTable.ts @@ -93,7 +93,7 @@ export const withDeleteTable = < return deleteForward(unit); }; - editor.deleteFragment = () => { + editor.deleteFragment = (direction) => { isRangeInSameBlock(editor, { match: (n) => n.type === getPluginType(editor, ELEMENT_TABLE), }); @@ -124,7 +124,7 @@ export const withDeleteTable = < } } - deleteFragment(); + deleteFragment(direction); }; return editor; diff --git a/packages/ui/nodes/font/src/ColorPickerToolbarDropdown/ColorPickerToolbarDropdown.tsx b/packages/ui/nodes/font/src/ColorPickerToolbarDropdown/ColorPickerToolbarDropdown.tsx index c21d1c8fa0..3c509060e0 100644 --- a/packages/ui/nodes/font/src/ColorPickerToolbarDropdown/ColorPickerToolbarDropdown.tsx +++ b/packages/ui/nodes/font/src/ColorPickerToolbarDropdown/ColorPickerToolbarDropdown.tsx @@ -47,7 +47,7 @@ export const ColorPickerToolbarDropdown = ({ const type = getPluginType(editorRef, pluginKey); - const color = editorRef && getMark(editorRef, type); + const color = editorRef && (getMark(editorRef, type) as string); const [selectedColor, setSelectedColor] = useState(); From 49f96fa01a649f71b95fb58570cae25fcdce7f39 Mon Sep 17 00:00:00 2001 From: zbeyens Date: Tue, 24 Jan 2023 03:37:44 +0100 Subject: [PATCH 3/7] fix --- .../core/src/plugins/createEditorProtocolPlugin.ts | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/packages/core/src/plugins/createEditorProtocolPlugin.ts b/packages/core/src/plugins/createEditorProtocolPlugin.ts index afe90111a1..1aeeef4c1f 100644 --- a/packages/core/src/plugins/createEditorProtocolPlugin.ts +++ b/packages/core/src/plugins/createEditorProtocolPlugin.ts @@ -1,4 +1,4 @@ -import { getBlockAbove, isSelectionAtBlockStart } from '../queries/index'; +import { getBlockAbove } from '../queries/index'; import { getMarks, isExpanded, isStartPoint, Value } from '../slate/index'; import { removeMark } from '../transforms/index'; import { PlateEditor } from '../types/index'; @@ -52,16 +52,6 @@ export const withEditorProtocol = < editor.deleteFragment = (direction) => { deleteFragment(direction); - if (isSelectionAtBlockStart(editor)) { - const marks = getMarks(editor); - - if (marks) { - // remove all marks - removeMark(editor, { - key: Object.keys(marks) as any, - }); - } - } resetMarks(); }; From b174ffcd9dd176d054ee377afe15a62e6a6863c8 Mon Sep 17 00:00:00 2001 From: Ziad Beyens Date: Tue, 24 Jan 2023 03:47:37 +0100 Subject: [PATCH 4/7] Create hungry-radios-fly.md --- .changeset/hungry-radios-fly.md | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 .changeset/hungry-radios-fly.md diff --git a/.changeset/hungry-radios-fly.md b/.changeset/hungry-radios-fly.md new file mode 100644 index 0000000000..8cd9ca5b84 --- /dev/null +++ b/.changeset/hungry-radios-fly.md @@ -0,0 +1,7 @@ +--- +"@udecode/plate-core": minor +--- + +- New core plugin: `editorProtocol` following https://github.com/udecode/editor-protocol core specs + - Fixes https://github.com/udecode/editor-protocol/issues/81 +- Slate types: replaced editor mark types by `string`. Derived types from `EMarks` are often unusable. From b93e6ff6670e2fcba4578784f10b68791cd1c0ad Mon Sep 17 00:00:00 2001 From: Ziad Beyens Date: Tue, 24 Jan 2023 03:49:25 +0100 Subject: [PATCH 5/7] Create hungry-radios-flya.md --- .changeset/hungry-radios-flya.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/hungry-radios-flya.md diff --git a/.changeset/hungry-radios-flya.md b/.changeset/hungry-radios-flya.md new file mode 100644 index 0000000000..fc51665505 --- /dev/null +++ b/.changeset/hungry-radios-flya.md @@ -0,0 +1,5 @@ +--- +"@udecode/plate-table": patch +--- + +fix: pass `deleteFragment` params From f708db8e6a2f8726d90e82566fe6d9dd63eaa739 Mon Sep 17 00:00:00 2001 From: zbeyens Date: Tue, 24 Jan 2023 03:50:14 +0100 Subject: [PATCH 6/7] fix --- .../src/plugins/createEditorProtocolPlugin.ts | 27 ++++--------------- .../src/queries/isSelectionAtBlockStart.ts | 13 +++++++-- .../src/transforms/removeSelectionMark.ts | 18 ++++++++++++- 3 files changed, 33 insertions(+), 25 deletions(-) diff --git a/packages/core/src/plugins/createEditorProtocolPlugin.ts b/packages/core/src/plugins/createEditorProtocolPlugin.ts index 1aeeef4c1f..fc3e8f996b 100644 --- a/packages/core/src/plugins/createEditorProtocolPlugin.ts +++ b/packages/core/src/plugins/createEditorProtocolPlugin.ts @@ -1,6 +1,6 @@ -import { getBlockAbove } from '../queries/index'; -import { getMarks, isExpanded, isStartPoint, Value } from '../slate/index'; -import { removeMark } from '../transforms/index'; +import { isSelectionAtBlockStart } from '../queries/index'; +import { Value } from '../slate/index'; +import { removeSelectionMark } from '../transforms/index'; import { PlateEditor } from '../types/index'; import { createPluginFactory } from '../utils/plate/createPluginFactory'; @@ -15,25 +15,8 @@ export const withEditorProtocol = < const { deleteBackward, deleteForward, deleteFragment } = editor; const resetMarks = () => { - // move to isSelectionAtBlockStart - const path = getBlockAbove(editor)?.[1]; - if (!path) return; - - let isAtBlockStart = isStartPoint(editor, editor.selection?.focus, path); - isAtBlockStart = - isAtBlockStart || - (isExpanded(editor.selection) && - isStartPoint(editor, editor.selection?.anchor, path)); - - if (isAtBlockStart) { - const marks = getMarks(editor); - - if (marks) { - // remove all marks - removeMark(editor, { - key: Object.keys(marks) as any, - }); - } + if (isSelectionAtBlockStart(editor)) { + removeSelectionMark(editor); } }; diff --git a/packages/core/src/queries/isSelectionAtBlockStart.ts b/packages/core/src/queries/isSelectionAtBlockStart.ts index ecfd26b261..73aa32b872 100644 --- a/packages/core/src/queries/isSelectionAtBlockStart.ts +++ b/packages/core/src/queries/isSelectionAtBlockStart.ts @@ -1,10 +1,11 @@ import { GetAboveNodeOptions } from '../slate/editor/getAboveNode'; import { isStartPoint } from '../slate/editor/isStartPoint'; import { TEditor, Value } from '../slate/editor/TEditor'; +import { isExpanded } from '../slate/index'; import { getBlockAbove } from './getBlockAbove'; /** - * Is the selection focus at the start of its parent block. + * Is the selection anchor or focus at the start of its parent block. * * Supports the same options provided by {@link getBlockAbove}. */ @@ -12,7 +13,15 @@ export const isSelectionAtBlockStart = ( editor: TEditor, options?: GetAboveNodeOptions ) => { + const { selection } = editor; + if (!selection) return; + const path = getBlockAbove(editor, options)?.[1]; + if (!path) return false; - return !!path && isStartPoint(editor, editor.selection?.focus, path); + return ( + isStartPoint(editor, selection.focus, path) || + (isExpanded(editor.selection) && + isStartPoint(editor, selection.anchor, path)) + ); }; diff --git a/packages/core/src/transforms/removeSelectionMark.ts b/packages/core/src/transforms/removeSelectionMark.ts index 666602c822..22f1730e47 100644 --- a/packages/core/src/transforms/removeSelectionMark.ts +++ b/packages/core/src/transforms/removeSelectionMark.ts @@ -1 +1,17 @@ -export const removeSelectionMark = () => {}; +import { getMarks, TEditor, Value } from '../slate/index'; +import { removeMark } from './removeMark'; + +/** + * Remove selection marks. + */ +export const removeSelectionMark = ( + editor: TEditor +) => { + const marks = getMarks(editor); + if (!marks) return; + + // remove all marks + removeMark(editor, { + key: Object.keys(marks), + }); +}; From 7ce3de4e2d0e1037a1cc1fd14f5487f3da5c66bb Mon Sep 17 00:00:00 2001 From: zbeyens Date: Tue, 24 Jan 2023 03:59:42 +0100 Subject: [PATCH 7/7] fix --- packages/core/src/queries/isSelectionAtBlockStart.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/core/src/queries/isSelectionAtBlockStart.ts b/packages/core/src/queries/isSelectionAtBlockStart.ts index 73aa32b872..bba94243da 100644 --- a/packages/core/src/queries/isSelectionAtBlockStart.ts +++ b/packages/core/src/queries/isSelectionAtBlockStart.ts @@ -14,7 +14,7 @@ export const isSelectionAtBlockStart = ( options?: GetAboveNodeOptions ) => { const { selection } = editor; - if (!selection) return; + if (!selection) return false; const path = getBlockAbove(editor, options)?.[1]; if (!path) return false;