forked from typeup/renderer
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathRenderer.ts
More file actions
37 lines (35 loc) · 1.13 KB
/
Renderer.ts
File metadata and controls
37 lines (35 loc) · 1.13 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
import * as dom from "@typeup/dom"
import * as math from "./math"
export type renderFunction = (renderer: Renderer, node: dom.Node) => Promise<string>
export class Renderer {
private constructor(private variables: { [name: string]: string } = {}) {
}
getVariable(name: string): string {
return this.variables[name]
}
setVariable(name: string, value: string) {
this.variables[name] = value
}
async render(node: dom.Node | dom.Node[]): Promise<string> {
let result: string
if (Array.isArray(node))
result = (await Promise.all(node.map(n => this.render(n)))).reduce<string[]>((r, e) => Array.isArray(e) ? [...r, ...e] : [...r, e], []).join("")
else {
const render = renderers[node.class]
result = render ? await render(this, node) : ""
if (node.class == "Document")
result = await math.typeset(result)
}
return result
}
scope(): Renderer {
return new Renderer({ ...this.variables })
}
static create(): Renderer {
return new Renderer({})
}
}
const renderers: { [className: string]: renderFunction } = {}
export function addRenderer(className: string, render: renderFunction) {
renderers[className] = render
}