@lofcz/platejs-code-block 52.0.11 → 52.3.6
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/{BaseCodeBlockPlugin-BntJ075t.js → BaseCodeBlockPlugin-CAamjco6.js} +11 -4
- package/dist/index.d.ts +31 -9
- package/dist/index.js +19 -7
- package/dist/react/index.d.ts +13 -5
- package/dist/react/index.js +2 -3
- package/package.json +4 -3
- package/dist/BaseCodeBlockPlugin-BntJ075t.js.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/react/index.d.ts.map +0 -1
- package/dist/react/index.js.map +0 -1
|
@@ -343,11 +343,18 @@ const withCodeBlock = (ctx) => {
|
|
|
343
343
|
const { editor, getOptions, tf: { apply, insertBreak, resetBlock, selectAll, tab }, type } = ctx;
|
|
344
344
|
return { transforms: {
|
|
345
345
|
apply(operation) {
|
|
346
|
+
let shouldRedecorate = false;
|
|
346
347
|
if (getOptions().lowlight && operation.type === "set_node") {
|
|
347
348
|
const entry = editor.api.node(operation.path);
|
|
348
|
-
|
|
349
|
+
const touchesLang = "lang" in (operation.properties ?? {}) || "lang" in (operation.newProperties ?? {});
|
|
350
|
+
const langChanged = operation.properties?.lang !== operation.newProperties?.lang;
|
|
351
|
+
if (entry?.[0].type === type && touchesLang && langChanged) {
|
|
352
|
+
resetCodeBlockDecorations(entry[0]);
|
|
353
|
+
shouldRedecorate = true;
|
|
354
|
+
}
|
|
349
355
|
}
|
|
350
356
|
apply(operation);
|
|
357
|
+
if (shouldRedecorate) editor.api.redecorate();
|
|
351
358
|
},
|
|
352
359
|
insertBreak() {
|
|
353
360
|
const apply$1 = () => {
|
|
@@ -393,7 +400,8 @@ const withCodeBlock = (ctx) => {
|
|
|
393
400
|
},
|
|
394
401
|
tab: (options) => {
|
|
395
402
|
const apply$1 = () => {
|
|
396
|
-
const
|
|
403
|
+
const codeLineType = editor.getType("code_line");
|
|
404
|
+
const _codeLines = editor.api.nodes({ match: { type: codeLineType } });
|
|
397
405
|
const codeLines = Array.from(_codeLines);
|
|
398
406
|
if (codeLines.length > 0) {
|
|
399
407
|
const [, firstLinePath] = codeLines[0];
|
|
@@ -461,5 +469,4 @@ const BaseCodeBlockPlugin = createTSlatePlugin({
|
|
|
461
469
|
} }));
|
|
462
470
|
|
|
463
471
|
//#endregion
|
|
464
|
-
export { getIndentDepth as _, withNormalizeCodeBlock as a, unwrapCodeBlock as c, deleteStartSpace as d, CODE_LINE_TO_DECORATIONS as f, isCodeBlockEmpty as g, setCodeBlockToDecorations as h, withCodeBlock as i, outdentCodeLine as l, resetCodeBlockDecorations as m, BaseCodeLinePlugin as n, withInsertFragmentCodeBlock as o, codeBlockToDecorations as p, BaseCodeSyntaxPlugin as r, withInsertDataCodeBlock as s, BaseCodeBlockPlugin as t, indentCodeLine as u, getCodeLineEntry as v, htmlDeserializerCodeBlock as y };
|
|
465
|
-
//# sourceMappingURL=BaseCodeBlockPlugin-BntJ075t.js.map
|
|
472
|
+
export { getIndentDepth as _, withNormalizeCodeBlock as a, unwrapCodeBlock as c, deleteStartSpace as d, CODE_LINE_TO_DECORATIONS as f, isCodeBlockEmpty as g, setCodeBlockToDecorations as h, withCodeBlock as i, outdentCodeLine as l, resetCodeBlockDecorations as m, BaseCodeLinePlugin as n, withInsertFragmentCodeBlock as o, codeBlockToDecorations as p, BaseCodeSyntaxPlugin as r, withInsertDataCodeBlock as s, BaseCodeBlockPlugin as t, indentCodeLine as u, getCodeLineEntry as v, htmlDeserializerCodeBlock as y };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import * as platejs2 from "platejs";
|
|
1
2
|
import { DecoratedRange, Editor, ElementEntry, ElementOf, HtmlDeserializer, InsertNodesOptions, NodeEntry, OverrideEditor, PluginConfig, SlateEditor, TCodeBlockElement, TElement, TLocation } from "platejs";
|
|
2
3
|
import { createLowlight } from "lowlight";
|
|
3
4
|
|
|
@@ -14,9 +15,22 @@ type CodeBlockConfig = PluginConfig<'code_block', {
|
|
|
14
15
|
*/
|
|
15
16
|
lowlight?: ReturnType<typeof createLowlight> | null;
|
|
16
17
|
}>;
|
|
17
|
-
declare const BaseCodeLinePlugin: any
|
|
18
|
-
declare const BaseCodeSyntaxPlugin:
|
|
19
|
-
declare const BaseCodeBlockPlugin:
|
|
18
|
+
declare const BaseCodeLinePlugin: platejs2.SlatePlugin<PluginConfig<any, {}, {}, {}, {}>>;
|
|
19
|
+
declare const BaseCodeSyntaxPlugin: platejs2.SlatePlugin<PluginConfig<"code_syntax", {}, {}, {}, {}>>;
|
|
20
|
+
declare const BaseCodeBlockPlugin: platejs2.SlatePlugin<PluginConfig<"code_block", {
|
|
21
|
+
/**
|
|
22
|
+
* Default language to use when no language is specified. Set to null to
|
|
23
|
+
* disable syntax highlighting by default.
|
|
24
|
+
*/
|
|
25
|
+
defaultLanguage?: string | null;
|
|
26
|
+
/**
|
|
27
|
+
* Lowlight instance to use for highlighting. If not provided, syntax
|
|
28
|
+
* highlighting will be disabled.
|
|
29
|
+
*/
|
|
30
|
+
lowlight?: ReturnType<typeof createLowlight> | null;
|
|
31
|
+
}, {}, Record<"code_block", {
|
|
32
|
+
toggle: () => void;
|
|
33
|
+
}>, {}>>;
|
|
20
34
|
//#endregion
|
|
21
35
|
//#region src/lib/setCodeBlockToDecorations.d.ts
|
|
22
36
|
declare const CODE_LINE_TO_DECORATIONS: WeakMap<TElement, DecoratedRange[]>;
|
|
@@ -43,7 +57,7 @@ declare const htmlDeserializerCodeBlock: HtmlDeserializer;
|
|
|
43
57
|
//#region src/lib/formatter/formatter.d.ts
|
|
44
58
|
declare const isLangSupported: (lang?: string) => boolean;
|
|
45
59
|
declare const isValidSyntax: (code: string, lang?: string) => boolean;
|
|
46
|
-
declare const formatCodeBlock: (editor:
|
|
60
|
+
declare const formatCodeBlock: (editor: SlateEditor, {
|
|
47
61
|
element
|
|
48
62
|
}: {
|
|
49
63
|
element: TCodeBlockElement;
|
|
@@ -60,7 +74,7 @@ declare const getCodeLineEntry: <N extends ElementOf<E>, E extends SlateEditor>(
|
|
|
60
74
|
}?: {
|
|
61
75
|
at?: TLocation | null;
|
|
62
76
|
}) => {
|
|
63
|
-
codeBlock:
|
|
77
|
+
codeBlock: NodeEntry<N>;
|
|
64
78
|
codeLine: NodeEntry<N>;
|
|
65
79
|
} | undefined;
|
|
66
80
|
//#endregion
|
|
@@ -85,7 +99,7 @@ declare const indentCodeLine: (editor: Editor, {
|
|
|
85
99
|
//#region src/lib/queries/getIndentDepth.d.ts
|
|
86
100
|
declare const getIndentDepth: (editor: Editor, {
|
|
87
101
|
codeLine
|
|
88
|
-
}: IndentCodeLineOptions) =>
|
|
102
|
+
}: IndentCodeLineOptions) => number;
|
|
89
103
|
//#endregion
|
|
90
104
|
//#region src/lib/queries/isCodeBlockEmpty.d.ts
|
|
91
105
|
/** Is the selection inside an empty code block */
|
|
@@ -93,7 +107,7 @@ declare const isCodeBlockEmpty: (editor: SlateEditor) => boolean;
|
|
|
93
107
|
//#endregion
|
|
94
108
|
//#region src/lib/queries/isSelectionAtCodeBlockStart.d.ts
|
|
95
109
|
/** Is the selection at the start of the first code line in a code block */
|
|
96
|
-
declare const isSelectionAtCodeBlockStart: (editor: SlateEditor) =>
|
|
110
|
+
declare const isSelectionAtCodeBlockStart: (editor: SlateEditor) => boolean;
|
|
97
111
|
//#endregion
|
|
98
112
|
//#region src/lib/transforms/outdentCodeLine.d.ts
|
|
99
113
|
type OutdentCodeLineOptions = {
|
|
@@ -137,11 +151,19 @@ declare const insertEmptyCodeBlock: (editor: SlateEditor, {
|
|
|
137
151
|
insertNodesOptions
|
|
138
152
|
}?: CodeBlockInsertOptions) => void;
|
|
139
153
|
//#endregion
|
|
154
|
+
//#region src/lib/transforms/setCodeBlockContent.d.ts
|
|
155
|
+
declare const setCodeBlockContent: (editor: SlateEditor, {
|
|
156
|
+
code,
|
|
157
|
+
element
|
|
158
|
+
}: {
|
|
159
|
+
code: string;
|
|
160
|
+
element: TCodeBlockElement;
|
|
161
|
+
}) => void;
|
|
162
|
+
//#endregion
|
|
140
163
|
//#region src/lib/transforms/toggleCodeBlock.d.ts
|
|
141
164
|
declare const toggleCodeBlock: (editor: SlateEditor) => void;
|
|
142
165
|
//#endregion
|
|
143
166
|
//#region src/lib/transforms/unwrapCodeBlock.d.ts
|
|
144
167
|
declare const unwrapCodeBlock: (editor: SlateEditor) => void;
|
|
145
168
|
//#endregion
|
|
146
|
-
export { BaseCodeBlockPlugin, BaseCodeLinePlugin, BaseCodeSyntaxPlugin, CODE_LINE_TO_DECORATIONS, CodeBlockConfig, CodeBlockInsertOptions, IndentCodeLineOptions, OutdentCodeLineOptions, codeBlockToDecorations, deleteStartSpace, formatCodeBlock, formatJson, getCodeLineEntry, getIndentDepth, htmlDeserializerCodeBlock, indentCodeLine, insertCodeBlock, insertCodeLine, insertEmptyCodeBlock, isCodeBlockEmpty, isLangSupported, isSelectionAtCodeBlockStart, isValidJson, isValidSyntax, outdentCodeLine, resetCodeBlockDecorations, setCodeBlockToDecorations, toggleCodeBlock, unwrapCodeBlock, withCodeBlock, withInsertDataCodeBlock, withInsertFragmentCodeBlock, withNormalizeCodeBlock };
|
|
147
|
-
//# sourceMappingURL=index.d.ts.map
|
|
169
|
+
export { BaseCodeBlockPlugin, BaseCodeLinePlugin, BaseCodeSyntaxPlugin, CODE_LINE_TO_DECORATIONS, CodeBlockConfig, CodeBlockInsertOptions, IndentCodeLineOptions, OutdentCodeLineOptions, codeBlockToDecorations, deleteStartSpace, formatCodeBlock, formatJson, getCodeLineEntry, getIndentDepth, htmlDeserializerCodeBlock, indentCodeLine, insertCodeBlock, insertCodeLine, insertEmptyCodeBlock, isCodeBlockEmpty, isLangSupported, isSelectionAtCodeBlockStart, isValidJson, isValidSyntax, outdentCodeLine, resetCodeBlockDecorations, setCodeBlockContent, setCodeBlockToDecorations, toggleCodeBlock, unwrapCodeBlock, withCodeBlock, withInsertDataCodeBlock, withInsertFragmentCodeBlock, withNormalizeCodeBlock };
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { _ as getIndentDepth, a as withNormalizeCodeBlock, c as unwrapCodeBlock, d as deleteStartSpace, f as CODE_LINE_TO_DECORATIONS, g as isCodeBlockEmpty, h as setCodeBlockToDecorations, i as withCodeBlock, l as outdentCodeLine, m as resetCodeBlockDecorations, n as BaseCodeLinePlugin, o as withInsertFragmentCodeBlock, p as codeBlockToDecorations, r as BaseCodeSyntaxPlugin, s as withInsertDataCodeBlock, t as BaseCodeBlockPlugin, u as indentCodeLine, v as getCodeLineEntry, y as htmlDeserializerCodeBlock } from "./BaseCodeBlockPlugin-
|
|
1
|
+
import { _ as getIndentDepth, a as withNormalizeCodeBlock, c as unwrapCodeBlock, d as deleteStartSpace, f as CODE_LINE_TO_DECORATIONS, g as isCodeBlockEmpty, h as setCodeBlockToDecorations, i as withCodeBlock, l as outdentCodeLine, m as resetCodeBlockDecorations, n as BaseCodeLinePlugin, o as withInsertFragmentCodeBlock, p as codeBlockToDecorations, r as BaseCodeSyntaxPlugin, s as withInsertDataCodeBlock, t as BaseCodeBlockPlugin, u as indentCodeLine, v as getCodeLineEntry, y as htmlDeserializerCodeBlock } from "./BaseCodeBlockPlugin-CAamjco6.js";
|
|
2
2
|
import { KEYS } from "platejs";
|
|
3
3
|
|
|
4
4
|
//#region src/lib/queries/isSelectionAtCodeBlockStart.ts
|
|
@@ -64,6 +64,19 @@ const insertEmptyCodeBlock = (editor, { defaultType = editor.getType(KEYS.p), in
|
|
|
64
64
|
insertCodeBlock(editor, insertNodesOptions);
|
|
65
65
|
};
|
|
66
66
|
|
|
67
|
+
//#endregion
|
|
68
|
+
//#region src/lib/transforms/setCodeBlockContent.ts
|
|
69
|
+
const setCodeBlockContent = (editor, { code, element }) => {
|
|
70
|
+
editor.tf.replaceNodes(code.split("\n").map((line) => ({
|
|
71
|
+
children: [{ text: line }],
|
|
72
|
+
type: editor.getType(KEYS.codeLine)
|
|
73
|
+
})), {
|
|
74
|
+
at: element,
|
|
75
|
+
children: true
|
|
76
|
+
});
|
|
77
|
+
editor.api.redecorate();
|
|
78
|
+
};
|
|
79
|
+
|
|
67
80
|
//#endregion
|
|
68
81
|
//#region src/lib/transforms/toggleCodeBlock.ts
|
|
69
82
|
const toggleCodeBlock = (editor) => {
|
|
@@ -117,10 +130,10 @@ const formatCodeBlock = (editor, { element }) => {
|
|
|
117
130
|
const { lang } = element;
|
|
118
131
|
if (!lang || !isLangSupported(lang)) return;
|
|
119
132
|
const code = editor.api.string(element);
|
|
120
|
-
if (isValidSyntax(code, lang)) {
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
}
|
|
133
|
+
if (isValidSyntax(code, lang)) setCodeBlockContent(editor, {
|
|
134
|
+
code: formatCode(code, lang),
|
|
135
|
+
element
|
|
136
|
+
});
|
|
124
137
|
};
|
|
125
138
|
const formatCode = (code, lang) => {
|
|
126
139
|
switch (lang) {
|
|
@@ -130,5 +143,4 @@ const formatCode = (code, lang) => {
|
|
|
130
143
|
};
|
|
131
144
|
|
|
132
145
|
//#endregion
|
|
133
|
-
export { BaseCodeBlockPlugin, BaseCodeLinePlugin, BaseCodeSyntaxPlugin, CODE_LINE_TO_DECORATIONS, codeBlockToDecorations, deleteStartSpace, formatCodeBlock, formatJson, getCodeLineEntry, getIndentDepth, htmlDeserializerCodeBlock, indentCodeLine, insertCodeBlock, insertCodeLine, insertEmptyCodeBlock, isCodeBlockEmpty, isLangSupported, isSelectionAtCodeBlockStart, isValidJson, isValidSyntax, outdentCodeLine, resetCodeBlockDecorations, setCodeBlockToDecorations, toggleCodeBlock, unwrapCodeBlock, withCodeBlock, withInsertDataCodeBlock, withInsertFragmentCodeBlock, withNormalizeCodeBlock };
|
|
134
|
-
//# sourceMappingURL=index.js.map
|
|
146
|
+
export { BaseCodeBlockPlugin, BaseCodeLinePlugin, BaseCodeSyntaxPlugin, CODE_LINE_TO_DECORATIONS, codeBlockToDecorations, deleteStartSpace, formatCodeBlock, formatJson, getCodeLineEntry, getIndentDepth, htmlDeserializerCodeBlock, indentCodeLine, insertCodeBlock, insertCodeLine, insertEmptyCodeBlock, isCodeBlockEmpty, isLangSupported, isSelectionAtCodeBlockStart, isValidJson, isValidSyntax, outdentCodeLine, resetCodeBlockDecorations, setCodeBlockContent, setCodeBlockToDecorations, toggleCodeBlock, unwrapCodeBlock, withCodeBlock, withInsertDataCodeBlock, withInsertFragmentCodeBlock, withNormalizeCodeBlock };
|
package/dist/react/index.d.ts
CHANGED
|
@@ -1,8 +1,16 @@
|
|
|
1
|
+
import * as platejs0 from "platejs";
|
|
2
|
+
import * as platejs_react0 from "platejs/react";
|
|
3
|
+
import * as lowlight0 from "lowlight";
|
|
4
|
+
|
|
1
5
|
//#region src/react/CodeBlockPlugin.d.ts
|
|
2
|
-
declare const CodeSyntaxPlugin:
|
|
3
|
-
declare const CodeLinePlugin: any
|
|
6
|
+
declare const CodeSyntaxPlugin: platejs_react0.PlatePlugin<platejs0.PluginConfig<"code_syntax", {}, {}, {}, {}>>;
|
|
7
|
+
declare const CodeLinePlugin: platejs_react0.PlatePlugin<platejs0.PluginConfig<any, {}, {}, {}, {}>>;
|
|
4
8
|
/** Enables support for pre-formatted code blocks. */
|
|
5
|
-
declare const CodeBlockPlugin:
|
|
9
|
+
declare const CodeBlockPlugin: platejs_react0.PlatePlugin<platejs0.PluginConfig<"code_block", {
|
|
10
|
+
defaultLanguage?: string | null;
|
|
11
|
+
lowlight?: ReturnType<typeof lowlight0.createLowlight> | null;
|
|
12
|
+
}, {}, Record<"code_block", {
|
|
13
|
+
toggle: () => void;
|
|
14
|
+
}>, {}>>;
|
|
6
15
|
//#endregion
|
|
7
|
-
export { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin };
|
|
8
|
-
//# sourceMappingURL=index.d.ts.map
|
|
16
|
+
export { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin };
|
package/dist/react/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { n as BaseCodeLinePlugin, r as BaseCodeSyntaxPlugin, t as BaseCodeBlockPlugin } from "../BaseCodeBlockPlugin-
|
|
1
|
+
import { n as BaseCodeLinePlugin, r as BaseCodeSyntaxPlugin, t as BaseCodeBlockPlugin } from "../BaseCodeBlockPlugin-CAamjco6.js";
|
|
2
2
|
import { toPlatePlugin } from "platejs/react";
|
|
3
3
|
|
|
4
4
|
//#region src/react/CodeBlockPlugin.tsx
|
|
@@ -8,5 +8,4 @@ const CodeLinePlugin = toPlatePlugin(BaseCodeLinePlugin);
|
|
|
8
8
|
const CodeBlockPlugin = toPlatePlugin(BaseCodeBlockPlugin, { plugins: [CodeLinePlugin, CodeSyntaxPlugin] });
|
|
9
9
|
|
|
10
10
|
//#endregion
|
|
11
|
-
export { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin };
|
|
12
|
-
//# sourceMappingURL=index.js.map
|
|
11
|
+
export { CodeBlockPlugin, CodeLinePlugin, CodeSyntaxPlugin };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@lofcz/platejs-code-block",
|
|
3
|
-
"version": "52.
|
|
3
|
+
"version": "52.3.6",
|
|
4
4
|
"description": "Code block plugin for Plate",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"plate",
|
|
@@ -30,10 +30,11 @@
|
|
|
30
30
|
],
|
|
31
31
|
"devDependencies": {
|
|
32
32
|
"lowlight": "^3.3.0",
|
|
33
|
-
"@plate/scripts": "1.0.0"
|
|
33
|
+
"@plate/scripts": "1.0.0",
|
|
34
|
+
"platejs": "npm:@lofcz/platejs@52.3.6"
|
|
34
35
|
},
|
|
35
36
|
"peerDependencies": {
|
|
36
|
-
"platejs": ">=52.
|
|
37
|
+
"platejs": ">=52.3.16",
|
|
37
38
|
"react": ">=18.0.0",
|
|
38
39
|
"react-dom": ">=18.0.0"
|
|
39
40
|
},
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"BaseCodeBlockPlugin-BntJ075t.js","names":["HtmlDeserializer","KEYS","htmlDeserializerCodeBlock","rules","validNodeName","validStyle","fontFamily","parse","element","languageSelectorText","childNodes","find","node","ChildNode","nodeName","textContent","replace","lines","split","length","codeLines","map","line","children","text","type","codeLine","codeBlock","ElementOf","NodeEntry","SlateEditor","TElement","TLocation","ElementApi","KEYS","getCodeLineEntry","E","editor","at","selection","api","some","match","type","getType","codeLine","selectionParent","parent","parentPath","above","N","codeLineNode","codeLinePath","isElement","codeBlock","Editor","IndentCodeLineOptions","nonWhitespaceOrEndRegex","getIndentDepth","editor","codeLine","codeLinePath","text","api","string","search","SlateEditor","NodeApi","getCodeLineEntry","isCodeBlockEmpty","editor","codeBlock","codeLines","Array","from","children","length","firstCodeLineNode","string","DecoratedRange","NodeEntry","SlateEditor","TCodeBlockElement","TElement","KEYS","NodeApi","BaseCodeBlockPlugin","CODE_LINE_TO_DECORATIONS","WeakMap","getHighlightNodes","result","value","children","parseNodes","nodes","className","classes","text","flatMap","node","properties","normalizeTokens","tokens","lines","content","currentLine","token","tokenLines","split","i","length","push","at","codeBlockToDecorations","editor","block","blockPath","Map","defaultLanguage","options","getOptions","lowlight","map","line","string","join","language","lang","effectiveLanguage","highlighted","highlightAuto","highlight","error","availableLanguages","listLanguages","isLanguageRegistered","includes","api","debug","warn","normalizedTokens","blockChildren","nodeToDecorations","numLines","Math","min","index","lineTokens","element","has","set","start","end","decoration","anchor","offset","path","focus","codeSyntax","get","setCodeBlockToDecorations","decorations","decs","entries","resetCodeBlockDecorations","codeBlock","forEach","delete","Editor","OutdentCodeLineOptions","whitespaceRegex","deleteStartSpace","editor","codeLine","codeLinePath","codeLineStart","api","start","codeLineEnd","after","spaceRange","range","spaceText","string","test","tf","delete","at","Editor","ElementEntry","nonWhitespaceRegex","IndentCodeLineOptions","codeBlock","codeLine","indentDepth","indentCodeLine","editor","codeLinePath","codeLineStart","api","start","indent","repeat","isExpanded","cursor","selection","anchor","range","text","string","test","tf","insertText","at","Editor","ElementEntry","deleteStartSpace","OutdentCodeLineOptions","codeBlock","codeLine","outdentCodeLine","editor","deleted","SlateEditor","TLocation","KEYS","NodeApi","unwrapCodeBlock","editor","selection","codeBlockType","getType","codeBlock","defaultType","p","tf","withoutNormalizing","codeBlockEntries","api","nodes","at","match","type","reversedCodeBlockEntries","Array","from","reverse","codeBlockEntry","codeLineEntries","children","path","setNodes","unwrapNodes","split","OverrideEditor","TElement","KEYS","withInsertDataCodeBlock","editor","tf","insertData","type","codeBlockType","transforms","data","text","getData","vscodeDataString","codeLineType","getType","codeLine","vscodeData","JSON","parse","lines","split","blockAbove","api","block","isInCodeBlock","includes","insertText","length","nodes","slice","map","line","children","insertNodes","node","lang","mode","select","_error","OverrideEditor","TElement","KEYS","NodeApi","extractCodeLinesFromCodeBlock","node","children","withInsertFragmentCodeBlock","editor","tf","insertFragment","type","codeBlockType","transforms","fragment","blockAbove","api","block","codeLineType","getType","codeLine","convertNodeToCodeLine","text","string","includes","flatMap","element","NodeEntry","OverrideEditor","TCodeBlockElement","ElementApi","KEYS","NodeApi","CodeBlockConfig","setCodeBlockToDecorations","withNormalizeCodeBlock","editor","getOptions","tf","normalizeNode","type","transforms","node","path","lowlight","isElement","codeBlockType","getType","codeBlock","codeLineType","codeLine","isCodeBlockRoot","nonCodeLine","Array","from","children","find","child","setNodes","at","OverrideEditor","TCodeBlockElement","TElement","CodeBlockConfig","getCodeLineEntry","getIndentDepth","resetCodeBlockDecorations","indentCodeLine","outdentCodeLine","unwrapCodeBlock","withInsertDataCodeBlock","withInsertFragmentCodeBlock","withNormalizeCodeBlock","withCodeBlock","ctx","editor","getOptions","tf","apply","insertBreak","resetBlock","selectAll","tab","type","transforms","operation","lowlight","entry","api","node","path","newProperties","lang","selection","res","codeBlock","codeLine","indentDepth","options","block","at","match","above","isAt","end","start","select","_codeLines","nodes","codeLines","Array","from","length","firstLinePath","parent","withoutNormalizing","reverse","createLowlight","PluginConfig","TCodeBlockElement","TElement","createSlatePlugin","createTSlatePlugin","KEYS","htmlDeserializerCodeBlock","isCodeBlockEmpty","CODE_LINE_TO_DECORATIONS","setCodeBlockToDecorations","withCodeBlock","CodeBlockConfig","defaultLanguage","lowlight","ReturnType","BaseCodeLinePlugin","key","codeLine","node","isElement","isStrictSiblings","BaseCodeSyntaxPlugin","codeSyntax","isLeaf","BaseCodeBlockPlugin","codeBlock","inject","plugins","html","parser","query","editor","api","some","match","type","getType","options","parsers","deserializer","render","as","rules","delete","empty","rule","includes","decorate","entry","path","getOptions","codeLineType","get","children","overrideEditor","extendTransforms","toggle","tf","toggleBlock"],"sources":["../src/lib/deserializer/htmlDeserializerCodeBlock.ts","../src/lib/queries/getCodeLineEntry.ts","../src/lib/queries/getIndentDepth.ts","../src/lib/queries/isCodeBlockEmpty.ts","../src/lib/setCodeBlockToDecorations.ts","../src/lib/transforms/deleteStartSpace.ts","../src/lib/transforms/indentCodeLine.ts","../src/lib/transforms/outdentCodeLine.ts","../src/lib/transforms/unwrapCodeBlock.ts","../src/lib/withInsertDataCodeBlock.ts","../src/lib/withInsertFragmentCodeBlock.ts","../src/lib/withNormalizeCodeBlock.tsx","../src/lib/withCodeBlock.ts","../src/lib/BaseCodeBlockPlugin.ts"],"sourcesContent":["import type { HtmlDeserializer } from 'platejs';\n\nimport { KEYS } from 'platejs';\n\nexport const htmlDeserializerCodeBlock: HtmlDeserializer = {\n rules: [\n {\n validNodeName: 'PRE',\n },\n {\n validNodeName: 'P',\n validStyle: {\n fontFamily: 'Consolas',\n },\n },\n ],\n parse: ({ element }) => {\n const languageSelectorText =\n [...element.childNodes].find(\n (node: ChildNode) => node.nodeName === 'SELECT'\n )?.textContent || '';\n\n const textContent =\n element.textContent?.replace(languageSelectorText, '') || '';\n\n let lines = textContent.split('\\n');\n\n if (!lines?.length) {\n lines = [textContent];\n }\n\n const codeLines = lines.map((line) => ({\n children: [{ text: line }],\n type: KEYS.codeLine,\n }));\n\n return {\n children: codeLines,\n type: KEYS.codeBlock,\n };\n },\n};\n","import {\n type ElementOf,\n type NodeEntry,\n type SlateEditor,\n type TElement,\n type TLocation,\n ElementApi,\n KEYS,\n} from 'platejs';\n\n/** If at (default = selection) is in ul>li>p, return li and ul node entries. */\nexport const getCodeLineEntry = <N extends ElementOf<E>, E extends SlateEditor>(\n editor: E,\n { at = editor.selection }: { at?: TLocation | null } = {}\n) => {\n if (\n at &&\n editor.api.some({\n at,\n match: { type: editor.getType(KEYS.codeLine) },\n })\n ) {\n const selectionParent = editor.api.parent(at);\n\n if (!selectionParent) return;\n\n const [, parentPath] = selectionParent;\n\n const codeLine =\n editor.api.above<TElement>({\n at,\n match: { type: editor.getType(KEYS.codeLine) },\n }) || editor.api.parent<N>(parentPath);\n\n if (!codeLine) return;\n\n const [codeLineNode, codeLinePath] = codeLine;\n\n if (\n ElementApi.isElement(codeLineNode) &&\n codeLineNode.type !== editor.getType(KEYS.codeLine)\n )\n return;\n\n const codeBlock = editor.api.parent<N>(codeLinePath);\n\n if (!codeBlock) return;\n\n return {\n codeBlock,\n codeLine: codeLine as NodeEntry<N>,\n };\n }\n};\n","import type { Editor } from 'platejs';\n\nimport type { IndentCodeLineOptions } from '../transforms/indentCodeLine';\n\nconst nonWhitespaceOrEndRegex = /\\S|$/;\n\nexport const getIndentDepth = (\n editor: Editor,\n { codeLine }: IndentCodeLineOptions\n) => {\n const [, codeLinePath] = codeLine;\n const text = editor.api.string(codeLinePath);\n\n return text.search(nonWhitespaceOrEndRegex);\n};\n","import { type SlateEditor, NodeApi } from 'platejs';\n\nimport { getCodeLineEntry } from './getCodeLineEntry';\n\n/** Is the selection inside an empty code block */\nexport const isCodeBlockEmpty = (editor: SlateEditor) => {\n const { codeBlock } = getCodeLineEntry(editor) ?? {};\n\n if (!codeBlock) return false;\n\n const codeLines = Array.from(NodeApi.children(editor, codeBlock[1]));\n\n if (codeLines.length === 0) return true;\n if (codeLines.length > 1) return false;\n\n const firstCodeLineNode = codeLines[0][0];\n\n return !NodeApi.string(firstCodeLineNode);\n};\n","import {\n type DecoratedRange,\n type NodeEntry,\n type SlateEditor,\n type TCodeBlockElement,\n type TElement,\n KEYS,\n NodeApi,\n} from 'platejs';\n\nimport { BaseCodeBlockPlugin } from './BaseCodeBlockPlugin';\n\n// Cache for storing decorations per code line element\nexport const CODE_LINE_TO_DECORATIONS: WeakMap<TElement, DecoratedRange[]> =\n new WeakMap();\n\n// Helper function to get highlight nodes from Lowlight result\nfunction getHighlightNodes(result: any) {\n return result.value || result.children || [];\n}\n\n// Helper function to parse nodes from Lowlight's hast tree\nfunction parseNodes(\n nodes: any[],\n className: string[] = []\n): { classes: string[]; text: string }[] {\n return nodes.flatMap((node) => {\n const classes = [\n ...className,\n ...(node.properties ? node.properties.className : []),\n ];\n if (node.children) {\n return parseNodes(node.children, classes);\n }\n return { classes, text: node.value };\n });\n}\n\n// Helper function to normalize tokens by line\nfunction normalizeTokens(tokens: { classes: string[]; text: string }[]) {\n const lines: { classes: string[]; content: string }[][] = [[]];\n let currentLine = lines[0];\n\n for (const token of tokens) {\n const tokenLines = token.text.split('\\n');\n\n for (let i = 0; i < tokenLines.length; i++) {\n const content = tokenLines[i];\n\n if (content) {\n currentLine.push({ classes: token.classes, content });\n }\n\n // Create a new line unless we're on the last line\n if (i < tokenLines.length - 1) {\n lines.push([]);\n currentLine = lines.at(-1) as any;\n }\n }\n }\n\n return lines;\n}\n\n// Helper function to compute decorations for a code block\nexport function codeBlockToDecorations(\n editor: SlateEditor,\n [block, blockPath]: NodeEntry<TCodeBlockElement>\n): Map<TElement, DecoratedRange[]> {\n const { defaultLanguage, ...options } =\n editor.getOptions(BaseCodeBlockPlugin);\n const lowlight = options.lowlight!;\n\n // Get all code lines and combine their text\n const text = block.children.map((line) => NodeApi.string(line)).join('\\n');\n const language = block.lang;\n const effectiveLanguage = language || defaultLanguage;\n\n let highlighted: any;\n try {\n // Skip highlighting for plaintext or when no language is specified\n if (!effectiveLanguage || effectiveLanguage === 'plaintext') {\n highlighted = { value: [] }; // Empty result for plaintext\n } else if (effectiveLanguage === 'auto') {\n highlighted = lowlight.highlightAuto(text);\n } else {\n highlighted = lowlight.highlight(effectiveLanguage, text);\n }\n } catch (error) {\n // Verify if language is registered, fallback to plaintext if not\n const availableLanguages = lowlight.listLanguages();\n const isLanguageRegistered =\n effectiveLanguage && availableLanguages.includes(effectiveLanguage);\n if (isLanguageRegistered) {\n editor.api.debug.error(error, 'CODE_HIGHLIGHT');\n highlighted = { value: [] }; // Empty result on error\n } else {\n editor.api.debug.warn(\n `Language \"${effectiveLanguage}\" is not registered. Falling back to plaintext`\n );\n highlighted = { value: [] };\n }\n }\n\n // Parse and normalize tokens\n const tokens = parseNodes(getHighlightNodes(highlighted));\n const normalizedTokens = normalizeTokens(tokens);\n const blockChildren = block.children as TElement[];\n\n // Create decorations map\n const nodeToDecorations = new Map<TElement, DecoratedRange[]>();\n\n // Safety check: don't process more lines than we have children\n const numLines = Math.min(normalizedTokens.length, blockChildren.length);\n\n // Process each line's tokens\n for (let index = 0; index < numLines; index++) {\n const lineTokens = normalizedTokens[index];\n const element = blockChildren[index];\n\n if (!nodeToDecorations.has(element)) {\n nodeToDecorations.set(element, []);\n }\n\n let start = 0;\n for (const token of lineTokens) {\n const length = token.content.length;\n if (!length) continue;\n\n const end = start + length;\n\n const decoration: DecoratedRange = {\n anchor: {\n offset: start,\n path: [...blockPath, index, 0],\n },\n className: token.classes.join(' '),\n focus: {\n offset: end,\n path: [...blockPath, index, 0],\n },\n [KEYS.codeSyntax]: true,\n } as any;\n\n nodeToDecorations.get(element)!.push(decoration);\n start = end;\n }\n }\n\n return nodeToDecorations;\n}\n\nexport function setCodeBlockToDecorations(\n editor: SlateEditor,\n [block, blockPath]: NodeEntry<TCodeBlockElement>\n) {\n const decorations = codeBlockToDecorations(editor, [block, blockPath]);\n\n // Update the global cache with the new decorations\n for (const [node, decs] of decorations.entries()) {\n CODE_LINE_TO_DECORATIONS.set(node, decs);\n }\n}\n\nexport function resetCodeBlockDecorations(codeBlock: TCodeBlockElement) {\n codeBlock.children.forEach((line) => {\n CODE_LINE_TO_DECORATIONS.delete(line as TElement);\n });\n}\n","import type { Editor } from 'platejs';\n\nimport type { OutdentCodeLineOptions } from './outdentCodeLine';\n\nconst whitespaceRegex = /\\s/;\n\n/** If there is a whitespace character at the start of the code line, delete it. */\nexport const deleteStartSpace = (\n editor: Editor,\n { codeLine }: OutdentCodeLineOptions\n) => {\n const [, codeLinePath] = codeLine;\n const codeLineStart = editor.api.start(codeLinePath);\n const codeLineEnd = codeLineStart && editor.api.after(codeLineStart);\n const spaceRange =\n codeLineEnd && editor.api.range(codeLineStart, codeLineEnd);\n const spaceText = editor.api.string(spaceRange);\n\n if (whitespaceRegex.test(spaceText)) {\n editor.tf.delete({ at: spaceRange });\n\n return true;\n }\n\n return false;\n};\n","import type { Editor, ElementEntry } from 'platejs';\n\nconst nonWhitespaceRegex = /\\S/;\n\nexport type IndentCodeLineOptions = {\n codeBlock: ElementEntry;\n codeLine: ElementEntry;\n indentDepth?: number;\n};\n\n/**\n * Indent if:\n *\n * - The selection is expanded OR\n * - There are no non-whitespace characters left of the cursor Indentation = 2\n * spaces.\n */\nexport const indentCodeLine = (\n editor: Editor,\n { codeLine, indentDepth = 2 }: IndentCodeLineOptions\n) => {\n const [, codeLinePath] = codeLine;\n const codeLineStart = editor.api.start(codeLinePath)!;\n const indent = ' '.repeat(indentDepth);\n\n if (!editor.api.isExpanded()) {\n const cursor = editor.selection?.anchor;\n const range = editor.api.range(codeLineStart, cursor);\n const text = editor.api.string(range);\n\n if (nonWhitespaceRegex.test(text)) {\n editor.tf.insertText(indent, { at: editor.selection! });\n\n return;\n }\n }\n\n editor.tf.insertText(indent, { at: codeLineStart });\n};\n","import type { Editor, ElementEntry } from 'platejs';\n\nimport { deleteStartSpace } from './deleteStartSpace';\n\nexport type OutdentCodeLineOptions = {\n codeBlock: ElementEntry;\n codeLine: ElementEntry;\n};\n\n/** Outdent the code line. Remove 2 whitespace characters if any. */\nexport const outdentCodeLine = (\n editor: Editor,\n { codeBlock, codeLine }: OutdentCodeLineOptions\n) => {\n const deleted = deleteStartSpace(editor, { codeBlock, codeLine });\n if (deleted) {\n deleteStartSpace(editor, { codeBlock, codeLine });\n }\n};\n","import { type SlateEditor, type TLocation, KEYS, NodeApi } from 'platejs';\n\nexport const unwrapCodeBlock = (editor: SlateEditor) => {\n if (!editor.selection) return;\n\n const codeBlockType = editor.getType(KEYS.codeBlock);\n const defaultType = editor.getType(KEYS.p);\n\n editor.tf.withoutNormalizing(() => {\n const codeBlockEntries = editor.api.nodes({\n at: editor.selection as TLocation,\n match: { type: codeBlockType },\n });\n\n const reversedCodeBlockEntries = Array.from(codeBlockEntries).reverse();\n\n for (const codeBlockEntry of reversedCodeBlockEntries) {\n const codeLineEntries = NodeApi.children(editor, codeBlockEntry[1]);\n\n for (const [, path] of codeLineEntries) {\n editor.tf.setNodes({ type: defaultType }, { at: path });\n }\n\n editor.tf.unwrapNodes({\n at: codeBlockEntry[1],\n match: { type: codeBlockType },\n split: true,\n });\n }\n });\n};\n","import type { OverrideEditor, TElement } from 'platejs';\n\nimport { KEYS } from 'platejs';\n\nexport const withInsertDataCodeBlock: OverrideEditor = ({\n editor,\n tf: { insertData },\n type: codeBlockType,\n}) => ({\n transforms: {\n insertData(data) {\n const text = data.getData('text/plain');\n const vscodeDataString = data.getData('vscode-editor-data');\n const codeLineType = editor.getType(KEYS.codeLine);\n\n // Handle VSCode paste with language\n if (vscodeDataString) {\n try {\n const vscodeData = JSON.parse(vscodeDataString);\n const lines = text.split('\\n');\n\n // Check if we're in a code block\n const [blockAbove] = editor.api.block<TElement>() ?? [];\n const isInCodeBlock =\n blockAbove &&\n [codeBlockType, codeLineType].includes(blockAbove?.type);\n\n if (isInCodeBlock) {\n // If in code block, insert first line as text at cursor\n if (lines[0]) {\n editor.tf.insertText(lines[0]);\n }\n\n // Insert remaining lines as new code lines\n if (lines.length > 1) {\n const nodes = lines.slice(1).map((line) => ({\n children: [{ text: line }],\n type: codeLineType,\n }));\n editor.tf.insertNodes(nodes);\n }\n } else {\n // Create new code block\n const node = {\n children: lines.map((line) => ({\n children: [{ text: line }],\n type: codeLineType,\n })),\n lang: vscodeData?.mode,\n type: codeBlockType,\n };\n\n editor.tf.insertNodes(node, {\n select: true,\n });\n }\n\n return;\n } catch (_error) {}\n }\n\n // Handle plain text paste into code block only if there are line breaks\n const [blockAbove] = editor.api.block<TElement>() ?? [];\n if (\n blockAbove &&\n [codeBlockType, codeLineType].includes(blockAbove?.type) &&\n text?.includes('\\n')\n ) {\n const lines = text.split('\\n');\n\n // Insert first line as text at cursor\n if (lines[0]) {\n editor.tf.insertText(lines[0]);\n }\n\n // Insert remaining lines as new code lines\n if (lines.length > 1) {\n const nodes = lines.slice(1).map((line) => ({\n children: [{ text: line }],\n type: codeLineType,\n }));\n editor.tf.insertNodes(nodes);\n }\n return;\n }\n\n insertData(data);\n },\n },\n});\n","import { type OverrideEditor, type TElement, KEYS, NodeApi } from 'platejs';\n\nfunction extractCodeLinesFromCodeBlock(node: TElement) {\n return node.children as TElement[];\n}\n\nexport const withInsertFragmentCodeBlock: OverrideEditor = ({\n editor,\n tf: { insertFragment },\n type: codeBlockType,\n}) => ({\n transforms: {\n insertFragment(fragment) {\n const [blockAbove] = editor.api.block<TElement>() ?? [];\n const codeLineType = editor.getType(KEYS.codeLine);\n\n function convertNodeToCodeLine(node: TElement): TElement {\n return {\n children: [{ text: NodeApi.string(node) }],\n type: codeLineType,\n };\n }\n\n if (\n blockAbove &&\n [codeBlockType, codeLineType].includes(blockAbove?.type)\n ) {\n return insertFragment(\n fragment.flatMap((node) => {\n const element = node as TElement;\n\n return element.type === codeBlockType\n ? extractCodeLinesFromCodeBlock(element)\n : convertNodeToCodeLine(element);\n })\n );\n }\n\n return insertFragment(fragment);\n },\n },\n});\n","import {\n type NodeEntry,\n type OverrideEditor,\n type TCodeBlockElement,\n ElementApi,\n KEYS,\n NodeApi,\n} from 'platejs';\n\nimport type { CodeBlockConfig } from './BaseCodeBlockPlugin';\n\nimport { setCodeBlockToDecorations } from './setCodeBlockToDecorations';\n\n/** Normalize code block node to force the pre>code>div.codeline structure. */\nexport const withNormalizeCodeBlock: OverrideEditor<CodeBlockConfig> = ({\n editor,\n getOptions,\n tf: { normalizeNode },\n type,\n}) => ({\n transforms: {\n normalizeNode([node, path]) {\n // Decorate is called on selection change as well, so we prefer to only run this on code block changes.\n if (node.type === type && getOptions().lowlight) {\n setCodeBlockToDecorations(editor, [\n node,\n path,\n ] as NodeEntry<TCodeBlockElement>);\n }\n\n normalizeNode([node, path]);\n\n if (!ElementApi.isElement(node)) {\n return;\n }\n\n const codeBlockType = editor.getType(KEYS.codeBlock);\n const codeLineType = editor.getType(KEYS.codeLine);\n const isCodeBlockRoot = node.type === codeBlockType;\n\n if (isCodeBlockRoot) {\n // Children should all be code lines\n const nonCodeLine = Array.from(NodeApi.children(editor, path)).find(\n ([child]) => child.type !== codeLineType\n );\n\n if (nonCodeLine) {\n editor.tf.setNodes({ type: codeLineType }, { at: nonCodeLine[1] });\n }\n }\n },\n },\n});\n","import type { OverrideEditor, TCodeBlockElement, TElement } from 'platejs';\n\nimport type { CodeBlockConfig } from './BaseCodeBlockPlugin';\n\nimport { getCodeLineEntry, getIndentDepth } from './queries';\nimport { resetCodeBlockDecorations } from './setCodeBlockToDecorations';\nimport { indentCodeLine, outdentCodeLine, unwrapCodeBlock } from './transforms';\nimport { withInsertDataCodeBlock } from './withInsertDataCodeBlock';\nimport { withInsertFragmentCodeBlock } from './withInsertFragmentCodeBlock';\nimport { withNormalizeCodeBlock } from './withNormalizeCodeBlock';\n\nexport const withCodeBlock: OverrideEditor<CodeBlockConfig> = (ctx) => {\n const {\n editor,\n getOptions,\n tf: { apply, insertBreak, resetBlock, selectAll, tab },\n type,\n } = ctx;\n\n return {\n transforms: {\n apply(operation) {\n if (getOptions().lowlight && operation.type === 'set_node') {\n const entry = editor.api.node(operation.path);\n\n if (entry?.[0].type === type && operation.newProperties?.lang) {\n // Clear decorations for all code lines in this block\n resetCodeBlockDecorations(entry[0] as TCodeBlockElement);\n }\n }\n\n apply(operation);\n },\n insertBreak() {\n const apply = () => {\n if (!editor.selection) return;\n\n const res = getCodeLineEntry(editor, {});\n\n if (!res) return;\n\n const { codeBlock, codeLine } = res;\n const indentDepth = getIndentDepth(editor, {\n codeBlock,\n codeLine,\n });\n\n insertBreak();\n\n indentCodeLine(editor, {\n codeBlock,\n codeLine,\n indentDepth,\n });\n\n return true;\n };\n\n if (apply()) return;\n\n insertBreak();\n },\n resetBlock(options) {\n if (\n editor.api.block({\n at: options?.at,\n match: { type },\n })\n ) {\n unwrapCodeBlock(editor);\n return;\n }\n\n return resetBlock(options);\n },\n selectAll: () => {\n const apply = () => {\n const codeBlock = editor.api.above({\n match: { type },\n });\n\n if (!codeBlock) return;\n\n if (\n editor.api.isAt({ end: true }) &&\n editor.api.isAt({ start: true })\n ) {\n return;\n }\n\n // Select the whole code block\n editor.tf.select(codeBlock[1]);\n return true;\n };\n\n if (apply()) return true;\n\n return selectAll();\n },\n tab: (options) => {\n const apply = () => {\n const _codeLines = editor.api.nodes<TElement>({\n match: { type },\n });\n const codeLines = Array.from(_codeLines);\n\n if (codeLines.length > 0) {\n const [, firstLinePath] = codeLines[0];\n const codeBlock = editor.api.parent<TElement>(firstLinePath);\n\n if (!codeBlock) return;\n\n editor.tf.withoutNormalizing(() => {\n for (const codeLine of codeLines) {\n if (options.reverse) {\n outdentCodeLine(editor, { codeBlock, codeLine });\n } else {\n indentCodeLine(editor, { codeBlock, codeLine });\n }\n }\n });\n\n return true; // Prevent default\n }\n };\n\n if (apply()) return true;\n\n return tab(options);\n },\n ...withInsertDataCodeBlock(ctx).transforms,\n ...withInsertFragmentCodeBlock(ctx).transforms,\n ...withNormalizeCodeBlock(ctx).transforms,\n },\n };\n};\n","import type { createLowlight } from 'lowlight';\n\nimport {\n type PluginConfig,\n type TCodeBlockElement,\n type TElement,\n createSlatePlugin,\n createTSlatePlugin,\n KEYS,\n} from 'platejs';\n\nimport { htmlDeserializerCodeBlock } from './deserializer/htmlDeserializerCodeBlock';\nimport { isCodeBlockEmpty } from './queries';\nimport {\n CODE_LINE_TO_DECORATIONS,\n setCodeBlockToDecorations,\n} from './setCodeBlockToDecorations';\nimport { withCodeBlock } from './withCodeBlock';\n\nexport type CodeBlockConfig = PluginConfig<\n 'code_block',\n {\n /**\n * Default language to use when no language is specified. Set to null to\n * disable syntax highlighting by default.\n */\n defaultLanguage?: string | null;\n /**\n * Lowlight instance to use for highlighting. If not provided, syntax\n * highlighting will be disabled.\n */\n lowlight?: ReturnType<typeof createLowlight> | null;\n }\n>;\n\nexport const BaseCodeLinePlugin = createTSlatePlugin({\n key: KEYS.codeLine,\n node: { isElement: true, isStrictSiblings: true },\n});\n\nexport const BaseCodeSyntaxPlugin = createSlatePlugin({\n key: KEYS.codeSyntax,\n node: { isLeaf: true },\n});\n\nexport const BaseCodeBlockPlugin = createTSlatePlugin<CodeBlockConfig>({\n key: KEYS.codeBlock,\n inject: {\n plugins: {\n [KEYS.html]: {\n parser: {\n query: ({ editor }) =>\n !editor.api.some({\n match: { type: editor.getType(KEYS.codeLine) },\n }),\n },\n },\n },\n },\n node: {\n isElement: true,\n },\n options: {\n defaultLanguage: null,\n lowlight: null,\n },\n parsers: { html: { deserializer: htmlDeserializerCodeBlock } },\n plugins: [BaseCodeLinePlugin, BaseCodeSyntaxPlugin],\n render: { as: 'pre' },\n rules: {\n delete: {\n empty: 'reset',\n },\n match: ({ editor, rule }) =>\n ['break.empty', 'delete.empty'].includes(rule) &&\n isCodeBlockEmpty(editor),\n },\n decorate: ({ editor, entry: [node, path], getOptions, type }) => {\n if (!getOptions().lowlight) return [];\n\n const codeLineType = editor.getType(KEYS.codeLine);\n\n // Initialize decorations for the code block, we assume code line decorate will be called next.\n if (\n node.type === type &&\n !CODE_LINE_TO_DECORATIONS.get((node.children as TElement[])[0])\n ) {\n setCodeBlockToDecorations(editor, [node as TCodeBlockElement, path]);\n }\n\n if (node.type === codeLineType) {\n return CODE_LINE_TO_DECORATIONS.get(node as TElement) || [];\n }\n\n return [];\n },\n})\n .overrideEditor(withCodeBlock)\n .extendTransforms(({ editor }) => ({\n toggle: () => {\n editor.tf.toggleBlock(editor.getType(KEYS.codeBlock));\n },\n }));\n"],"mappings":"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"}
|
package/dist/index.d.ts.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":[],"sources":["../src/lib/BaseCodeBlockPlugin.ts","../src/lib/setCodeBlockToDecorations.ts","../src/lib/withCodeBlock.ts","../src/lib/withInsertDataCodeBlock.ts","../src/lib/withInsertFragmentCodeBlock.ts","../src/lib/withNormalizeCodeBlock.tsx","../src/lib/deserializer/htmlDeserializerCodeBlock.ts","../src/lib/formatter/formatter.ts","../src/lib/formatter/jsonFormatter.ts","../src/lib/queries/getCodeLineEntry.ts","../src/lib/transforms/indentCodeLine.ts","../src/lib/queries/getIndentDepth.ts","../src/lib/queries/isCodeBlockEmpty.ts","../src/lib/queries/isSelectionAtCodeBlockStart.ts","../src/lib/transforms/outdentCodeLine.ts","../src/lib/transforms/deleteStartSpace.ts","../src/lib/transforms/insertCodeBlock.ts","../src/lib/transforms/insertCodeLine.ts","../src/lib/transforms/insertEmptyCodeBlock.ts","../src/lib/transforms/toggleCodeBlock.ts","../src/lib/transforms/unwrapCodeBlock.ts"],"sourcesContent":[],"mappings":";;;;KAmBY,eAAA,GAAkB;;AAA9B;;;EAA8B,eAAA,CAAA,EAAA,MAAA,GAAA,IAAA;EAAY;AAgB1C;AAKA;AAKA;aAde,kBAAkB;;cAIpB;ACtBA,cD2BA,oBC1BE,EAAA,GAAA;AADgC,cDgClC,mBChCkC,EAAA,GAAA;;;cAAlC,0BAA0B,QAAQ,UAAU;iBAoDzC,sBAAA,SACN,iCACY,UAAU,qBAC7B,IAAI,UAAU;iBAoFD,yBAAA,SACN,iCACY,UAAU;ADvIpB,iBCiJI,yBAAA,CDjJW,SAAA,ECiJ0B,iBDjJ1B,CAAA,EAAA,IAAA;;;cERd,eAAe,eAAe;;;cCP9B,yBAAyB;;;cCEzB,6BAA6B;;;;cCQ7B,wBAAwB,eAAe;;;cCVvC,2BAA2B;;;cCE3B;cAGA;cAeA,0BACH;;;EPNE,OAAA,EOUC,iBPVc;CAYM,EAAA,GAAA,IAAA;;;cQ/BpB;cAQA;;;;cCGA,6BAA8B,UAAU,cAAc,qBACzD;;ATOV,CAAA;OSNoC;ATMpC,CAAA,EAAA,GAAY;EAYqB,SAAA,EAAA,GAAA;EAAlB,QAAA,ESmBa,STnBb,CSmBuB,CTnBvB,CAAA;CAZe,GAAA,SAAA;;;KUflB,qBAAA;aACC;YACD;EVaA,WAAA,CAAA,EAAA,MAAe;CAYM;;;;AAIjC;AAKA;AAKA;;cU5Ba,yBACH;;;GACuB;;;cCbpB,yBACH;;GACM;;;;cCHH,2BAA4B;;;;cCA5B,sCAAuC;;;KCDxC,sBAAA;aACC;YACD;AdaZ,CAAA;;AAYe,ccrBF,edqBE,EAAA,CAAA,MAAA,EcpBL,MdoBK,EAAA;EAAA,SAAA;EAAA;AAAA,CAAA,EcnBY,sBdmBZ,EAAA,GAAA,IAAA;;;;cexBF,2BACH;;GACM;;;;;;AfUhB;AAYiC,cgBvBpB,ehBuBoB,EAAA,CAAA,MAAA,EgBtBvB,WhBsBuB,EAAA,kBAAA,CAAA,EgBrBX,IhBqBW,CgBrBN,kBhBqBM,EAAA,OAAA,CAAA,EAAA,GAAA,IAAA;;;;ciB1BpB,yBAA0B;;;KCD3B,sBAAA;;uBAEW,KAAK;AlBa5B,CAAA;;;;;AAgBa,ckBtBA,oBlByBX,EAAA,CAAA,MAAA,EkBxBQ,WlBwBR,EAAA;EAAA,WAAA;EAAA;AAAA,CAAA,CAAA,EkBpBG,sBlBoBH,EAAA,GAAA,IAAA;;;cmBhCW,0BAA2B;;;cCJ3B,0BAA2B"}
|
package/dist/index.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":["SlateEditor","getCodeLineEntry","isSelectionAtCodeBlockStart","editor","selection","api","isExpanded","codeBlock","isStart","anchor","InsertNodesOptions","SlateEditor","TElement","KEYS","insertCodeBlock","editor","insertNodesOptions","Omit","selection","api","isExpanded","matchCodeElements","node","type","codeBlock","codeLine","some","match","isAt","start","tf","insertBreak","setNodes","children","text","wrapNodes","SlateEditor","KEYS","insertCodeLine","editor","indentDepth","selection","indent","repeat","tf","insertNodes","children","text","type","getType","codeLine","InsertNodesOptions","SlateEditor","KEYS","insertCodeBlock","CodeBlockInsertOptions","defaultType","insertNodesOptions","Omit","insertEmptyCodeBlock","editor","getType","p","selection","api","isExpanded","isEmpty","block","tf","insertNodes","create","children","text","type","nextBlock","select","SlateEditor","TElement","KEYS","unwrapCodeBlock","toggleCodeBlock","editor","selection","codeBlockType","getType","codeBlock","codeLineType","codeLine","isActive","api","some","match","type","tf","withoutNormalizing","setNodes","children","wrapNodes","formatJson","code","JSON","stringify","parse","_error","isValidJson","Editor","TCodeBlockElement","formatJson","isValidJson","supportedLanguages","Set","isLangSupported","lang","Boolean","has","isValidSyntax","code","formatCodeBlock","editor","element","api","string","formattedCode","formatCode","tf","insertText","at"],"sources":["../src/lib/queries/isSelectionAtCodeBlockStart.ts","../src/lib/transforms/insertCodeBlock.ts","../src/lib/transforms/insertCodeLine.ts","../src/lib/transforms/insertEmptyCodeBlock.ts","../src/lib/transforms/toggleCodeBlock.ts","../src/lib/formatter/jsonFormatter.ts","../src/lib/formatter/formatter.ts"],"sourcesContent":["import type { SlateEditor } from 'platejs';\n\nimport { getCodeLineEntry } from './getCodeLineEntry';\n\n/** Is the selection at the start of the first code line in a code block */\nexport const isSelectionAtCodeBlockStart = (editor: SlateEditor) => {\n const { selection } = editor;\n\n if (!selection || editor.api.isExpanded()) return false;\n\n const { codeBlock } = getCodeLineEntry(editor) ?? {};\n\n if (!codeBlock) return false;\n\n return editor.api.isStart(selection.anchor, codeBlock[1]);\n};\n","import type { InsertNodesOptions, SlateEditor, TElement } from 'platejs';\n\nimport { KEYS } from 'platejs';\n\n/**\n * Insert a code block: set the node to code line and wrap it with a code block.\n * If the cursor is not at the block start, insert break before.\n */\nexport const insertCodeBlock = (\n editor: SlateEditor,\n insertNodesOptions: Omit<InsertNodesOptions, 'match'> = {}\n) => {\n if (!editor.selection || editor.api.isExpanded()) return;\n\n const matchCodeElements = (node: TElement) =>\n node.type === KEYS.codeBlock || node.type === KEYS.codeLine;\n\n if (\n editor.api.some({\n match: matchCodeElements,\n })\n ) {\n return;\n }\n if (!editor.api.isAt({ start: true })) {\n editor.tf.insertBreak();\n }\n\n editor.tf.setNodes(\n {\n children: [{ text: '' }],\n type: KEYS.codeLine,\n },\n insertNodesOptions\n );\n\n editor.tf.wrapNodes<TElement>(\n {\n children: [],\n type: KEYS.codeBlock,\n },\n insertNodesOptions\n );\n};\n","import type { SlateEditor } from 'platejs';\n\nimport { KEYS } from 'platejs';\n\n/** Insert a code line starting with indentation. */\nexport const insertCodeLine = (editor: SlateEditor, indentDepth = 0) => {\n if (editor.selection) {\n const indent = ' '.repeat(indentDepth);\n\n editor.tf.insertNodes({\n children: [{ text: indent }],\n type: editor.getType(KEYS.codeLine),\n });\n }\n};\n","import { type InsertNodesOptions, type SlateEditor, KEYS } from 'platejs';\n\nimport { insertCodeBlock } from './insertCodeBlock';\n\nexport type CodeBlockInsertOptions = {\n defaultType?: string;\n insertNodesOptions?: Omit<InsertNodesOptions, 'match'>;\n};\n\n/**\n * Called by toolbars to make sure a code-block gets inserted below a paragraph\n * rather than awkwardly splitting the current selection.\n */\nexport const insertEmptyCodeBlock = (\n editor: SlateEditor,\n {\n defaultType = editor.getType(KEYS.p),\n insertNodesOptions,\n }: CodeBlockInsertOptions = {}\n) => {\n if (!editor.selection) return;\n if (\n editor.api.isExpanded() ||\n !editor.api.isEmpty(editor.selection, { block: true })\n ) {\n editor.tf.insertNodes(\n editor.api.create.block({ children: [{ text: '' }], type: defaultType }),\n {\n nextBlock: true,\n select: true,\n ...insertNodesOptions,\n }\n );\n }\n\n insertCodeBlock(editor, insertNodesOptions);\n};\n","import type { SlateEditor, TElement } from 'platejs';\n\nimport { KEYS } from 'platejs';\n\nimport { unwrapCodeBlock } from './unwrapCodeBlock';\n\nexport const toggleCodeBlock = (editor: SlateEditor) => {\n if (!editor.selection) return;\n\n const codeBlockType = editor.getType(KEYS.codeBlock);\n const codeLineType = editor.getType(KEYS.codeLine);\n\n const isActive = editor.api.some({\n match: { type: codeBlockType },\n });\n\n editor.tf.withoutNormalizing(() => {\n unwrapCodeBlock(editor);\n\n if (!isActive) {\n editor.tf.setNodes({\n type: codeLineType,\n });\n\n const codeBlock = {\n children: [],\n type: codeBlockType,\n };\n\n editor.tf.wrapNodes<TElement>(codeBlock);\n }\n });\n};\n","export const formatJson = (code: string): string => {\n try {\n return JSON.stringify(JSON.parse(code), null, 2);\n } catch (_error) {\n return code;\n }\n};\n\nexport const isValidJson = (code: string): boolean => {\n try {\n JSON.parse(code);\n\n return true;\n } catch (_error) {\n return false;\n }\n};\n","import type { Editor, TCodeBlockElement } from 'platejs';\n\nimport { formatJson, isValidJson } from './jsonFormatter';\n\nconst supportedLanguages = new Set(['json']);\n\nexport const isLangSupported = (lang?: string): boolean =>\n Boolean(lang && supportedLanguages.has(lang));\n\nexport const isValidSyntax = (code: string, lang?: string): boolean => {\n if (!isLangSupported(lang)) {\n return false;\n }\n\n switch (lang) {\n case 'json': {\n return isValidJson(code);\n }\n default: {\n return false;\n }\n }\n};\n\nexport const formatCodeBlock = (\n editor: Editor,\n {\n element,\n }: {\n element: TCodeBlockElement;\n }\n) => {\n const { lang } = element;\n\n if (!lang || !isLangSupported(lang)) {\n return;\n }\n\n const code = editor.api.string(element);\n\n if (isValidSyntax(code, lang)) {\n const formattedCode = formatCode(code, lang);\n editor.tf.insertText(formattedCode, { at: element });\n }\n};\n\nconst formatCode = (code: string, lang?: string): string => {\n switch (lang) {\n case 'json': {\n return formatJson(code);\n }\n default: {\n return code;\n }\n }\n};\n"],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":[],"sources":["../../src/react/CodeBlockPlugin.tsx"],"sourcesContent":[],"mappings":";cAQa;AAAA,cAEA,cAFsD,EAAA,GAAA;AAEnE;AAGa,cAAA,eAEX,EAAA,GAAA"}
|
package/dist/react/index.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":["toPlatePlugin","BaseCodeBlockPlugin","BaseCodeLinePlugin","BaseCodeSyntaxPlugin","CodeSyntaxPlugin","CodeLinePlugin","CodeBlockPlugin","plugins"],"sources":["../../src/react/CodeBlockPlugin.tsx"],"sourcesContent":["import { toPlatePlugin } from 'platejs/react';\n\nimport {\n BaseCodeBlockPlugin,\n BaseCodeLinePlugin,\n BaseCodeSyntaxPlugin,\n} from '../lib/BaseCodeBlockPlugin';\n\nexport const CodeSyntaxPlugin = toPlatePlugin(BaseCodeSyntaxPlugin);\n\nexport const CodeLinePlugin = toPlatePlugin(BaseCodeLinePlugin);\n\n/** Enables support for pre-formatted code blocks. */\nexport const CodeBlockPlugin = toPlatePlugin(BaseCodeBlockPlugin, {\n plugins: [CodeLinePlugin, CodeSyntaxPlugin],\n});\n"],"mappings":";;;;AAQA,MAAaI,mBAAmBJ,cAAcG,qBAAqB;AAEnE,MAAaE,iBAAiBL,cAAcE,mBAAmB;;AAG/D,MAAaI,kBAAkBN,cAAcC,qBAAqB,EAChEM,SAAS,CAACF,gBAAgBD,iBAAgB,EAC3C,CAAC"}
|