改用katex进行渲染,支持离线渲染

This commit is contained in:
xunbu
2025-05-26 22:08:14 +08:00
parent 40a4cb0b62
commit 3390a1f967
10 changed files with 9169 additions and 522 deletions

View File

@@ -0,0 +1,120 @@
!function (e, t) {
"object" == typeof exports && "object" == typeof module ? module.exports = t(require("katex")) : "function" == typeof define && define.amd ? define(["katex"], t) : "object" == typeof exports ? exports.renderMathInElement = t(require("katex")) : e.renderMathInElement = t(e.katex)
}("undefined" != typeof self ? self : this, (function (e) {
return function () {
"use strict";
var t = {
757: function (t) {
t.exports = e
}
}, n = {};
function r(e) {
var o = n[e];
if (void 0 !== o) return o.exports;
var i = n[e] = {exports: {}};
return t[e](i, i.exports, r), i.exports
}
r.n = function (e) {
var t = e && e.__esModule ? function () {
return e.default
} : function () {
return e
};
return r.d(t, {a: t}), t
}, r.d = function (e, t) {
for (var n in t) r.o(t, n) && !r.o(e, n) && Object.defineProperty(e, n, {enumerable: !0, get: t[n]})
}, r.o = function (e, t) {
return Object.prototype.hasOwnProperty.call(e, t)
};
var o = {};
r.d(o, {
default: function () {
return p
}
});
var i = r(757), a = r.n(i);
const l = function (e, t, n) {
let r = n, o = 0;
const i = e.length;
for (; r < t.length;) {
const n = t[r];
if (o <= 0 && t.slice(r, r + i) === e) return r;
"\\" === n ? r++ : "{" === n ? o++ : "}" === n && o--, r++
}
return -1
}, s = /^\\begin{/;
var d = function (e, t) {
let n;
const r = [],
o = new RegExp("(" + t.map((e => e.left.replace(/[-/\\^$*+?.()|[\]{}]/g, "\\$&"))).join("|") + ")");
for (; n = e.search(o), -1 !== n;) {
n > 0 && (r.push({type: "text", data: e.slice(0, n)}), e = e.slice(n));
const o = t.findIndex((t => e.startsWith(t.left)));
if (n = l(t[o].right, e, t[o].left.length), -1 === n) break;
const i = e.slice(0, n + t[o].right.length), a = s.test(i) ? i : e.slice(t[o].left.length, n);
r.push({type: "math", data: a, rawData: i, display: t[o].display}), e = e.slice(n + t[o].right.length)
}
return "" !== e && r.push({type: "text", data: e}), r
};
const c = function (e, t) {
const n = d(e, t.delimiters);
if (1 === n.length && "text" === n[0].type) return null;
const r = document.createDocumentFragment();
for (let e = 0; e < n.length; e++) if ("text" === n[e].type) r.appendChild(document.createTextNode(n[e].data)); else {
const o = document.createElement("span");
let i = n[e].data;
t.displayMode = n[e].display;
try {
t.preProcess && (i = t.preProcess(i)), a().render(i, o, t)
} catch (o) {
if (!(o instanceof a().ParseError)) throw o;
t.errorCallback("KaTeX auto-render: Failed to parse `" + n[e].data + "` with ", o), r.appendChild(document.createTextNode(n[e].rawData));
continue
}
r.appendChild(o)
}
return r
}, f = function (e, t) {
for (let n = 0; n < e.childNodes.length; n++) {
const r = e.childNodes[n];
if (3 === r.nodeType) {
let o = r.textContent, i = r.nextSibling, a = 0;
for (; i && i.nodeType === Node.TEXT_NODE;) o += i.textContent, i = i.nextSibling, a++;
const l = c(o, t);
if (l) {
for (let e = 0; e < a; e++) r.nextSibling.remove();
n += l.childNodes.length - 1, e.replaceChild(l, r)
} else n += a
} else if (1 === r.nodeType) {
const e = " " + r.className + " ";
-1 === t.ignoredTags.indexOf(r.nodeName.toLowerCase()) && t.ignoredClasses.every((t => -1 === e.indexOf(" " + t + " "))) && f(r, t)
}
}
};
var p = function (e, t) {
if (!e) throw new Error("No element provided to render");
const n = {};
for (const e in t) t.hasOwnProperty(e) && (n[e] = t[e]);
n.delimiters = n.delimiters || [{left: "$$", right: "$$", display: !0}, {
left: "\\(",
right: "\\)",
display: !1
}, {left: "\\begin{equation}", right: "\\end{equation}", display: !0}, {
left: "\\begin{align}",
right: "\\end{align}",
display: !0
}, {left: "\\begin{alignat}", right: "\\end{alignat}", display: !0}, {
left: "\\begin{gather}",
right: "\\end{gather}",
display: !0
}, {left: "\\begin{CD}", right: "\\end{CD}", display: !0}, {
left: "\\[",
right: "\\]",
display: !0
}], n.ignoredTags = n.ignoredTags || ["script", "noscript", "style", "textarea", "pre", "code", "option"], n.ignoredClasses = n.ignoredClasses || [], n.errorCallback = n.errorCallback || console.error, n.macros = n.macros || {}, f(e, n)
};
return o = o.default
}()
}));

View File

@@ -699,7 +699,7 @@
try {
const response = await fetch("/meta")
let meta = await response.json();
versionDisplay.textContent = `版本号${meta.version}`;
versionDisplay.textContent = `版本号${meta.version}`;
} catch (error) {
console.warn("获取版本号失败", error);
}
@@ -840,11 +840,7 @@
return resp.text();
})
.then(html => {
let finalHtml = html;
if (!html.toLowerCase().includes('/static/pico.css')) {
finalHtml = `<link rel="stylesheet" href="/static/pico.css">\n<style>body{padding:1em;}</style>\n${html}`;
}
const blob = new Blob([finalHtml], {type: 'text/html'});
const blob = new Blob([html], {type: 'text/html'});
const blobUrl = URL.createObjectURL(blob);
translatedPreviewFrame.src = blobUrl;
translatedPreviewFrame.onload = function () {
@@ -882,9 +878,6 @@
})
.then(htmlContent => {
let finalHtml = htmlContent;
if (!htmlContent.toLowerCase().includes('/static/pico.css')) {
finalHtml = `<link rel="stylesheet" href="/static/pico.css">\n<style>body{padding:1em; break-inside: avoid;}</style>\n${htmlContent}`;
}
iframe.onload = () => {
iframe.onload = null;
setTimeout(() => {

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long