feat(js): tabs.js — tab activation + expand-to-active-modal

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
mwiegand 2026-05-17 21:14:34 +02:00
parent be3a00a8f5
commit eb0c1a52db
No known key found for this signature in database

View file

@ -0,0 +1,62 @@
// l4d2web/l4d2web/static/js/tabs.js
// Tabbed strips: any element with [data-tab-strip] activates the first
// [role="tab"] in DOM order (or the one carrying [aria-selected="true"]
// if present) on load, and switches panes on click. The strip's
// [data-active-tab] attribute mirrors the active tab name and is read
// by the expand-to-modal handler.
(function () {
function activateTab(strip, name) {
strip.querySelectorAll('[role="tab"]').forEach((t) => {
const on = t.dataset.tab === name;
t.setAttribute("aria-selected", on ? "true" : "false");
t.tabIndex = on ? 0 : -1;
});
strip.querySelectorAll('[role="tabpanel"]').forEach((p) => {
p.hidden = p.dataset.tab !== name;
});
strip.dataset.activeTab = name;
}
function activeTabName(strip) {
const selected = strip.querySelector('[role="tab"][aria-selected="true"]');
if (selected) return selected.dataset.tab;
const first = strip.querySelector('[role="tab"]');
return first ? first.dataset.tab : null;
}
function initStrips(root) {
(root || document).querySelectorAll("[data-tab-strip]").forEach((strip) => {
// Initialise active tab on load.
const name = activeTabName(strip);
if (name) activateTab(strip, name);
// Bind tab clicks.
strip.addEventListener("click", (ev) => {
const tab = ev.target.closest('[role="tab"]');
if (tab && strip.contains(tab)) {
activateTab(strip, tab.dataset.tab);
}
});
// Bind expand button: opens <dialog id="<tabname>-modal">.
const expand = strip.querySelector(".strip-expand");
if (expand) {
expand.addEventListener("click", () => {
const name = strip.dataset.activeTab;
if (!name) return;
const dlg = document.getElementById(`${name}-modal`);
if (dlg && typeof dlg.showModal === "function" && !dlg.open) {
dlg.showModal();
}
});
}
});
}
if (document.readyState === "loading") {
document.addEventListener("DOMContentLoaded", () => initStrips());
} else {
initStrips();
}
})();