@blankdotpage/cake 0.1.2 → 0.1.4
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/cake/core/runtime.d.ts +50 -13
- package/dist/cake/engine/cake-engine.d.ts +15 -0
- package/dist/cake/engine/selection/selection-layout-dom.d.ts +7 -0
- package/dist/cake/extensions/blockquote/blockquote.d.ts +1 -2
- package/dist/cake/extensions/bold/bold.d.ts +1 -2
- package/dist/cake/extensions/combined-emphasis/combined-emphasis.d.ts +1 -2
- package/dist/cake/extensions/heading/heading.d.ts +1 -2
- package/dist/cake/extensions/image/image.d.ts +1 -2
- package/dist/cake/extensions/index.d.ts +1 -0
- package/dist/cake/extensions/italic/italic.d.ts +1 -2
- package/dist/cake/extensions/link/link-popover.d.ts +6 -0
- package/dist/cake/extensions/link/link.d.ts +15 -2
- package/dist/cake/extensions/list/list.d.ts +11 -2
- package/dist/cake/extensions/pipe-link/pipe-link.d.ts +1 -2
- package/dist/cake/extensions/scrollbar/index.d.ts +1 -2
- package/dist/cake/extensions/strikethrough/strikethrough.d.ts +1 -2
- package/dist/cake/react/CakeEditor.d.ts +2 -0
- package/dist/cake/test/harness.d.ts +12 -0
- package/dist/index.cjs +662 -179
- package/dist/index.js +662 -179
- package/package.json +1 -1
|
@@ -10,6 +10,7 @@ export type OverlayExtensionContext = {
|
|
|
10
10
|
start: number;
|
|
11
11
|
end: number;
|
|
12
12
|
} | null;
|
|
13
|
+
executeCommand: (command: EditCommand) => boolean;
|
|
13
14
|
contentRoot?: HTMLElement;
|
|
14
15
|
overlayRoot?: HTMLElement;
|
|
15
16
|
toOverlayRect?: (rect: DOMRectReadOnly) => {
|
|
@@ -37,33 +38,46 @@ export type SerializeInlineResult = {
|
|
|
37
38
|
source: string;
|
|
38
39
|
map: CursorSourceMap;
|
|
39
40
|
};
|
|
40
|
-
|
|
41
|
+
/** Insert command */
|
|
42
|
+
export type InsertCommand = {
|
|
41
43
|
type: "insert";
|
|
42
44
|
text: string;
|
|
43
|
-
}
|
|
45
|
+
};
|
|
46
|
+
/** Commands that can be applied directly by the engine */
|
|
47
|
+
export type ApplyEditCommand = InsertCommand | {
|
|
44
48
|
type: "insert-line-break";
|
|
45
|
-
} | {
|
|
46
|
-
type: "exit-block-wrapper";
|
|
47
49
|
} | {
|
|
48
50
|
type: "delete-backward";
|
|
49
51
|
} | {
|
|
50
52
|
type: "delete-forward";
|
|
51
|
-
}
|
|
53
|
+
};
|
|
54
|
+
/** Structural edit commands that modify document structure */
|
|
55
|
+
export type StructuralEditCommand = ApplyEditCommand | {
|
|
56
|
+
type: "exit-block-wrapper";
|
|
57
|
+
};
|
|
58
|
+
/** Core edit commands handled by the runtime */
|
|
59
|
+
export type CoreEditCommand = StructuralEditCommand | {
|
|
52
60
|
type: "indent";
|
|
53
61
|
} | {
|
|
54
62
|
type: "outdent";
|
|
55
|
-
} | {
|
|
56
|
-
type: "toggle-bullet-list";
|
|
57
|
-
} | {
|
|
58
|
-
type: "toggle-numbered-list";
|
|
59
63
|
} | {
|
|
60
64
|
type: "toggle-inline";
|
|
61
65
|
marker: string;
|
|
62
|
-
} | {
|
|
63
|
-
type: "wrap-link";
|
|
64
|
-
url?: string;
|
|
65
|
-
openPopover?: boolean;
|
|
66
66
|
};
|
|
67
|
+
/** Base type for extension-defined commands */
|
|
68
|
+
export type ExtensionCommand = {
|
|
69
|
+
type: string;
|
|
70
|
+
[key: string]: any;
|
|
71
|
+
};
|
|
72
|
+
/**
|
|
73
|
+
* Edit commands can be core commands or extension-defined commands.
|
|
74
|
+
* Extensions handle their own commands in onEdit before the core processes them.
|
|
75
|
+
*/
|
|
76
|
+
export type EditCommand = CoreEditCommand | ExtensionCommand;
|
|
77
|
+
/** Type guard to check if a command is a structural edit */
|
|
78
|
+
export declare function isStructuralEdit(command: EditCommand): command is StructuralEditCommand;
|
|
79
|
+
/** Type guard to check if a command can be applied directly by the engine */
|
|
80
|
+
export declare function isApplyEditCommand(command: EditCommand): command is ApplyEditCommand;
|
|
67
81
|
export type EditResult = {
|
|
68
82
|
source: string;
|
|
69
83
|
selection: Selection;
|
|
@@ -114,6 +128,29 @@ export type CakeExtension = {
|
|
|
114
128
|
renderBlock?: (block: Block, context: DomRenderContext) => Node | Node[] | null;
|
|
115
129
|
renderOverlay?: (context: OverlayExtensionContext) => ReactElement | null;
|
|
116
130
|
};
|
|
131
|
+
/**
|
|
132
|
+
* Extension config with typed custom commands.
|
|
133
|
+
*/
|
|
134
|
+
export type ExtensionConfig<TCommand extends ExtensionCommand> = Omit<CakeExtension, "onEdit"> & {
|
|
135
|
+
onEdit?: (command: EditCommand | TCommand, state: RuntimeState) => EditResult | EditCommand | TCommand | null;
|
|
136
|
+
};
|
|
137
|
+
/**
|
|
138
|
+
* Define an extension with typed custom commands.
|
|
139
|
+
*
|
|
140
|
+
* @example
|
|
141
|
+
* type MyCommand = { type: "my-command"; value: number };
|
|
142
|
+
* export const myExtension = defineExtension<MyCommand>({
|
|
143
|
+
* name: "my-extension",
|
|
144
|
+
* onEdit(command, state) {
|
|
145
|
+
* if (command.type === "my-command") {
|
|
146
|
+
* // command is narrowed to MyCommand here
|
|
147
|
+
* console.log(command.value);
|
|
148
|
+
* }
|
|
149
|
+
* return null;
|
|
150
|
+
* },
|
|
151
|
+
* });
|
|
152
|
+
*/
|
|
153
|
+
export declare function defineExtension<TCommand extends ExtensionCommand>(extension: ExtensionConfig<TCommand>): CakeExtension;
|
|
117
154
|
export type RuntimeState = {
|
|
118
155
|
source: string;
|
|
119
156
|
selection: Selection;
|
|
@@ -11,6 +11,14 @@ type EngineOptions = {
|
|
|
11
11
|
readOnly?: boolean;
|
|
12
12
|
spellCheckEnabled?: boolean;
|
|
13
13
|
};
|
|
14
|
+
export type RenderPerf = {
|
|
15
|
+
totalMs: number;
|
|
16
|
+
renderAndMapMs: number;
|
|
17
|
+
applySelectionMs: number;
|
|
18
|
+
didUpdateDom: boolean;
|
|
19
|
+
blockCount: number;
|
|
20
|
+
runCount: number;
|
|
21
|
+
};
|
|
14
22
|
export declare class CakeEngine {
|
|
15
23
|
private container;
|
|
16
24
|
private runtime;
|
|
@@ -40,6 +48,8 @@ export declare class CakeEngine {
|
|
|
40
48
|
private caretBlinkTimeoutId;
|
|
41
49
|
private overlayUpdateId;
|
|
42
50
|
private scrollCaretIntoViewId;
|
|
51
|
+
private selectionRectElements;
|
|
52
|
+
private lastSelectionRects;
|
|
43
53
|
private onChange?;
|
|
44
54
|
private onSelectionChange?;
|
|
45
55
|
private readOnly;
|
|
@@ -48,8 +58,10 @@ export declare class CakeEngine {
|
|
|
48
58
|
private placeholderRoot;
|
|
49
59
|
private lastFocusRect;
|
|
50
60
|
private verticalNavGoalX;
|
|
61
|
+
private lastRenderPerf;
|
|
51
62
|
private history;
|
|
52
63
|
private pendingClickHit;
|
|
64
|
+
getLastRenderPerf(): RenderPerf | null;
|
|
53
65
|
private isEventTargetInContentRoot;
|
|
54
66
|
private handleBeforeInputBound;
|
|
55
67
|
private handleInputBound;
|
|
@@ -76,12 +88,14 @@ export declare class CakeEngine {
|
|
|
76
88
|
private selectionDragState;
|
|
77
89
|
private pointerDownPosition;
|
|
78
90
|
private hasMovedSincePointerDown;
|
|
91
|
+
private lastTouchTime;
|
|
79
92
|
constructor(options: EngineOptions);
|
|
80
93
|
destroy(): void;
|
|
81
94
|
setReadOnly(readOnly: boolean): void;
|
|
82
95
|
setSpellCheckEnabled(enabled: boolean): void;
|
|
83
96
|
getValue(): string;
|
|
84
97
|
getSelection(): Selection;
|
|
98
|
+
getCursorLength(): number;
|
|
85
99
|
getFocusRect(): SelectionRect | null;
|
|
86
100
|
getContainer(): HTMLElement;
|
|
87
101
|
getContentRoot(): HTMLElement | null;
|
|
@@ -179,6 +193,7 @@ export declare class CakeEngine {
|
|
|
179
193
|
private scheduleOverlayUpdate;
|
|
180
194
|
private flushOverlayUpdate;
|
|
181
195
|
private ensureOverlayRoot;
|
|
196
|
+
private selectionRectsEqual;
|
|
182
197
|
private ensureExtensionsRoot;
|
|
183
198
|
private updateExtensionsOverlayPosition;
|
|
184
199
|
private updateSelectionOverlay;
|
|
@@ -17,6 +17,13 @@ export declare function measureLayoutModelFromDom(params: {
|
|
|
17
17
|
root: HTMLElement;
|
|
18
18
|
container: HTMLElement;
|
|
19
19
|
}): LayoutModel | null;
|
|
20
|
+
export declare function measureLayoutModelRangeFromDom(params: {
|
|
21
|
+
lines: LineInfo[];
|
|
22
|
+
root: HTMLElement;
|
|
23
|
+
container: HTMLElement;
|
|
24
|
+
startLineIndex: number;
|
|
25
|
+
endLineIndex: number;
|
|
26
|
+
}): LayoutModel | null;
|
|
20
27
|
export declare function getLineElement(root: HTMLElement, lineIndex: number): HTMLElement | null;
|
|
21
28
|
export declare function resolveDomPosition(lineElement: HTMLElement, offsetInLine: number): {
|
|
22
29
|
node: Node;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const blockquoteExtension: CakeExtension;
|
|
1
|
+
export declare const blockquoteExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const boldExtension: CakeExtension;
|
|
1
|
+
export declare const boldExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const combinedEmphasisExtension: CakeExtension;
|
|
1
|
+
export declare const combinedEmphasisExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const headingExtension: CakeExtension;
|
|
1
|
+
export declare const headingExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const imageExtension: CakeExtension;
|
|
1
|
+
export declare const imageExtension: import("../../..").CakeExtension;
|
|
@@ -10,4 +10,5 @@ import { listExtension } from "./list/list";
|
|
|
10
10
|
import { scrollbarExtension } from "./scrollbar";
|
|
11
11
|
import { strikethroughExtension } from "./strikethrough/strikethrough";
|
|
12
12
|
export { boldExtension, combinedEmphasisExtension, linkExtension, pipeLinkExtension, blockquoteExtension, italicExtension, headingExtension, imageExtension, listExtension, scrollbarExtension, strikethroughExtension, };
|
|
13
|
+
export declare const bundledExtensionsWithoutImage: import("../..").CakeExtension[];
|
|
13
14
|
export declare const bundledExtensions: import("../..").CakeExtension[];
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const italicExtension: CakeExtension;
|
|
1
|
+
export declare const italicExtension: import("../../..").CakeExtension;
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { EditCommand } from "../../core/runtime";
|
|
1
2
|
export declare function CakeLinkPopover(params: {
|
|
2
3
|
container: HTMLElement;
|
|
3
4
|
contentRoot: HTMLElement;
|
|
@@ -7,4 +8,9 @@ export declare function CakeLinkPopover(params: {
|
|
|
7
8
|
width: number;
|
|
8
9
|
height: number;
|
|
9
10
|
};
|
|
11
|
+
getSelection: () => {
|
|
12
|
+
start: number;
|
|
13
|
+
end: number;
|
|
14
|
+
} | null;
|
|
15
|
+
executeCommand: (command: EditCommand) => boolean;
|
|
10
16
|
}): import("react/jsx-runtime").JSX.Element | null;
|
|
@@ -1,2 +1,15 @@
|
|
|
1
|
-
|
|
2
|
-
export
|
|
1
|
+
/** Command to wrap selected text in a link */
|
|
2
|
+
export type WrapLinkCommand = {
|
|
3
|
+
type: "wrap-link";
|
|
4
|
+
url?: string;
|
|
5
|
+
openPopover?: boolean;
|
|
6
|
+
};
|
|
7
|
+
/** Command to remove link formatting */
|
|
8
|
+
export type UnlinkCommand = {
|
|
9
|
+
type: "unlink";
|
|
10
|
+
start: number;
|
|
11
|
+
end: number;
|
|
12
|
+
};
|
|
13
|
+
/** All link extension commands */
|
|
14
|
+
export type LinkCommand = WrapLinkCommand | UnlinkCommand;
|
|
15
|
+
export declare const linkExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1,11 @@
|
|
|
1
|
-
|
|
2
|
-
export
|
|
1
|
+
/** Command to toggle bullet list formatting */
|
|
2
|
+
export type ToggleBulletListCommand = {
|
|
3
|
+
type: "toggle-bullet-list";
|
|
4
|
+
};
|
|
5
|
+
/** Command to toggle numbered list formatting */
|
|
6
|
+
export type ToggleNumberedListCommand = {
|
|
7
|
+
type: "toggle-numbered-list";
|
|
8
|
+
};
|
|
9
|
+
/** All list extension commands */
|
|
10
|
+
export type ListCommand = ToggleBulletListCommand | ToggleNumberedListCommand;
|
|
11
|
+
export declare const listExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const pipeLinkExtension: CakeExtension;
|
|
1
|
+
export declare const pipeLinkExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const scrollbarExtension: CakeExtension;
|
|
1
|
+
export declare const scrollbarExtension: import("../../..").CakeExtension;
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export declare const strikethroughExtension: CakeExtension;
|
|
1
|
+
export declare const strikethroughExtension: import("../../..").CakeExtension;
|
|
@@ -22,6 +22,7 @@ export interface CakeEditorProps {
|
|
|
22
22
|
style?: React.CSSProperties;
|
|
23
23
|
extensions?: CakeExtension[];
|
|
24
24
|
onBlur?: (event?: FocusEvent) => void;
|
|
25
|
+
disableImageExtension?: boolean;
|
|
25
26
|
}
|
|
26
27
|
export interface CakeEditorRef {
|
|
27
28
|
element: HTMLElement | null;
|
|
@@ -36,6 +37,7 @@ export interface CakeEditorRef {
|
|
|
36
37
|
start: number;
|
|
37
38
|
end: number;
|
|
38
39
|
} | null;
|
|
40
|
+
getCursorLength: () => number;
|
|
39
41
|
insertText: (text: string) => void;
|
|
40
42
|
replaceText: (oldText: string, newText: string) => void;
|
|
41
43
|
}
|
|
@@ -12,6 +12,14 @@ export interface CaretInfo {
|
|
|
12
12
|
left: number;
|
|
13
13
|
height: number;
|
|
14
14
|
}
|
|
15
|
+
export interface VisualRowInfo {
|
|
16
|
+
startOffset: number;
|
|
17
|
+
endOffset: number;
|
|
18
|
+
top: number;
|
|
19
|
+
bottom: number;
|
|
20
|
+
left: number;
|
|
21
|
+
right: number;
|
|
22
|
+
}
|
|
15
23
|
export interface TestHarness {
|
|
16
24
|
container: HTMLDivElement;
|
|
17
25
|
contentRoot: HTMLElement;
|
|
@@ -24,6 +32,7 @@ export interface TestHarness {
|
|
|
24
32
|
getCharRect(offset: number, lineIndex?: number): DOMRect;
|
|
25
33
|
getSelectionRects(): SelectionRectInfo[];
|
|
26
34
|
getCaretRect(): CaretInfo | null;
|
|
35
|
+
getVisualRows(lineIndex?: number): VisualRowInfo[];
|
|
27
36
|
clickLeftOf(offset: number, lineIndex?: number): Promise<void>;
|
|
28
37
|
clickRightOf(offset: number, lineIndex?: number): Promise<void>;
|
|
29
38
|
clickAt(offset: number, lineIndex?: number): Promise<void>;
|
|
@@ -42,6 +51,9 @@ export interface TestHarness {
|
|
|
42
51
|
alt?: boolean;
|
|
43
52
|
}): Promise<void>;
|
|
44
53
|
focus(): Promise<void>;
|
|
54
|
+
assertCaretOnVisualRow(rowIndex: number, lineIndex?: number): void;
|
|
55
|
+
assertCaretAtEndOfVisualRow(rowIndex: number, lineIndex?: number): void;
|
|
56
|
+
assertCaretAtStartOfVisualRow(rowIndex: number, lineIndex?: number): void;
|
|
45
57
|
destroy(): void;
|
|
46
58
|
}
|
|
47
59
|
export interface TestHarnessOptions {
|