UNPKG

@atlaskit/editor-plugin-synced-block

Version:

SyncedBlock plugin for @atlaskit/editor-core

45 lines • 1.99 kB
import { bind } from 'bind-event-listener'; import { SyncBlockSharedCssClassName } from '@atlaskit/editor-common/sync-block'; import { NodeSelection } from '@atlaskit/editor-prosemirror/state'; const getSelectedReference = view => { const selection = view.dom.ownerDocument.getSelection(); const anchor = selection === null || selection === void 0 ? void 0 : selection.anchorNode; const anchorElement = anchor instanceof Element ? anchor : anchor === null || anchor === void 0 ? void 0 : anchor.parentElement; const renderer = anchorElement === null || anchorElement === void 0 ? void 0 : anchorElement.closest(`.${SyncBlockSharedCssClassName.renderer}`); if (!renderer || !(selection !== null && selection !== void 0 && selection.focusNode) || !renderer.contains(selection.focusNode)) { return null; } const reference = renderer.closest(`.${SyncBlockSharedCssClassName.prefix}`); return reference && view.dom.contains(reference) ? reference : null; }; export const createReferenceSelectionView = view => { const syncReferenceSelection = () => { var _doc$nodeAt; if (!view.editable) { return; } const reference = getSelectedReference(view); if (!reference) { return; } const pos = view.posAtDOM(reference, 0); const { doc, schema, selection } = view.state; if (((_doc$nodeAt = doc.nodeAt(pos)) === null || _doc$nodeAt === void 0 ? void 0 : _doc$nodeAt.type) !== schema.nodes.syncBlock || selection instanceof NodeSelection && selection.from === pos) { return; } // The selectable renderer owns native focus, so PM's observer ignores its selection. // Track the containing atom without focusing the editor or clearing highlighted text. view.dispatch(view.state.tr.setSelection(NodeSelection.create(doc, pos))); }; const unbind = bind(view.dom.ownerDocument, { type: 'selectionchange', listener: syncReferenceSelection }); return { destroy: unbind }; };