Browse Source

Fix issues that cropped up in editor debug

master
buttercat1791 1 year ago
parent
commit
2da83972a0
  1. 35
      src/lib/components/Preview.svelte
  2. 55
      src/lib/parser.ts
  3. 12
      src/routes/new/edit/+page.svelte

35
src/lib/components/Preview.svelte

@ -1,10 +1,43 @@
<script lang="ts"> <script lang="ts">
import Pharos from "$lib/parser"; import Pharos from "$lib/parser";
import { Heading } from "flowbite-svelte";
export let parser: Pharos; export let parser: Pharos;
export let rootIndexId: string; export let rootIndexId: string;
export let depth: number = 0;
const title = parser.getIndexTitle(rootIndexId);
const orderedChildren = parser.getOrderedChildIds(rootIndexId);
const childIndices = parser.getChildIndexIds(rootIndexId);
const childZettels = parser.getChildZettelIds(rootIndexId);
const getHeadingTag = (depth: number) => {
switch (depth) {
case 0:
return "h2";
case 1:
return "h3";
case 2:
return "h4";
case 3:
return "h5";
case 4:
return "h6";
}
};
</script> </script>
<div> <div>
<!-- Custom rendering logic will go here --> {#if depth < 4}
<Heading tag={getHeadingTag(depth)}>{title}</Heading>
{#each orderedChildren as id}
{#if childIndices.includes(id)}
<svelte:self {parser} rootIndexId={id} depth={depth + 1} />
{:else if (childZettels.includes(id))}
{@html parser.getHtmlContent(id)}
{/if}
{/each}
{:else}
{@html parser.getHtmlContent(rootIndexId)}
{/if}
</div> </div>

55
src/lib/parser.ts

@ -1,5 +1,5 @@
import NDK, { NDKEvent } from '@nostr-dev-kit/ndk'; import NDK, { NDKEvent } from '@nostr-dev-kit/ndk';
import { import asciidoctor, {
AbstractBlock, AbstractBlock,
AbstractNode, AbstractNode,
Asciidoctor, Asciidoctor,
@ -28,7 +28,7 @@ interface IndexMetadata {
* @class * @class
* @augments Asciidoctor * @augments Asciidoctor
*/ */
export default class Pharos extends Asciidoctor { export default class Pharos {
/** /**
* Key to terminology used in the class: * Key to terminology used in the class:
* *
@ -50,8 +50,12 @@ export default class Pharos extends Asciidoctor {
* hierarchically to form the Abstract Syntax Tree (AST) representation of the document. * hierarchically to form the Abstract Syntax Tree (AST) representation of the document.
*/ */
private asciidoctor: Asciidoctor;
private ndk: NDK; private ndk: NDK;
private blockCounter: number = 0;
/** /**
* The HTML content of the converted document. * The HTML content of the converted document.
*/ */
@ -95,12 +99,12 @@ export default class Pharos extends Asciidoctor {
// #region Public API // #region Public API
constructor(ndk: NDK) { constructor(ndk: NDK) {
super(); this.asciidoctor = asciidoctor();
this.ndk = ndk; this.ndk = ndk;
const pharos = this; const pharos = this;
this.Extensions.register(function () { this.asciidoctor.Extensions.register(function () {
const registry = this; const registry = this;
registry.treeProcessor(function () { registry.treeProcessor(function () {
const dsl = this; const dsl = this;
@ -113,7 +117,7 @@ export default class Pharos extends Asciidoctor {
} }
parse(content: string, options?: ProcessorOptions | undefined): void { parse(content: string, options?: ProcessorOptions | undefined): void {
this.html = this.convert(content, options) as string | Document | undefined; this.html = this.asciidoctor.convert(content, options) as string | Document | undefined;
} }
getEvents(pubkey: string): NDKEvent[] { getEvents(pubkey: string): NDKEvent[] {
@ -134,7 +138,7 @@ export default class Pharos extends Asciidoctor {
* @remarks The root index ID may be used to retrieve metadata or children from the root index. * @remarks The root index ID may be used to retrieve metadata or children from the root index.
*/ */
getRootIndexId(): string { getRootIndexId(): string {
return this.rootIndexId!; return this.rootNodeId!;
} }
/** /**
@ -162,9 +166,16 @@ export default class Pharos extends Asciidoctor {
} }
/** /**
* @returns The converted content of the zettel with the given ID. * @returns The IDs of any child nodes in the order in which they should be rendered.
*/ */
getZettelHtml(id: string): string { getOrderedChildIds(id: string): string[] {
return Array.from(this.indexToChildEventsMap.get(id)!);
}
/**
* @returns The converted content of the node with the given ID.
*/
getHtmlContent(id: string): string {
const block = this.nodes.get(id) as Block; const block = this.nodes.get(id) as Block;
return block.convert(); return block.convert();
} }
@ -181,6 +192,11 @@ export default class Pharos extends Asciidoctor {
*/ */
private treeProcessor(treeProcessor: Extensions.TreeProcessor, document: Document) { private treeProcessor(treeProcessor: Extensions.TreeProcessor, document: Document) {
this.rootNodeId = document.getId(); this.rootNodeId = document.getId();
if (!this.rootNodeId) {
this.rootNodeId = this.normalizeNodeId(document.getTitle() ?? 'root');
document.setId(this.rootNodeId);
}
this.nodes.set(this.rootNodeId, document); this.nodes.set(this.rootNodeId, document);
this.eventToKindMap.set(this.rootNodeId, 30040); this.eventToKindMap.set(this.rootNodeId, 30040);
this.indexToChildEventsMap.set(this.rootNodeId, new Set<string>()); this.indexToChildEventsMap.set(this.rootNodeId, new Set<string>());
@ -194,8 +210,8 @@ export default class Pharos extends Asciidoctor {
continue; continue;
} }
if (block instanceof Section) { if (block.getContext() === 'section') {
const children = this.processSection(block); const children = this.processSection(block as Section);
nodeQueue.push(...children); nodeQueue.push(...children);
} else { } else {
this.processBlock(block as Block); this.processBlock(block as Block);
@ -211,7 +227,10 @@ export default class Pharos extends Asciidoctor {
* @remarks Sections are mapped as kind 30040 indexToChildEventsMap by default. * @remarks Sections are mapped as kind 30040 indexToChildEventsMap by default.
*/ */
private processSection(section: Section): AbstractNode[] { private processSection(section: Section): AbstractNode[] {
const sectionId = section.getId(); let sectionId = section.getId();
if (!sectionId) {
sectionId = this.normalizeNodeId(section.getTitle() ?? `${section.getContext()}_${this.blockCounter++}`);
}
// Prevent duplicates. // Prevent duplicates.
if (this.nodes.has(sectionId)) { if (this.nodes.has(sectionId)) {
@ -244,7 +263,12 @@ export default class Pharos extends Asciidoctor {
* @remarks Blocks are mapped as kind 30041 zettels by default. * @remarks Blocks are mapped as kind 30041 zettels by default.
*/ */
private processBlock(block: Block): void { private processBlock(block: Block): void {
const blockId = block.getId(); // Obtain or generate a unique ID for the block.
let blockId = block.getId();
if (!blockId) {
blockId = `${this.normalizeNodeId(block.getContext())}_${this.blockCounter++}`;
block.setId(blockId);
}
// Prevent duplicates. // Prevent duplicates.
if (this.nodes.has(blockId)) { if (this.nodes.has(blockId)) {
@ -426,6 +450,13 @@ export default class Pharos extends Asciidoctor {
// #region Utility Functions // #region Utility Functions
private normalizeNodeId(input: string): string {
return input
.toLowerCase()
.replace(/\s+/g, '_') // Replace spaces with underscores.
.replace(/[^a-z0-9\_]/g, ''); // Remove non-alphanumeric characters except underscores.
}
/** /**
* Normalizes a string to lower-kebab-case. * Normalizes a string to lower-kebab-case.
* @param input The string to normalize. * @param input The string to normalize.

12
src/routes/new/edit/+page.svelte

@ -6,13 +6,15 @@
import Pharos from "$lib/parser"; import Pharos from "$lib/parser";
import { ndk } from "$lib/ndk"; import { ndk } from "$lib/ndk";
const parser: Pharos = new Pharos($ndk); let parser: Pharos;
let isEditing: boolean = true; let isEditing: boolean = true;
$: rootIndexId = parser?.getRootIndexId();
const showPreview = () => { const showPreview = () => {
isEditing = false; parser = new Pharos($ndk);
parser.parse($editorText); parser.parse($editorText);
isEditing = false;
}; };
const hidePreview = () => { const hidePreview = () => {
@ -51,7 +53,9 @@
<CodeOutline class='w-6 h-6' /> <CodeOutline class='w-6 h-6' />
</ToolbarButton> </ToolbarButton>
</Toolbar> </Toolbar>
<Preview parser={parser} rootIndexId={parser.getRootIndexId()} /> {#if rootIndexId}
<Preview {parser} {rootIndexId} />
{/if}
</div> </div>
{/if} {/if}
</div> </div>

Loading…
Cancel
Save