Fixes #263: Implement TOC

This commit is contained in:
Zef Hemel
2023-11-25 13:40:56 +01:00
parent cd27739336
commit 1ac494765f
10 changed files with 190 additions and 6 deletions
@@ -5,19 +5,34 @@ import { PanelConfig } from "../types.ts";
import { createWidgetSandboxIFrame } from "../components/widget_sandbox_iframe.ts";
class IFrameWidget extends WidgetType {
widgetHeightCacheKey: string;
constructor(
readonly editor: Client,
readonly panel: PanelConfig,
readonly className: string,
) {
super();
this.widgetHeightCacheKey = `${this.editor.currentPage!}#${this.className}`;
}
toDOM(): HTMLElement {
const iframe = createWidgetSandboxIFrame(this.editor, null, this.panel);
iframe.classList.add("sb-ps-iframe");
const iframe = createWidgetSandboxIFrame(
this.editor,
this.widgetHeightCacheKey,
this.panel,
);
iframe.classList.add(this.className);
return iframe;
}
get estimatedHeight(): number {
const height = this.editor.space.getCachedWidgetHeight(
this.widgetHeightCacheKey,
);
console.log("GOt height", height);
return height;
}
eq(other: WidgetType): boolean {
return this.panel.html ===
(other as IFrameWidget).panel.html &&
@@ -26,15 +41,29 @@ class IFrameWidget extends WidgetType {
}
}
export function postScriptPlugin(editor: Client) {
export function postScriptPrefacePlugin(editor: Client) {
return decoratorStateField((state: EditorState) => {
const widgets: any[] = [];
if (editor.ui.viewState.panels.preface.html) {
widgets.push(
Decoration.widget({
widget: new IFrameWidget(
editor,
editor.ui.viewState.panels.preface,
"sb-preface-iframe",
),
side: -1,
block: true,
}).range(0),
);
}
if (editor.ui.viewState.panels.ps.html) {
widgets.push(
Decoration.widget({
widget: new IFrameWidget(
editor,
editor.ui.viewState.panels.ps,
"sb-ps-iframe",
),
side: 1,
block: true,
+2 -2
View File
@@ -40,7 +40,7 @@ import {
pasteLinkExtension,
} from "./cm_plugins/editor_paste.ts";
import { TextChange } from "$sb/lib/change.ts";
import { postScriptPlugin } from "./cm_plugins/post_script.ts";
import { postScriptPrefacePlugin } from "./cm_plugins/preface_ps.ts";
import { languageFor } from "../common/languages.ts";
import { plugLinter } from "./cm_plugins/lint.ts";
@@ -144,7 +144,7 @@ export function createEditorState(
plugLinter(client),
// lintGutter(),
// gutters(),
postScriptPlugin(client),
postScriptPrefacePlugin(client),
lineWrapper([
{ selector: "ATXHeading1", class: "sb-line-h1" },
{ selector: "ATXHeading2", class: "sb-line-h2" },
+7
View File
@@ -154,6 +154,13 @@ body {
border-radius: 5px;
}
.sb-preface-iframe {
width: 100%;
margin-top: 10px;
border: 1px solid var(--editor-directive-background-color);
border-radius: 5px;
}
#sb-main {
display: flex;
+1
View File
@@ -186,6 +186,7 @@ export function editorSyscalls(editor: Client): SysCallMapping {
],
});
}
editor.editorView.focus();
},
"editor.setSelection": (_ctx, from: number, to: number) => {
editor.editorView.dispatch({
+1
View File
@@ -91,6 +91,7 @@ export const initialViewState: AppViewState = {
bhs: {},
modal: {},
ps: {},
preface: {},
},
allPages: [],
commands: new Map(),