MediaWiki:BibTest.js
From Illustrations in German Translations of Mark Twain's Works
Note: After publishing, you may have to bypass your browser's cache to see the changes.
- Firefox / Safari: Hold Shift while clicking Reload, or press either Ctrl-F5 or Ctrl-R (⌘-R on a Mac)
- Google Chrome: Press Ctrl-Shift-R (⌘-Shift-R on a Mac)
- Edge: Hold Ctrl while clicking Refresh, or press Ctrl-F5.
(function () {
const DATA_URL = "/index.php?title=BibliographyData&action=raw&ctype=application/json";
let DATA = [];
let ACTIVE_TAGS = new Set();
// MediaWiki-safe init
if (document.readyState === "loading") {
document.addEventListener("DOMContentLoaded", init);
} else {
init();
}
async function init() {
try {
await loadData();
renderTags();
renderList();
} catch (e) {
console.error("Bibliography load error:", e);
}
}
// -------------------- LOAD DATA --------------------
async function loadData() {
const res = await fetch(DATA_URL);
DATA = await res.json();
// alphabetisch sortieren
DATA.sort((a, b) =>
(a.title || "").localeCompare(b.title || "")
);
}
// -------------------- TAGS --------------------
function renderTags() {
const tagBar = document.getElementById("tagBar");
if (!tagBar) return;
tagBar.innerHTML = "";
const tags = new Set();
DATA.forEach(item => {
(item.tags || []).forEach(t => tags.add(t));
});
[...tags].sort().forEach(tag => {
const el = document.createElement("span");
el.className = "tag inactive";
el.textContent = tag;
el.onclick = () => toggleTag(tag);
tagBar.appendChild(el);
});
}
function toggleTag(tag) {
if (ACTIVE_TAGS.has(tag)) {
ACTIVE_TAGS.delete(tag);
} else {
ACTIVE_TAGS.add(tag);
}
updateTagStyles();
renderList();
}
function updateTagStyles() {
document.querySelectorAll("#tagBar .tag").forEach(el => {
const t = el.textContent;
if (ACTIVE_TAGS.has(t)) {
el.classList.add("active");
el.classList.remove("inactive");
} else {
el.classList.remove("active");
el.classList.add("inactive");
}
});
}
// -------------------- LIST --------------------
function renderList() {
const container = document.getElementById("listView");
if (!container) return;
container.innerHTML = "";
let filtered = DATA;
if (ACTIVE_TAGS.size > 0) {
filtered = DATA.filter(item =>
(item.tags || []).some(t => ACTIVE_TAGS.has(t))
);
}
filtered.forEach(item => {
const div = document.createElement("div");
div.className = "bib-entry";
div.innerHTML = renderEntry(item);
container.appendChild(div);
});
}
// -------------------- ENTRY --------------------
function renderEntry(item) {
const authors = (item.authors || [])
.map(a => typeof a === "string"
? a
: (a.family || "Unknown"))
.join(", ");
const tags = (item.tags || []).map(t =>
`<span class="tag ${ACTIVE_TAGS.has(t) ? 'active' : 'inactive'}">
${t}
</span>`
).join(" ");
return `
<h3>
${authors || "Unknown"}.
<i>${item.title || "Untitled"}</i>.
${item.year || ""}
</h3>
<div class="bib-tags">${tags}</div>
${item.container ? `<p><em>${item.container}</em></p>` : ""}
${item.url ? `<a href="${item.url}" target="_blank">Source</a>` : ""}
`;
}
})();