markdown2html/src/katex.ts

68 lines
1.6 KiB
TypeScript

import { marked } from 'marked';
import katex = require('katex');
import type { KatexOptions } from 'katex';
import { MarkdownOptions } from './render';
export interface KatexToken extends marked.Tokens.Generic {
text: string;
}
export function katex_block_ext(renderer: marked.Renderer, opts: MarkdownOptions) : marked.TokenizerExtension & marked.RendererExtension {
return {
name: 'katex_block',
level: 'block',
start: (src) => src.match(/^\$\$/)?.index,
tokenizer(src, tokens) {
const rule = /^\$\$((?:[^\$]|\$(?!\$))+)\$\$/;
const match = rule.exec(src);
if (match) {
return {
type: 'katex_block',
raw: match[0],
text: match[1]
};
}
},
renderer(token: KatexToken) {
const katex_opts: KatexOptions = {
displayMode: true, // true == "block"
output: 'html',
macros: opts.katex_macros,
};
return (katex as any).renderToString(token.text, katex_opts);
}
};
}
export function katex_inline_ext(renderer: marked.Renderer, opts: MarkdownOptions) : marked.TokenizerExtension & marked.RendererExtension {
return {
name: 'katex_inline',
level: 'inline',
start: (src) => src.match(/\$/)?.index,
tokenizer(src, tokens) {
const rule = /^\$([^\n\s](?:[^\n\$]*[^\n\s])?)\$/;
const match = rule.exec(src);
if (match) {
return {
type: 'katex_inline',
raw: match[0],
text: match[1]
};
}
},
renderer(token: KatexToken) {
const katex_opts: KatexOptions = {
displayMode: false, // false == "inline"
output: 'html',
macros: opts.katex_macros,
};
return (katex as any).renderToString(token.text, katex_opts);
}
};
}