All checks were successful
Deploy Quartz site to GitHub Pages / build (push) Successful in 1m21s
74 lines
2.5 KiB
JavaScript
74 lines
2.5 KiB
JavaScript
MathJax.Hub.Config({
|
|
config: ["MMLorHTML.js"],
|
|
jax: ["input/TeX", "output/HTML-CSS", "output/NativeMML"],
|
|
extensions: ["MathMenu.js", "MathZoom.js"]
|
|
});
|
|
|
|
let indexData = null;
|
|
|
|
async function loadIndex() {
|
|
if (indexData) return indexData;
|
|
const res = await fetch("/index.json");
|
|
indexData = await res.json();
|
|
return indexData;
|
|
}
|
|
|
|
const templates = {
|
|
folder: i => `<li><details><summary>${i.key}</summary>${i.inner}</details></li>`,
|
|
file: i => `<li><a href="${i.href}">${i.title}</a></li>`
|
|
};
|
|
|
|
function renderTree(data) {
|
|
const items = Object.entries(data).map(([key, note]) => {
|
|
if (key === "children") return null;
|
|
if (note.children) return { type: "folder", key, inner: renderTree(note.children) };
|
|
if (note.folder && note.filename) {
|
|
const title = note.title || note.filename.replace(/\.md$/, "");
|
|
let href = title + ".html";
|
|
if (note.folder !== ".") href = `${note.folder}/${href}`;
|
|
href = "/" + href;
|
|
return { type: "file", href, title };
|
|
}
|
|
return null;
|
|
}).filter((i) => i !== null);
|
|
|
|
// Sort: folders first (alphabetically), then files (alphabetically)
|
|
// Use natural sorting for numbers (1, 2, 10 instead of 1, 10, 2)
|
|
items.sort((a, b) => {
|
|
if (a.type !== b.type) return a.type === "folder" ? -1 : 1;
|
|
const nameA = (a.type === "folder" ? a.key : a.title);
|
|
const nameB = (b.type === "folder" ? b.key : b.title);
|
|
return nameA.localeCompare(nameB, undefined, { numeric: true, sensitivity: "base" });
|
|
});
|
|
|
|
return `<ul>${items.map(i => templates[i.type](i)).join("")}</ul>`;
|
|
}
|
|
|
|
loadIndex().then(data => {
|
|
const sidebar = document.querySelector(".sidebar");
|
|
if (sidebar) {
|
|
sidebar.innerHTML = renderTree(data);
|
|
|
|
// Find and highlight the current page link
|
|
const currentPath = window.location.pathname;
|
|
const links = sidebar.querySelectorAll("a");
|
|
for (const link of links) {
|
|
const linkPath = new URL(link.href, window.location.origin).pathname;
|
|
if (linkPath === currentPath) {
|
|
link.classList.add("active");
|
|
|
|
// Expand all parent <details> elements
|
|
let parent = link.parentElement;
|
|
while (parent && parent !== sidebar) {
|
|
if (parent.tagName === "DETAILS") {
|
|
parent.open = true;
|
|
}
|
|
parent = parent.parentElement;
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
});
|
|
|