ElementNode,
LexicalEditor,
LexicalNode,
- ParagraphNode, SerializedElementNode, Spread
+ ParagraphNode, Spread
} from 'lexical';
import type {EditorConfig} from "lexical/LexicalEditor";
import type {RangeSelection} from "lexical/LexicalSelection";
+import {
+ CommonBlockAlignment, commonPropertiesDifferent, deserializeCommonBlockNode,
+ SerializedCommonBlockNode,
+ setCommonBlockPropsFromElement,
+ updateElementWithCommonBlockProps
+} from "./_common";
export type CalloutCategory = 'info' | 'danger' | 'warning' | 'success';
export type SerializedCalloutNode = Spread<{
category: CalloutCategory;
-}, SerializedElementNode>
-
-export class Callout extends ElementNode {
+}, SerializedCommonBlockNode>
+export class CalloutNode extends ElementNode {
+ __id: string = '';
__category: CalloutCategory = 'info';
+ __alignment: CommonBlockAlignment = '';
+ __inset: number = 0;
static getType() {
return 'callout';
}
- static clone(node: Callout) {
- return new Callout(node.__category, node.__key);
+ static clone(node: CalloutNode) {
+ const newNode = new CalloutNode(node.__category, node.__key);
+ newNode.__id = node.__id;
+ newNode.__alignment = node.__alignment;
+ newNode.__inset = node.__inset;
+ return newNode;
}
constructor(category: CalloutCategory, key?: string) {
this.__category = category;
}
+ setCategory(category: CalloutCategory) {
+ const self = this.getWritable();
+ self.__category = category;
+ }
+
+ getCategory(): CalloutCategory {
+ const self = this.getLatest();
+ return self.__category;
+ }
+
+ setId(id: string) {
+ const self = this.getWritable();
+ self.__id = id;
+ }
+
+ getId(): string {
+ const self = this.getLatest();
+ return self.__id;
+ }
+
+ setAlignment(alignment: CommonBlockAlignment) {
+ const self = this.getWritable();
+ self.__alignment = alignment;
+ }
+
+ getAlignment(): CommonBlockAlignment {
+ const self = this.getLatest();
+ return self.__alignment;
+ }
+
+ setInset(size: number) {
+ const self = this.getWritable();
+ self.__inset = size;
+ }
+
+ getInset(): number {
+ const self = this.getLatest();
+ return self.__inset;
+ }
+
createDOM(_config: EditorConfig, _editor: LexicalEditor) {
const element = document.createElement('p');
element.classList.add('callout', this.__category || '');
+ updateElementWithCommonBlockProps(element, this);
return element;
}
- updateDOM(prevNode: unknown, dom: HTMLElement) {
- // Returning false tells Lexical that this node does not need its
- // DOM element replacing with a new copy from createDOM.
- return false;
+ updateDOM(prevNode: CalloutNode): boolean {
+ return prevNode.__category !== this.__category ||
+ commonPropertiesDifferent(prevNode, this);
}
- insertNewAfter(selection: RangeSelection, restoreSelection?: boolean): Callout|ParagraphNode {
+ insertNewAfter(selection: RangeSelection, restoreSelection?: boolean): CalloutNode|ParagraphNode {
const anchorOffset = selection ? selection.anchor.offset : 0;
const newElement = anchorOffset === this.getTextContentSize() || !selection
? $createParagraphNode() : $createCalloutNode(this.__category);
}
}
+ const node = new CalloutNode(category);
+ setCommonBlockPropsFromElement(element, node);
+
return {
- node: new Callout(category),
+ node,
};
},
priority: 3,
type: 'callout',
version: 1,
category: this.__category,
+ id: this.__id,
+ alignment: this.__alignment,
+ inset: this.__inset,
};
}
- static importJSON(serializedNode: SerializedCalloutNode): Callout {
- return $createCalloutNode(serializedNode.category);
+ static importJSON(serializedNode: SerializedCalloutNode): CalloutNode {
+ const node = $createCalloutNode(serializedNode.category);
+ deserializeCommonBlockNode(serializedNode, node);
+ return node;
}
}
export function $createCalloutNode(category: CalloutCategory = 'info') {
- return new Callout(category);
+ return new CalloutNode(category);
+}
+
+export function $isCalloutNode(node: LexicalNode | null | undefined): node is CalloutNode {
+ return node instanceof CalloutNode;
}
-export function $isCalloutNode(node: LexicalNode | null | undefined) {
- return node instanceof Callout;
+export function $isCalloutNodeOfCategory(node: LexicalNode | null | undefined, category: CalloutCategory = 'info') {
+ return node instanceof CalloutNode && (node as CalloutNode).getCategory() === category;
}