@team-monolith/cds 0.30.2 → 0.31.0
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.
- package/dist/CodleDesignSystemProvider.d.ts +3 -0
- package/dist/patterns/LexicalEditor/LexicalEditor.d.ts +14 -0
- package/dist/patterns/LexicalEditor/LexicalEditor.js +39 -0
- package/dist/patterns/LexicalEditor/Plugins.d.ts +10 -0
- package/dist/patterns/LexicalEditor/Plugins.js +81 -0
- package/dist/patterns/LexicalEditor/hr.svg +3 -0
- package/dist/patterns/LexicalEditor/index.d.ts +1 -0
- package/dist/patterns/LexicalEditor/index.js +1 -0
- package/dist/patterns/LexicalEditor/nodes/ImageComponent.d.ts +18 -0
- package/dist/patterns/LexicalEditor/nodes/ImageComponent.js +143 -0
- package/dist/patterns/LexicalEditor/nodes/ImageNode.d.ts +56 -0
- package/dist/patterns/LexicalEditor/nodes/ImageNode.js +117 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/ComponentAdder.d.ts +10 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/ComponentAdder.js +68 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/ComponentAdderPlugin.d.ts +11 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/ComponentAdderPlugin.js +214 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/getContextMenuOptions.d.ts +6 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/getContextMenuOptions.js +90 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/index.d.ts +1 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/index.js +1 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/menu.svg +8 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/plus.svg +3 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/useDraggableBlockMenu.d.ts +16 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/useDraggableBlockMenu.js +234 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/useFloatingMenu.d.ts +20 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentAdderPlugin/useFloatingMenu.js +158 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuItem.d.ts +10 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuItem.js +40 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuList.d.ts +9 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuList.js +46 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuPlugin.d.ts +26 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/ComponentPickerMenuPlugin.js +174 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/index.d.ts +3 -0
- package/dist/patterns/LexicalEditor/plugins/ComponentPickerMenuPlugin/index.js +3 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingLinkEditorPlugin/FloatingLinkEditor.d.ts +11 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingLinkEditorPlugin/FloatingLinkEditor.js +201 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingLinkEditorPlugin/index.d.ts +6 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingLinkEditorPlugin/index.js +62 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingTextFormatToolbarPlugin/FloatingTextFormatPopup.d.ts +13 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingTextFormatToolbarPlugin/FloatingTextFormatPopup.js +60 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingTextFormatToolbarPlugin/index.d.ts +4 -0
- package/dist/patterns/LexicalEditor/plugins/FloatingTextFormatToolbarPlugin/index.js +190 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageDialog.d.ts +8 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageDialog.js +39 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageUploadedDialogBody.d.ts +6 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageUploadedDialogBody.js +49 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageUriDialogBody.d.ts +6 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/InsertImageUriDialogBody.js +24 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/index.d.ts +14 -0
- package/dist/patterns/LexicalEditor/plugins/ImagesPlugin/index.js +151 -0
- package/dist/patterns/LexicalEditor/plugins/ListMaxIndentLevelPlugin/index.d.ts +12 -0
- package/dist/patterns/LexicalEditor/plugins/ListMaxIndentLevelPlugin/index.js +49 -0
- package/dist/patterns/LexicalEditor/plugins/MarkdownTransformers/index.d.ts +12 -0
- package/dist/patterns/LexicalEditor/plugins/MarkdownTransformers/index.js +184 -0
- package/dist/patterns/LexicalEditor/theme.d.ts +24 -0
- package/dist/patterns/LexicalEditor/theme.js +178 -0
- package/dist/patterns/LexicalEditor/utils/getDOMRangeRect.d.ts +8 -0
- package/dist/patterns/LexicalEditor/utils/getDOMRangeRect.js +22 -0
- package/dist/patterns/LexicalEditor/utils/getSelectedNode.d.ts +2 -0
- package/dist/patterns/LexicalEditor/utils/getSelectedNode.js +24 -0
- package/dist/patterns/LexicalEditor/utils/guard.d.ts +8 -0
- package/dist/patterns/LexicalEditor/utils/guard.js +10 -0
- package/dist/patterns/LexicalEditor/utils/point.d.ts +21 -0
- package/dist/patterns/LexicalEditor/utils/point.js +41 -0
- package/dist/patterns/LexicalEditor/utils/rect.d.ts +45 -0
- package/dist/patterns/LexicalEditor/utils/rect.js +99 -0
- package/dist/patterns/LexicalEditor/utils/setFloatingElemPosition.d.ts +1 -0
- package/dist/patterns/LexicalEditor/utils/setFloatingElemPosition.js +36 -0
- package/dist/patterns/LexicalEditor/utils/setFloatingElemPositionForLinkEditor.d.ts +1 -0
- package/dist/patterns/LexicalEditor/utils/setFloatingElemPositionForLinkEditor.js +32 -0
- package/dist/patterns/LexicalEditor/utils/url.d.ts +9 -0
- package/dist/patterns/LexicalEditor/utils/url.js +34 -0
- package/dist/patterns/ReactEditorJS/ReactEditorJS.d.ts +2 -1
- package/dist/patterns/SegmentedControl/SegmentedControlButton.js +19 -6
- package/dist/patterns/SegmentedControl/SegmentedControlSquareButton.d.ts +1 -1
- package/dist/patterns/SegmentedControl/SegmentedControlSquareButton.js +35 -17
- package/package.json +4 -1
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { useState } from "react";
|
|
3
|
+
import styled from "@emotion/styled";
|
|
4
|
+
import { AlertDialogContent, AlertDialogActions } from "../../../../components/AlertDialog";
|
|
5
|
+
import Input from "../../../../components/Input";
|
|
6
|
+
import Button from "../../../../components/Button";
|
|
7
|
+
export function InsertImageUriDialogBody(props) {
|
|
8
|
+
const { onClick } = props;
|
|
9
|
+
const [src, setSrc] = useState("");
|
|
10
|
+
const [altText, setAltText] = useState("");
|
|
11
|
+
const isDisabled = src === "";
|
|
12
|
+
return (_jsxs(_Fragment, { children: [_jsx(AlertDialogContent, { children: _jsxs(Inputs, { children: [_jsx(Input, { fullWidth: true, label: "URL", placeholder: "https://source.unsplash.com/random", color: "default", size: "medium", onChange: (e) => {
|
|
13
|
+
setSrc(e.target.value);
|
|
14
|
+
}, value: src }), _jsx(Input, { fullWidth: true, label: "\uC124\uBA85", placeholder: "\uC774\uBBF8\uC9C0\uC5D0 \uB300\uD55C \uC124\uBA85", color: "default", size: "medium", onChange: (e) => {
|
|
15
|
+
setAltText(e.target.value);
|
|
16
|
+
}, value: altText })] }) }), _jsx(AlertDialogActions, { children: _jsx(Button, { label: "\uD655\uC778", size: "large", color: "primary", disabled: isDisabled, onClick: () => onClick({ altText, src }) }) })] }));
|
|
17
|
+
}
|
|
18
|
+
const Inputs = styled.div `
|
|
19
|
+
display: flex;
|
|
20
|
+
flex-direction: column;
|
|
21
|
+
gap: 20px;
|
|
22
|
+
margin-top: 20px;
|
|
23
|
+
margin-bottom: 10px;
|
|
24
|
+
`;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/// <reference types="react" />
|
|
2
|
+
import { LexicalCommand } from "lexical";
|
|
3
|
+
import { ImagePayload } from "../../nodes/ImageNode";
|
|
4
|
+
export type InsertImagePayload = Readonly<ImagePayload>;
|
|
5
|
+
export declare const INSERT_IMAGE_COMMAND: LexicalCommand<InsertImagePayload>;
|
|
6
|
+
export default function ImagesPlugin({ captionsEnabled, }: {
|
|
7
|
+
captionsEnabled?: boolean;
|
|
8
|
+
}): JSX.Element | null;
|
|
9
|
+
declare global {
|
|
10
|
+
interface DragEvent {
|
|
11
|
+
rangeOffset?: number;
|
|
12
|
+
rangeParent?: Node;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
import { useLexicalComposerContext } from "@lexical/react/LexicalComposerContext";
|
|
9
|
+
import { $wrapNodeInElement, mergeRegister } from "@lexical/utils";
|
|
10
|
+
import { $createParagraphNode, $createRangeSelection, $getSelection, $insertNodes, $isNodeSelection, $isRootOrShadowRoot, $setSelection, COMMAND_PRIORITY_EDITOR, COMMAND_PRIORITY_HIGH, COMMAND_PRIORITY_LOW, createCommand, DRAGOVER_COMMAND, DRAGSTART_COMMAND, DROP_COMMAND, } from "lexical";
|
|
11
|
+
import { useEffect } from "react";
|
|
12
|
+
import { $createImageNode, $isImageNode, ImageNode, } from "../../nodes/ImageNode";
|
|
13
|
+
const CAN_USE_DOM = typeof window !== "undefined" &&
|
|
14
|
+
typeof window.document !== "undefined" &&
|
|
15
|
+
typeof window.document.createElement !== "undefined";
|
|
16
|
+
const getDOMSelection = (targetWindow) => CAN_USE_DOM ? (targetWindow || window).getSelection() : null;
|
|
17
|
+
export const INSERT_IMAGE_COMMAND = createCommand("INSERT_IMAGE_COMMAND");
|
|
18
|
+
export default function ImagesPlugin({ captionsEnabled, }) {
|
|
19
|
+
const [editor] = useLexicalComposerContext();
|
|
20
|
+
useEffect(() => {
|
|
21
|
+
if (!editor.hasNodes([ImageNode])) {
|
|
22
|
+
throw new Error("ImagesPlugin: ImageNode not registered on editor");
|
|
23
|
+
}
|
|
24
|
+
return mergeRegister(editor.registerCommand(INSERT_IMAGE_COMMAND, (payload) => {
|
|
25
|
+
const imageNode = $createImageNode(payload);
|
|
26
|
+
$insertNodes([imageNode]);
|
|
27
|
+
if ($isRootOrShadowRoot(imageNode.getParentOrThrow())) {
|
|
28
|
+
$wrapNodeInElement(imageNode, $createParagraphNode).selectEnd();
|
|
29
|
+
}
|
|
30
|
+
return true;
|
|
31
|
+
}, COMMAND_PRIORITY_EDITOR), editor.registerCommand(DRAGSTART_COMMAND, (event) => {
|
|
32
|
+
return onDragStart(event);
|
|
33
|
+
}, COMMAND_PRIORITY_HIGH), editor.registerCommand(DRAGOVER_COMMAND, (event) => {
|
|
34
|
+
return onDragover(event);
|
|
35
|
+
}, COMMAND_PRIORITY_LOW), editor.registerCommand(DROP_COMMAND, (event) => {
|
|
36
|
+
return onDrop(event, editor);
|
|
37
|
+
}, COMMAND_PRIORITY_HIGH));
|
|
38
|
+
}, [captionsEnabled, editor]);
|
|
39
|
+
return null;
|
|
40
|
+
}
|
|
41
|
+
const TRANSPARENT_IMAGE = "data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7";
|
|
42
|
+
const img = document.createElement("img");
|
|
43
|
+
img.src = TRANSPARENT_IMAGE;
|
|
44
|
+
function onDragStart(event) {
|
|
45
|
+
const node = getImageNodeInSelection();
|
|
46
|
+
if (!node) {
|
|
47
|
+
return false;
|
|
48
|
+
}
|
|
49
|
+
const dataTransfer = event.dataTransfer;
|
|
50
|
+
if (!dataTransfer) {
|
|
51
|
+
return false;
|
|
52
|
+
}
|
|
53
|
+
dataTransfer.setData("text/plain", "_");
|
|
54
|
+
dataTransfer.setDragImage(img, 0, 0);
|
|
55
|
+
dataTransfer.setData("application/x-lexical-drag", JSON.stringify({
|
|
56
|
+
data: {
|
|
57
|
+
altText: node.__altText,
|
|
58
|
+
caption: node.__caption,
|
|
59
|
+
height: node.__height,
|
|
60
|
+
key: node.getKey(),
|
|
61
|
+
maxWidth: node.__maxWidth,
|
|
62
|
+
showCaption: node.__showCaption,
|
|
63
|
+
src: node.__src,
|
|
64
|
+
width: node.__width,
|
|
65
|
+
},
|
|
66
|
+
type: "image",
|
|
67
|
+
}));
|
|
68
|
+
return true;
|
|
69
|
+
}
|
|
70
|
+
function onDragover(event) {
|
|
71
|
+
const node = getImageNodeInSelection();
|
|
72
|
+
if (!node) {
|
|
73
|
+
return false;
|
|
74
|
+
}
|
|
75
|
+
if (!canDropImage(event)) {
|
|
76
|
+
event.preventDefault();
|
|
77
|
+
}
|
|
78
|
+
return true;
|
|
79
|
+
}
|
|
80
|
+
function onDrop(event, editor) {
|
|
81
|
+
const node = getImageNodeInSelection();
|
|
82
|
+
if (!node) {
|
|
83
|
+
return false;
|
|
84
|
+
}
|
|
85
|
+
const data = getDragImageData(event);
|
|
86
|
+
if (!data) {
|
|
87
|
+
return false;
|
|
88
|
+
}
|
|
89
|
+
event.preventDefault();
|
|
90
|
+
if (canDropImage(event)) {
|
|
91
|
+
const range = getDragSelection(event);
|
|
92
|
+
node.remove();
|
|
93
|
+
const rangeSelection = $createRangeSelection();
|
|
94
|
+
if (range !== null && range !== undefined) {
|
|
95
|
+
rangeSelection.applyDOMRange(range);
|
|
96
|
+
}
|
|
97
|
+
$setSelection(rangeSelection);
|
|
98
|
+
editor.dispatchCommand(INSERT_IMAGE_COMMAND, data);
|
|
99
|
+
}
|
|
100
|
+
return true;
|
|
101
|
+
}
|
|
102
|
+
function getImageNodeInSelection() {
|
|
103
|
+
const selection = $getSelection();
|
|
104
|
+
if (!$isNodeSelection(selection)) {
|
|
105
|
+
return null;
|
|
106
|
+
}
|
|
107
|
+
const nodes = selection.getNodes();
|
|
108
|
+
const node = nodes[0];
|
|
109
|
+
return $isImageNode(node) ? node : null;
|
|
110
|
+
}
|
|
111
|
+
function getDragImageData(event) {
|
|
112
|
+
var _a;
|
|
113
|
+
const dragData = (_a = event.dataTransfer) === null || _a === void 0 ? void 0 : _a.getData("application/x-lexical-drag");
|
|
114
|
+
if (!dragData) {
|
|
115
|
+
return null;
|
|
116
|
+
}
|
|
117
|
+
const { type, data } = JSON.parse(dragData);
|
|
118
|
+
if (type !== "image") {
|
|
119
|
+
return null;
|
|
120
|
+
}
|
|
121
|
+
return data;
|
|
122
|
+
}
|
|
123
|
+
function canDropImage(event) {
|
|
124
|
+
const target = event.target;
|
|
125
|
+
return !!(target &&
|
|
126
|
+
target instanceof HTMLElement &&
|
|
127
|
+
!target.closest("code, span.editor-image") &&
|
|
128
|
+
target.parentElement &&
|
|
129
|
+
target.parentElement.closest("div.ContentEditable__root"));
|
|
130
|
+
}
|
|
131
|
+
function getDragSelection(event) {
|
|
132
|
+
let range;
|
|
133
|
+
const target = event.target;
|
|
134
|
+
const targetWindow = target == null
|
|
135
|
+
? null
|
|
136
|
+
: target.nodeType === 9
|
|
137
|
+
? target.defaultView
|
|
138
|
+
: target.ownerDocument.defaultView;
|
|
139
|
+
const domSelection = getDOMSelection(targetWindow);
|
|
140
|
+
if (document.caretRangeFromPoint) {
|
|
141
|
+
range = document.caretRangeFromPoint(event.clientX, event.clientY);
|
|
142
|
+
}
|
|
143
|
+
else if (event.rangeParent && domSelection !== null) {
|
|
144
|
+
domSelection.collapse(event.rangeParent, event.rangeOffset || 0);
|
|
145
|
+
range = domSelection.getRangeAt(0);
|
|
146
|
+
}
|
|
147
|
+
else {
|
|
148
|
+
throw Error(`Cannot get the selection when dragging`);
|
|
149
|
+
}
|
|
150
|
+
return range;
|
|
151
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
type Props = Readonly<{
|
|
9
|
+
maxDepth: number | null | undefined;
|
|
10
|
+
}>;
|
|
11
|
+
export default function ListMaxIndentLevelPlugin({ maxDepth }: Props): null;
|
|
12
|
+
export {};
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
import { $getListDepth, $isListItemNode, $isListNode } from "@lexical/list";
|
|
9
|
+
import { useLexicalComposerContext } from "@lexical/react/LexicalComposerContext";
|
|
10
|
+
import { $getSelection, $isElementNode, $isRangeSelection, COMMAND_PRIORITY_CRITICAL, INDENT_CONTENT_COMMAND, } from "lexical";
|
|
11
|
+
import { useEffect } from "react";
|
|
12
|
+
function getElementNodesInSelection(selection) {
|
|
13
|
+
const nodesInSelection = selection.getNodes();
|
|
14
|
+
if (nodesInSelection.length === 0) {
|
|
15
|
+
return new Set([
|
|
16
|
+
selection.anchor.getNode().getParentOrThrow(),
|
|
17
|
+
selection.focus.getNode().getParentOrThrow(),
|
|
18
|
+
]);
|
|
19
|
+
}
|
|
20
|
+
return new Set(nodesInSelection.map((n) => ($isElementNode(n) ? n : n.getParentOrThrow())));
|
|
21
|
+
}
|
|
22
|
+
function isIndentPermitted(maxDepth) {
|
|
23
|
+
const selection = $getSelection();
|
|
24
|
+
if (!$isRangeSelection(selection)) {
|
|
25
|
+
return false;
|
|
26
|
+
}
|
|
27
|
+
const elementNodesInSelection = getElementNodesInSelection(selection);
|
|
28
|
+
let totalDepth = 0;
|
|
29
|
+
for (const elementNode of elementNodesInSelection) {
|
|
30
|
+
if ($isListNode(elementNode)) {
|
|
31
|
+
totalDepth = Math.max($getListDepth(elementNode) + 1, totalDepth);
|
|
32
|
+
}
|
|
33
|
+
else if ($isListItemNode(elementNode)) {
|
|
34
|
+
const parent = elementNode.getParent();
|
|
35
|
+
if (!$isListNode(parent)) {
|
|
36
|
+
throw new Error("ListMaxIndentLevelPlugin: A ListItemNode must have a ListNode for a parent.");
|
|
37
|
+
}
|
|
38
|
+
totalDepth = Math.max($getListDepth(parent) + 1, totalDepth);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
return totalDepth <= maxDepth;
|
|
42
|
+
}
|
|
43
|
+
export default function ListMaxIndentLevelPlugin({ maxDepth }) {
|
|
44
|
+
const [editor] = useLexicalComposerContext();
|
|
45
|
+
useEffect(() => {
|
|
46
|
+
return editor.registerCommand(INDENT_CONTENT_COMMAND, () => !isIndentPermitted(maxDepth !== null && maxDepth !== void 0 ? maxDepth : 7), COMMAND_PRIORITY_CRITICAL);
|
|
47
|
+
}, [editor, maxDepth]);
|
|
48
|
+
return null;
|
|
49
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
import { ElementTransformer, TextMatchTransformer, Transformer } from "@lexical/markdown";
|
|
9
|
+
export declare const HR: ElementTransformer;
|
|
10
|
+
export declare const IMAGE: TextMatchTransformer;
|
|
11
|
+
export declare const TABLE: ElementTransformer;
|
|
12
|
+
export declare const CODLE_TRANSFORMERS: Array<Transformer>;
|
|
@@ -0,0 +1,184 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
import { $convertFromMarkdownString, $convertToMarkdownString, CHECK_LIST, ELEMENT_TRANSFORMERS, TEXT_FORMAT_TRANSFORMERS, TEXT_MATCH_TRANSFORMERS, } from "@lexical/markdown";
|
|
9
|
+
import { $createHorizontalRuleNode, $isHorizontalRuleNode, HorizontalRuleNode, } from "@lexical/react/LexicalHorizontalRuleNode";
|
|
10
|
+
import { $createTableCellNode, $createTableNode, $createTableRowNode, $isTableCellNode, $isTableNode, $isTableRowNode, TableCellHeaderStates, TableCellNode, TableNode, TableRowNode, } from "@lexical/table";
|
|
11
|
+
import { $isParagraphNode, $isTextNode } from "lexical";
|
|
12
|
+
import { $createImageNode, $isImageNode, ImageNode, } from "../../nodes/ImageNode";
|
|
13
|
+
export const HR = {
|
|
14
|
+
dependencies: [HorizontalRuleNode],
|
|
15
|
+
export: (node) => {
|
|
16
|
+
return $isHorizontalRuleNode(node) ? "***" : null;
|
|
17
|
+
},
|
|
18
|
+
regExp: /^(---|\*\*\*|___)\s?$/,
|
|
19
|
+
replace: (parentNode, _1, _2, isImport) => {
|
|
20
|
+
const line = $createHorizontalRuleNode();
|
|
21
|
+
// TODO: Get rid of isImport flag
|
|
22
|
+
if (isImport || parentNode.getNextSibling() != null) {
|
|
23
|
+
parentNode.replace(line);
|
|
24
|
+
}
|
|
25
|
+
else {
|
|
26
|
+
parentNode.insertBefore(line);
|
|
27
|
+
}
|
|
28
|
+
line.selectNext();
|
|
29
|
+
},
|
|
30
|
+
type: "element",
|
|
31
|
+
};
|
|
32
|
+
export const IMAGE = {
|
|
33
|
+
dependencies: [ImageNode],
|
|
34
|
+
export: (node) => {
|
|
35
|
+
if (!$isImageNode(node)) {
|
|
36
|
+
return null;
|
|
37
|
+
}
|
|
38
|
+
return `})`;
|
|
39
|
+
},
|
|
40
|
+
importRegExp: /!(?:\[([^[]*)\])(?:\(([^(]+)\))/,
|
|
41
|
+
regExp: /!(?:\[([^[]*)\])(?:\(([^(]+)\))$/,
|
|
42
|
+
replace: (textNode, match) => {
|
|
43
|
+
const [, altText, src] = match;
|
|
44
|
+
const imageNode = $createImageNode({
|
|
45
|
+
altText,
|
|
46
|
+
maxWidth: 800,
|
|
47
|
+
src,
|
|
48
|
+
});
|
|
49
|
+
textNode.replace(imageNode);
|
|
50
|
+
},
|
|
51
|
+
trigger: ")",
|
|
52
|
+
type: "text-match",
|
|
53
|
+
};
|
|
54
|
+
// Very primitive table setup
|
|
55
|
+
const TABLE_ROW_REG_EXP = /^(?:\|)(.+)(?:\|)\s?$/;
|
|
56
|
+
const TABLE_ROW_DIVIDER_REG_EXP = /^(\| ?:?-*:? ?)+\|\s?$/;
|
|
57
|
+
export const TABLE = {
|
|
58
|
+
dependencies: [TableNode, TableRowNode, TableCellNode],
|
|
59
|
+
export: (node) => {
|
|
60
|
+
if (!$isTableNode(node)) {
|
|
61
|
+
return null;
|
|
62
|
+
}
|
|
63
|
+
const output = [];
|
|
64
|
+
for (const row of node.getChildren()) {
|
|
65
|
+
const rowOutput = [];
|
|
66
|
+
if (!$isTableRowNode(row)) {
|
|
67
|
+
continue;
|
|
68
|
+
}
|
|
69
|
+
let isHeaderRow = false;
|
|
70
|
+
for (const cell of row.getChildren()) {
|
|
71
|
+
// It's TableCellNode so it's just to make flow happy
|
|
72
|
+
if ($isTableCellNode(cell)) {
|
|
73
|
+
rowOutput.push($convertToMarkdownString(CODLE_TRANSFORMERS, cell).replace(/\n/g, "\\n"));
|
|
74
|
+
if (cell.__headerState === TableCellHeaderStates.ROW) {
|
|
75
|
+
isHeaderRow = true;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
output.push(`| ${rowOutput.join(" | ")} |`);
|
|
80
|
+
if (isHeaderRow) {
|
|
81
|
+
output.push(`| ${rowOutput.map((_) => "---").join(" | ")} |`);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
return output.join("\n");
|
|
85
|
+
},
|
|
86
|
+
regExp: TABLE_ROW_REG_EXP,
|
|
87
|
+
replace: (parentNode, _1, match) => {
|
|
88
|
+
// Header row
|
|
89
|
+
if (TABLE_ROW_DIVIDER_REG_EXP.test(match[0])) {
|
|
90
|
+
const table = parentNode.getPreviousSibling();
|
|
91
|
+
if (!table || !$isTableNode(table)) {
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
94
|
+
const rows = table.getChildren();
|
|
95
|
+
const lastRow = rows[rows.length - 1];
|
|
96
|
+
if (!lastRow || !$isTableRowNode(lastRow)) {
|
|
97
|
+
return;
|
|
98
|
+
}
|
|
99
|
+
// Add header state to row cells
|
|
100
|
+
lastRow.getChildren().forEach((cell) => {
|
|
101
|
+
if (!$isTableCellNode(cell)) {
|
|
102
|
+
return;
|
|
103
|
+
}
|
|
104
|
+
cell.toggleHeaderStyle(TableCellHeaderStates.ROW);
|
|
105
|
+
});
|
|
106
|
+
// Remove line
|
|
107
|
+
parentNode.remove();
|
|
108
|
+
return;
|
|
109
|
+
}
|
|
110
|
+
const matchCells = mapToTableCells(match[0]);
|
|
111
|
+
if (matchCells == null) {
|
|
112
|
+
return;
|
|
113
|
+
}
|
|
114
|
+
const rows = [matchCells];
|
|
115
|
+
let sibling = parentNode.getPreviousSibling();
|
|
116
|
+
let maxCells = matchCells.length;
|
|
117
|
+
while (sibling) {
|
|
118
|
+
if (!$isParagraphNode(sibling)) {
|
|
119
|
+
break;
|
|
120
|
+
}
|
|
121
|
+
if (sibling.getChildrenSize() !== 1) {
|
|
122
|
+
break;
|
|
123
|
+
}
|
|
124
|
+
const firstChild = sibling.getFirstChild();
|
|
125
|
+
if (!$isTextNode(firstChild)) {
|
|
126
|
+
break;
|
|
127
|
+
}
|
|
128
|
+
const cells = mapToTableCells(firstChild.getTextContent());
|
|
129
|
+
if (cells == null) {
|
|
130
|
+
break;
|
|
131
|
+
}
|
|
132
|
+
maxCells = Math.max(maxCells, cells.length);
|
|
133
|
+
rows.unshift(cells);
|
|
134
|
+
const previousSibling = sibling.getPreviousSibling();
|
|
135
|
+
sibling.remove();
|
|
136
|
+
sibling = previousSibling;
|
|
137
|
+
}
|
|
138
|
+
const table = $createTableNode();
|
|
139
|
+
for (const cells of rows) {
|
|
140
|
+
const tableRow = $createTableRowNode();
|
|
141
|
+
table.append(tableRow);
|
|
142
|
+
for (let i = 0; i < maxCells; i++) {
|
|
143
|
+
tableRow.append(i < cells.length ? cells[i] : createTableCell(""));
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
const previousSibling = parentNode.getPreviousSibling();
|
|
147
|
+
if ($isTableNode(previousSibling) &&
|
|
148
|
+
getTableColumnsSize(previousSibling) === maxCells) {
|
|
149
|
+
previousSibling.append(...table.getChildren());
|
|
150
|
+
parentNode.remove();
|
|
151
|
+
}
|
|
152
|
+
else {
|
|
153
|
+
parentNode.replace(table);
|
|
154
|
+
}
|
|
155
|
+
table.selectEnd();
|
|
156
|
+
},
|
|
157
|
+
type: "element",
|
|
158
|
+
};
|
|
159
|
+
function getTableColumnsSize(table) {
|
|
160
|
+
const row = table.getFirstChild();
|
|
161
|
+
return $isTableRowNode(row) ? row.getChildrenSize() : 0;
|
|
162
|
+
}
|
|
163
|
+
const createTableCell = (textContent) => {
|
|
164
|
+
textContent = textContent.replace(/\\n/g, "\n");
|
|
165
|
+
const cell = $createTableCellNode(TableCellHeaderStates.NO_STATUS);
|
|
166
|
+
$convertFromMarkdownString(textContent, CODLE_TRANSFORMERS, cell);
|
|
167
|
+
return cell;
|
|
168
|
+
};
|
|
169
|
+
const mapToTableCells = (textContent) => {
|
|
170
|
+
const match = textContent.match(TABLE_ROW_REG_EXP);
|
|
171
|
+
if (!match || !match[1]) {
|
|
172
|
+
return null;
|
|
173
|
+
}
|
|
174
|
+
return match[1].split("|").map((text) => createTableCell(text));
|
|
175
|
+
};
|
|
176
|
+
export const CODLE_TRANSFORMERS = [
|
|
177
|
+
TABLE,
|
|
178
|
+
HR,
|
|
179
|
+
IMAGE,
|
|
180
|
+
CHECK_LIST,
|
|
181
|
+
...ELEMENT_TRANSFORMERS,
|
|
182
|
+
...TEXT_FORMAT_TRANSFORMERS,
|
|
183
|
+
...TEXT_MATCH_TRANSFORMERS,
|
|
184
|
+
];
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { Theme } from "@emotion/react";
|
|
2
|
+
export declare function getTheme(theme: Theme): {
|
|
3
|
+
paragraph: string;
|
|
4
|
+
quote: string;
|
|
5
|
+
heading: {
|
|
6
|
+
h1: string;
|
|
7
|
+
h2: string;
|
|
8
|
+
h3: string;
|
|
9
|
+
};
|
|
10
|
+
link: string;
|
|
11
|
+
list: {
|
|
12
|
+
nested: {
|
|
13
|
+
listitem: string;
|
|
14
|
+
};
|
|
15
|
+
olDepth: string[];
|
|
16
|
+
ulDepth: string[];
|
|
17
|
+
listitem: string;
|
|
18
|
+
};
|
|
19
|
+
code: string;
|
|
20
|
+
text: {
|
|
21
|
+
code: string;
|
|
22
|
+
strikethrough: string;
|
|
23
|
+
};
|
|
24
|
+
};
|
|
@@ -0,0 +1,178 @@
|
|
|
1
|
+
import { css } from "@emotion/css";
|
|
2
|
+
export function getTheme(theme) {
|
|
3
|
+
return {
|
|
4
|
+
paragraph: css `
|
|
5
|
+
color: ${theme.color.foreground.neutralBase};
|
|
6
|
+
|
|
7
|
+
/* Default/Paragraph/16px-Rg */
|
|
8
|
+
font-family: ${theme.fontFamily.ui};
|
|
9
|
+
font-size: 16px;
|
|
10
|
+
font-style: normal;
|
|
11
|
+
font-weight: 400;
|
|
12
|
+
line-height: 24px; /* 150% */
|
|
13
|
+
`,
|
|
14
|
+
quote: css `
|
|
15
|
+
color: ${theme.color.container.marbleOnContainer};
|
|
16
|
+
|
|
17
|
+
/* Default/Paragraph/14px-Rg */
|
|
18
|
+
font-family: ${theme.fontFamily.ui};
|
|
19
|
+
font-size: 14px;
|
|
20
|
+
font-style: normal;
|
|
21
|
+
font-weight: 400;
|
|
22
|
+
line-height: 20px; /* 142.857% */
|
|
23
|
+
|
|
24
|
+
margin: 16px 0;
|
|
25
|
+
padding-left: 12px;
|
|
26
|
+
border-left: 2px solid ${theme.color.container.marbleContainer};
|
|
27
|
+
`,
|
|
28
|
+
heading: {
|
|
29
|
+
h1: css `
|
|
30
|
+
color: ${theme.color.foreground.neutralBase};
|
|
31
|
+
|
|
32
|
+
/* Alt/Heading/32px-Hv */
|
|
33
|
+
font-family: ${theme.fontFamily.title};
|
|
34
|
+
font-size: 32px;
|
|
35
|
+
font-style: normal;
|
|
36
|
+
font-weight: 900;
|
|
37
|
+
line-height: 40px; /* 125% */
|
|
38
|
+
`,
|
|
39
|
+
h2: css `
|
|
40
|
+
color: ${theme.color.foreground.neutralBase};
|
|
41
|
+
|
|
42
|
+
/* Default/Heading/24px-Bd */
|
|
43
|
+
font-family: ${theme.fontFamily.ui};
|
|
44
|
+
font-size: 24px;
|
|
45
|
+
font-style: normal;
|
|
46
|
+
font-weight: 700;
|
|
47
|
+
line-height: 32px; /* 133.333% */
|
|
48
|
+
`,
|
|
49
|
+
h3: css `
|
|
50
|
+
color: ${theme.color.foreground.neutralBase};
|
|
51
|
+
|
|
52
|
+
/* Default/Paragraph/18px-Bd */
|
|
53
|
+
font-family: ${theme.fontFamily.ui};
|
|
54
|
+
font-size: 18px;
|
|
55
|
+
font-style: normal;
|
|
56
|
+
font-weight: 700;
|
|
57
|
+
line-height: 28px; /* 155.556% */
|
|
58
|
+
`,
|
|
59
|
+
},
|
|
60
|
+
link: css `
|
|
61
|
+
color: ${theme.color.foreground.primary};
|
|
62
|
+
text-decoration: underline;
|
|
63
|
+
cursor: pointer;
|
|
64
|
+
`,
|
|
65
|
+
list: {
|
|
66
|
+
nested: {
|
|
67
|
+
listitem: css `
|
|
68
|
+
list-style-type: none;
|
|
69
|
+
&::before,
|
|
70
|
+
&::after {
|
|
71
|
+
display: none;
|
|
72
|
+
}
|
|
73
|
+
`,
|
|
74
|
+
},
|
|
75
|
+
olDepth: [
|
|
76
|
+
css `
|
|
77
|
+
padding: 0;
|
|
78
|
+
margin: 16px 0;
|
|
79
|
+
list-style-position: inside;
|
|
80
|
+
`,
|
|
81
|
+
css `
|
|
82
|
+
padding: 0;
|
|
83
|
+
margin: 0;
|
|
84
|
+
list-style-type: upper-alpha;
|
|
85
|
+
list-style-position: inside;
|
|
86
|
+
`,
|
|
87
|
+
css `
|
|
88
|
+
padding: 0;
|
|
89
|
+
margin: 0;
|
|
90
|
+
list-style-type: lower-alpha;
|
|
91
|
+
list-style-position: inside;
|
|
92
|
+
`,
|
|
93
|
+
css `
|
|
94
|
+
padding: 0;
|
|
95
|
+
margin: 0;
|
|
96
|
+
list-style-type: upper-roman;
|
|
97
|
+
list-style-position: inside;
|
|
98
|
+
`,
|
|
99
|
+
css `
|
|
100
|
+
padding: 0;
|
|
101
|
+
margin: 0;
|
|
102
|
+
list-style-type: lower-roman;
|
|
103
|
+
list-style-position: inside;
|
|
104
|
+
`,
|
|
105
|
+
],
|
|
106
|
+
ulDepth: [
|
|
107
|
+
css `
|
|
108
|
+
padding: 0;
|
|
109
|
+
margin: 16px 0;
|
|
110
|
+
list-style-position: inside;
|
|
111
|
+
`,
|
|
112
|
+
css `
|
|
113
|
+
padding: 0;
|
|
114
|
+
margin: 0;
|
|
115
|
+
list-style-position: inside;
|
|
116
|
+
`,
|
|
117
|
+
css `
|
|
118
|
+
padding: 0;
|
|
119
|
+
margin: 0;
|
|
120
|
+
list-style-position: inside;
|
|
121
|
+
`,
|
|
122
|
+
css `
|
|
123
|
+
padding: 0;
|
|
124
|
+
margin: 0;
|
|
125
|
+
list-style-position: inside;
|
|
126
|
+
`,
|
|
127
|
+
css `
|
|
128
|
+
padding: 0;
|
|
129
|
+
margin: 0;
|
|
130
|
+
list-style-position: inside;
|
|
131
|
+
`,
|
|
132
|
+
],
|
|
133
|
+
listitem: css `
|
|
134
|
+
margin: 0 24px;
|
|
135
|
+
|
|
136
|
+
color: ${theme.color.foreground.neutralBase};
|
|
137
|
+
|
|
138
|
+
/* Default/Paragraph/16px-Rg */
|
|
139
|
+
font-family: ${theme.fontFamily.ui};
|
|
140
|
+
font-size: 16px;
|
|
141
|
+
font-style: normal;
|
|
142
|
+
font-weight: 400;
|
|
143
|
+
line-height: 24px; /* 150% */
|
|
144
|
+
`,
|
|
145
|
+
},
|
|
146
|
+
code: css `
|
|
147
|
+
margin: 16px 0;
|
|
148
|
+
|
|
149
|
+
display: block;
|
|
150
|
+
padding: 4px 8px;
|
|
151
|
+
border-radius: 6px;
|
|
152
|
+
background: ${theme.color.background.neutralAlt};
|
|
153
|
+
|
|
154
|
+
color: ${theme.color.foreground.neutralBase};
|
|
155
|
+
|
|
156
|
+
/* Mono/Paragraph/14px-Rg */
|
|
157
|
+
font-family: D2Coding;
|
|
158
|
+
font-size: 14px;
|
|
159
|
+
font-style: normal;
|
|
160
|
+
font-weight: 400;
|
|
161
|
+
line-height: 20px; /* 142.857% */
|
|
162
|
+
`,
|
|
163
|
+
text: {
|
|
164
|
+
code: css `
|
|
165
|
+
padding: 4px 8px;
|
|
166
|
+
border-radius: 6px;
|
|
167
|
+
background: ${theme.color.background.neutralAlt};
|
|
168
|
+
|
|
169
|
+
color: ${theme.color.foreground.neutralBase};
|
|
170
|
+
/* Mono/Paragraph/14px-Rg */
|
|
171
|
+
font-family: D2Coding;
|
|
172
|
+
`,
|
|
173
|
+
strikethrough: css `
|
|
174
|
+
text-decoration: line-through;
|
|
175
|
+
`,
|
|
176
|
+
},
|
|
177
|
+
};
|
|
178
|
+
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
export declare function getDOMRangeRect(nativeSelection: Selection, rootElement: HTMLElement): DOMRect;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
*/
|
|
8
|
+
export function getDOMRangeRect(nativeSelection, rootElement) {
|
|
9
|
+
const domRange = nativeSelection.getRangeAt(0);
|
|
10
|
+
let rect;
|
|
11
|
+
if (nativeSelection.anchorNode === rootElement) {
|
|
12
|
+
let inner = rootElement;
|
|
13
|
+
while (inner.firstElementChild != null) {
|
|
14
|
+
inner = inner.firstElementChild;
|
|
15
|
+
}
|
|
16
|
+
rect = inner.getBoundingClientRect();
|
|
17
|
+
}
|
|
18
|
+
else {
|
|
19
|
+
rect = domRange.getBoundingClientRect();
|
|
20
|
+
}
|
|
21
|
+
return rect;
|
|
22
|
+
}
|