X-Git-Url: http://source.bookstackapp.com/bookstack/blobdiff_plain/662110c269218807379546cc19c2292f5e3765de..refs/pull/5689/head:/resources/js/wysiwyg/utils/selection.ts diff --git a/resources/js/wysiwyg/utils/selection.ts b/resources/js/wysiwyg/utils/selection.ts index 2110ea4be..e4b5bf2dc 100644 --- a/resources/js/wysiwyg/utils/selection.ts +++ b/resources/js/wysiwyg/utils/selection.ts @@ -2,23 +2,21 @@ import { $createNodeSelection, $createParagraphNode, $createRangeSelection, $getRoot, - $getSelection, $isDecoratorNode, - $isElementNode, + $getSelection, $isBlockElementNode, $isDecoratorNode, + $isElementNode, $isParagraphNode, $isTextNode, $setSelection, BaseSelection, DecoratorNode, - ElementFormatType, ElementNode, LexicalEditor, LexicalNode, TextFormatType, TextNode } from "lexical"; -import {$findMatchingParent, $getNearestBlockElementAncestorOrThrow} from "@lexical/utils"; +import {$getNearestBlockElementAncestorOrThrow} from "@lexical/utils"; import {LexicalElementNodeCreator, LexicalNodeMatcher} from "../nodes"; import {$setBlocksType} from "@lexical/selection"; import {$getNearestNodeBlockParent, $getParentOfType, nodeHasAlignment} from "./nodes"; -import {$createCustomParagraphNode} from "../nodes/custom-paragraph"; -import {CommonBlockAlignment} from "../nodes/_common"; +import {CommonBlockAlignment} from "lexical/nodes/common"; const lastSelectionByEditor = new WeakMap; @@ -53,17 +51,28 @@ export function $getNodeFromSelection(selection: BaseSelection | null, matcher: return null; } +export function $getTextNodeFromSelection(selection: BaseSelection | null): TextNode|null { + return $getNodeFromSelection(selection, $isTextNode) as TextNode|null; +} + export function $selectionContainsTextFormat(selection: BaseSelection | null, format: TextFormatType): boolean { if (!selection) { return false; } - for (const node of selection.getNodes()) { + // Check text nodes + const nodes = selection.getNodes(); + for (const node of nodes) { if ($isTextNode(node) && node.hasFormat(format)) { return true; } } + // If we're in an empty paragraph, check the paragraph format + if (nodes.length === 1 && $isParagraphNode(nodes[0]) && nodes[0].hasTextFormat(format)) { + return true; + } + return false; } @@ -71,7 +80,7 @@ export function $toggleSelectionBlockNodeType(matcher: LexicalNodeMatcher, creat const selection = $getSelection(); const blockElement = selection ? $getNearestBlockElementAncestorOrThrow(selection.getNodes()[0]) : null; if (selection && matcher(blockElement)) { - $setBlocksType(selection, $createCustomParagraphNode); + $setBlocksType(selection, $createParagraphNode); } else { $setBlocksType(selection, creator); } @@ -82,8 +91,8 @@ export function $insertNewBlockNodeAtSelection(node: LexicalNode, insertAfter: b } export function $insertNewBlockNodesAtSelection(nodes: LexicalNode[], insertAfter: boolean = true) { - const selection = $getSelection(); - const blockElement = selection ? $getNearestBlockElementAncestorOrThrow(selection.getNodes()[0]) : null; + const selectionNodes = $getSelection()?.getNodes() || []; + const blockElement = selectionNodes.length > 0 ? $getNearestNodeBlockParent(selectionNodes[0]) : null; if (blockElement) { if (insertAfter) { @@ -199,6 +208,22 @@ export function $selectionContainsAlignment(selection: BaseSelection | null, ali return false; } +export function $selectionContainsDirection(selection: BaseSelection | null, direction: 'rtl'|'ltr'): boolean { + + const nodes = [ + ...(selection?.getNodes() || []), + ...$getBlockElementNodesInSelection(selection) + ]; + + for (const node of nodes) { + if ($isBlockElementNode(node) && node.getDirection() === direction) { + return true; + } + } + + return false; +} + export function $getBlockElementNodesInSelection(selection: BaseSelection | null): ElementNode[] { if (!selection) { return [];