643 lines
No EOL
22 KiB
JavaScript
643 lines
No EOL
22 KiB
JavaScript
let questionid="";
|
|
window.onload = () => resetState();
|
|
document.addEventListener('DOMContentLoaded', () => {
|
|
resetState();
|
|
jsonDataFetched = false;
|
|
});
|
|
|
|
function handleYearSort() {
|
|
const yearButton = document.getElementById('sort-by-year');
|
|
if (yearButton.textContent === 'Year ▼') {
|
|
sortQuestionsByYear('asc');
|
|
yearButton.textContent = 'Year ▲';
|
|
} else {
|
|
sortQuestionsByYear('desc');
|
|
yearButton.textContent = 'Year ▼';
|
|
}
|
|
}
|
|
|
|
function toggleModal(){document.getElementById("modal").classList.toggle("hidden")}
|
|
function toggleMS(){document.getElementById("markscheme").classList.toggle("hidden")}
|
|
function toggleR(){document.getElementById("report").classList.toggle("hidden")}
|
|
function toggleHelp(){document.getElementById("helpmenu").classList.toggle("hidden")}
|
|
function toggleDownAllQs(){document.getElementById("addalltoPDFbtn").classList.remove('hidden');document.getElementById("generatePDFbtn").classList.remove('hidden')}
|
|
|
|
function toggleDarkMode() {
|
|
var body = document.body;
|
|
var head = document.head;
|
|
var toggleButton = document.getElementById("darkmodebtn");
|
|
|
|
if (localStorage.getItem("darkMode") === "disabled") {
|
|
body.classList.add("dark-mode");
|
|
head.classList.add("dark-mode");
|
|
localStorage.setItem("darkMode", "enabled");
|
|
toggleButton.innerText = "Light Mode";
|
|
} else {
|
|
body.classList.remove("dark-mode");
|
|
head.classList.remove("dark-mode");
|
|
localStorage.setItem("darkMode", "disabled");
|
|
toggleButton.innerText = "Dark Mode";
|
|
}
|
|
}
|
|
|
|
document.addEventListener("DOMContentLoaded", () => {
|
|
const darkModeStatus = localStorage.getItem("darkMode");
|
|
const prefersDarkScheme = window.matchMedia("(prefers-color-scheme: dark)").matches;
|
|
|
|
if (darkModeStatus === "enabled") {
|
|
document.body.classList.add("dark-mode");
|
|
document.head.classList.add("dark-mode");
|
|
document.getElementById("darkmodebtn").innerText = "Light Mode";
|
|
} else if (darkModeStatus === "disabled") {
|
|
document.body.classList.remove("dark-mode");
|
|
document.head.classList.remove("dark-mode");
|
|
document.getElementById("darkmodebtn").innerText = "Dark Mode";
|
|
} else if (prefersDarkScheme) {
|
|
document.body.classList.add("dark-mode");
|
|
document.head.classList.add("dark-mode");
|
|
document.getElementById("darkmodebtn").innerText = "Light Mode";
|
|
localStorage.setItem("darkMode", "enabled");
|
|
} else {
|
|
document.body.classList.remove("dark-mode");
|
|
document.head.classList.remove("dark-mode");
|
|
document.getElementById("darkmodebtn").innerText = "Dark Mode";
|
|
localStorage.setItem("darkMode", "disabled");
|
|
}
|
|
});
|
|
|
|
function startRandomTimerLoop() {
|
|
var randomTime = Math.floor(11 * Math.random()) + 20;
|
|
setTimeout(() => {
|
|
alert("Provided by pirateIB\nhttps://pirateib.xyz");
|
|
startRandomTimerLoop();
|
|
}, 60 * randomTime * 1000);
|
|
}
|
|
window.onload = function() {
|
|
setTimeout(() => {
|
|
startRandomTimerLoop();
|
|
}, 300000);
|
|
};
|
|
|
|
/*function generatePDF() {
|
|
const selectedQuestionIds = JSON.parse(sessionStorage.getItem("selectedQuestionIds")) || [];
|
|
if (0 === selectedQuestionIds.length) return alert("Select some questions first!");
|
|
const printWindow = window.open("", "_blank");
|
|
printWindow.document.write('\n <html>\n <head>\n <title>QuestionBank Test</title>\n <link rel="stylesheet" href="../assets/style.css">\n <style>\n @media print { body { overflow: hidden; } ::-webkit-scrollbar { display: none; } }\n </style>\n </head>\n <body>\n ');
|
|
let concatenatedHTML = "";
|
|
let markschemesHTML = '';
|
|
selectedQuestionIds.forEach((questionId => {
|
|
const questionDiv = document.getElementById(questionId),
|
|
h3 = questionDiv.querySelector("h3"),
|
|
squareContainer = questionDiv.querySelector(".square-container");
|
|
concatenatedHTML += h3.outerHTML + squareContainer.outerHTML
|
|
const msDiv = document.querySelector(`[id*="markscheme-${questionId}"]`);
|
|
const cloneMsDiv = msDiv.cloneNode(true);
|
|
cloneMsDiv.classList.remove('hidden');
|
|
markschemesHTML += h3.outerHTML + cloneMsDiv.outerHTML;
|
|
})), printWindow.document.write(`<h2>Questions</h2><br>${concatenatedHTML}<div style="page-break-after: always;"></div><h2>Markschemes</h2><br>${markschemesHTML}`), printWindow.document.write("\n </body>\n </html>\n "), printWindow.document.close();
|
|
setTimeout(() => {
|
|
printWindow.print(), printWindow.onafterprint = () => printWindow.close();
|
|
}, 1000);}*/
|
|
|
|
function generatePDF() {
|
|
const selectedQuestionIds = JSON.parse(sessionStorage.getItem("selectedQuestionIds")) || [];
|
|
if (0 === selectedQuestionIds.length) return alert("Select some questions first!");
|
|
|
|
// Prompt the user for including markschemes
|
|
let includeMarkschemes = null;
|
|
while (includeMarkschemes !== "yes" && includeMarkschemes !== "no") {
|
|
includeMarkschemes = prompt("Do you want to include markschemes? (yes/no)").toLowerCase();
|
|
if (includeMarkschemes !== "yes" && includeMarkschemes !== "no") {
|
|
alert("Please answer 'yes' or 'no'.");
|
|
}
|
|
}
|
|
|
|
const printWindow = window.open("", "_blank");
|
|
printWindow.document.write('\n <html>\n <head>\n <title>QuestionBank Test</title>\n <link rel="stylesheet" href="../assets/style.css">\n <style>\n @media print { body { overflow: hidden; } ::-webkit-scrollbar { display: none; } }\n </style>\n </head>\n <body>\n ');
|
|
|
|
let concatenatedHTML = "";
|
|
let markschemesHTML = '';
|
|
|
|
selectedQuestionIds.forEach((questionId) => {
|
|
const questionDiv = document.getElementById(questionId),
|
|
h3 = questionDiv.querySelector("h3"),
|
|
squareContainer = questionDiv.querySelector(".square-container");
|
|
concatenatedHTML += h3.outerHTML + squareContainer.outerHTML;
|
|
|
|
if (includeMarkschemes === "yes") {
|
|
const msDiv = document.querySelector(`[id*="markscheme-${questionId} "]`);
|
|
const cloneMsDiv = msDiv.cloneNode(true);
|
|
cloneMsDiv.classList.remove('hidden');
|
|
markschemesHTML += h3.outerHTML + cloneMsDiv.outerHTML;
|
|
}
|
|
});
|
|
|
|
printWindow.document.write(`<h2>Questions</h2><br>${concatenatedHTML}`);
|
|
|
|
if (includeMarkschemes === "yes") {
|
|
printWindow.document.write(`<div style="page-break-after: always;"></div><h2>Markschemes</h2><br>${markschemesHTML}`);
|
|
}
|
|
|
|
printWindow.document.write("\n </body>\n </html>\n ");
|
|
printWindow.document.close();
|
|
|
|
setTimeout(() => {
|
|
printWindow.print();
|
|
printWindow.onafterprint = () => printWindow.close();
|
|
}, 1000);
|
|
}
|
|
|
|
|
|
function addalltoPDF() {
|
|
const buttons = document.querySelectorAll('.btn-secondary');
|
|
buttons.forEach(button => {
|
|
if (button.textContent.trim() === "Add to PDF" && !button.parentElement.parentElement.classList.contains('hidden')) {
|
|
button.click();
|
|
}
|
|
});
|
|
}
|
|
|
|
let jsonDataFetched = false;
|
|
let jsonData = null;
|
|
let currentFileName = null;
|
|
let topics = [];
|
|
let subtopics = [];
|
|
let sortOrder = null;
|
|
|
|
const domCache = {
|
|
rightCol: document.getElementById("right-col"),
|
|
msbox: document.getElementById("markscheme-box"),
|
|
reportbox: document.getElementById("report-box"),
|
|
msbox2: document.getElementById("markscheme-box2"),
|
|
repbox2: document.getElementById("report-box2"),
|
|
leftCol: document.getElementById('left-col')
|
|
};
|
|
|
|
document.addEventListener('keydown', (event) => {
|
|
if (event.key === 'Escape') {
|
|
const modal = document.getElementById('modal');
|
|
const helpmenu = document.getElementById('helpmenu');
|
|
if (modal && !modal.classList.contains('hidden')) {
|
|
toggleModal();
|
|
} else if (helpmenu && !helpmenu.classList.contains('hidden')) {
|
|
toggleHelp();
|
|
}
|
|
}
|
|
});
|
|
|
|
const fileNameMap = {
|
|
'bioqb': 'Biology QB.json',
|
|
'bioqb25-split': 'Biology 2025 QB split.json',
|
|
'bioqb25-full': 'Biology 2025 QB full.json',
|
|
'bmqb': 'Business Management QB.json',
|
|
'chemqb': 'Chemistry QB.json',
|
|
'chemqb25-split': 'Chemistry 2025 QB split.json',
|
|
'chemqb25-full': 'Chemistry 2025 QB full.json',
|
|
'compsciqb': 'Computer Science QB.json',
|
|
'destechqb': 'Design Technology QB.json',
|
|
'digsocqb': 'Digital Society QB.json',
|
|
'econqb': 'Economics QB.json',
|
|
'essqb': 'ESS QB.json',
|
|
'geoqb': 'Geography QB.json',
|
|
'histqb': 'History QB.json',
|
|
'mathaaqb': 'Math AA QB.json',
|
|
'mathaiqb': 'Math AI QB.json',
|
|
'phyqb': 'Physics QB.json',
|
|
'phyqb25-split': 'Physics 2025 QB split.json',
|
|
'phyqb25-full': 'Physics 2025 QB full.json',
|
|
'psychqb': 'Psychology QB.json',
|
|
'sehsqb': 'SEHS QB.json'
|
|
};
|
|
|
|
function createSVGElement(questionid) {
|
|
const svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
|
|
const attributes = {
|
|
"width": "2rem",
|
|
"height": "2rem",
|
|
"viewBox": "0 0 24 24",
|
|
"fill": "none",
|
|
"stroke": "currentColor",
|
|
"stroke-width": "2",
|
|
"stroke-linecap": "round",
|
|
"stroke-linejoin": "round"
|
|
};
|
|
|
|
Object.entries(attributes).forEach(([key, value]) => {
|
|
svg.setAttribute(key, value);
|
|
});
|
|
|
|
svg.classList.add("cursor-pointer", "text-primary", "hidden");
|
|
svg.innerHTML = `
|
|
<rect x="3" y="3" width="18" height="18" rx="2" ry="2"></rect>
|
|
<line x1="9" y1="9" x2="15" y2="15"></line>
|
|
<line x1="15" y1="9" x2="9" y2="15"></line>
|
|
`;
|
|
return svg;
|
|
}
|
|
|
|
function showLoading() {
|
|
document.getElementById('loadingBanner').style.display = 'block';
|
|
}
|
|
|
|
function hideLoading() {
|
|
document.getElementById('loadingBanner').style.display = 'none';
|
|
}
|
|
|
|
function openDatabase() {
|
|
return new Promise((resolve, reject) => {
|
|
const request = indexedDB.open('myDatabase', 1);
|
|
|
|
request.onupgradeneeded = (event) => {
|
|
const db = event.target.result;
|
|
if (!db.objectStoreNames.contains('myStore')) {
|
|
db.createObjectStore('myStore');
|
|
}
|
|
};
|
|
|
|
request.onsuccess = (event) => {
|
|
resolve(event.target.result);
|
|
};
|
|
|
|
request.onerror = (event) => {
|
|
reject('Error opening database:', event.target.error);
|
|
};
|
|
});
|
|
}
|
|
|
|
async function loadJSON(filename) {
|
|
showLoading();
|
|
const db = await openDatabase();
|
|
|
|
const cachedData = await new Promise((resolve, reject) => {
|
|
const transaction = db.transaction('myStore', 'readonly');
|
|
const store = transaction.objectStore('myStore');
|
|
const request = store.get(filename);
|
|
|
|
request.onsuccess = (event) => {
|
|
resolve(event.target.result);
|
|
};
|
|
|
|
request.onerror = (event) => {
|
|
reject('Error fetching data from IndexedDB:', event.target.error);
|
|
};
|
|
});
|
|
|
|
if (cachedData) {
|
|
hideLoading();
|
|
processData(cachedData, filename);
|
|
return;
|
|
}
|
|
|
|
try {
|
|
const response = await fetch(`../assets/jsonqb/${filename}`);
|
|
if (!response.ok) {
|
|
throw new Error('Network response was not ok');
|
|
}
|
|
const data = await response.json();
|
|
|
|
await new Promise((resolve, reject) => {
|
|
const transaction = db.transaction('myStore', 'readwrite');
|
|
const store = transaction.objectStore('myStore');
|
|
const request = store.put(data, filename);
|
|
|
|
request.onsuccess = () => {
|
|
resolve();
|
|
};
|
|
|
|
request.onerror = (event) => {
|
|
reject('Error storing data in IndexedDB:', event.target.error);
|
|
};
|
|
});
|
|
sessionStorage.setItem('selectedQuestionIds', '[]');
|
|
|
|
setTimeout(() => {
|
|
processData(data, filename);
|
|
hideLoading();
|
|
sessionStorage.setItem('selectedQuestionIds', '[]');
|
|
}, 0);
|
|
|
|
} catch (error) {
|
|
console.error('Error fetching JSON:', error);
|
|
hideLoading();
|
|
sessionStorage.setItem('selectedQuestionIds', '[]');
|
|
}
|
|
}
|
|
|
|
// Extract year from question ID (e.g., "23M.1A.SL.TZ2.39" -> 2023)
|
|
function extractYear(questionId) {
|
|
if (!questionId || typeof questionId !== 'string') return 0;
|
|
|
|
// Extract the first two digits
|
|
const match = questionId.match(/^(\d{2})/);
|
|
if (!match) return 0;
|
|
|
|
let year = parseInt(match[1], 10);
|
|
|
|
// Convert to four-digit year
|
|
if (year >= 0 && year <= 99) {
|
|
if (year >= 0 && year <= 25) {
|
|
year += 2000; // 00-25 -> 2000-2025
|
|
} else {
|
|
year += 1900; // 26-99 -> 1926-1999
|
|
}
|
|
}
|
|
|
|
return year;
|
|
}
|
|
|
|
// Function to sort questions by year
|
|
function sortQuestionsByYear(direction = 'asc') {
|
|
if (!jsonData || !Array.isArray(jsonData)) return;
|
|
|
|
sortOrder = direction;
|
|
|
|
const sortedData = [...jsonData].sort((a, b) => {
|
|
const yearA = extractYear(a.question_id);
|
|
const yearB = extractYear(b.question_id);
|
|
|
|
return direction === 'asc' ? yearA - yearB : yearB - yearA;
|
|
});
|
|
|
|
// Clear the existing questions
|
|
clearDisplayedQuestions();
|
|
|
|
// Re-render with sorted data
|
|
renderQuestions(sortedData);
|
|
|
|
// Maintain topic filter states
|
|
document.querySelectorAll('input[name="topic"]:checked').forEach(checkbox => {
|
|
document.querySelectorAll(`div[class*="${checkbox.value}"]`)
|
|
.forEach(div => div.classList.remove('hidden'));
|
|
});
|
|
}
|
|
|
|
// Function to reset sorting and show questions in original order
|
|
function resetSorting() {
|
|
if (!jsonData || !Array.isArray(jsonData)) return;
|
|
|
|
sortOrder = null;
|
|
document.getElementById('sort-by-year').textContent = 'Year ▼';
|
|
|
|
// Clear the existing questions
|
|
clearDisplayedQuestions();
|
|
|
|
// Re-render with original data
|
|
renderQuestions(jsonData);
|
|
|
|
// Maintain topic filter states
|
|
document.querySelectorAll('input[name="topic"]:checked').forEach(checkbox => {
|
|
document.querySelectorAll(`div[class*="${checkbox.value}"]`)
|
|
.forEach(div => div.classList.remove('hidden'));
|
|
});
|
|
}
|
|
|
|
// Function to clear displayed questions but keep filters
|
|
function clearDisplayedQuestions() {
|
|
domCache.rightCol.innerHTML = '';
|
|
document.querySelectorAll('#markscheme-box > div').forEach(el => el.remove());
|
|
document.querySelectorAll('#report-box > div').forEach(el => el.remove());
|
|
document.querySelectorAll('#markscheme-box2 > svg').forEach(el => el.remove());
|
|
document.querySelectorAll('#report-box2 > svg').forEach(el => el.remove());
|
|
}
|
|
|
|
// Function to render questions (extracted from processData)
|
|
function renderQuestions(data) {
|
|
const fragment = document.createDocumentFragment();
|
|
|
|
data.forEach(item => {
|
|
const {
|
|
Question: question,
|
|
question_id: questionid,
|
|
Markscheme: markscheme,
|
|
'Examiners report': report,
|
|
topics,
|
|
subtopics,
|
|
year
|
|
} = item;
|
|
|
|
const bigQuestionBox = document.createElement("div");
|
|
bigQuestionBox.id = questionid;
|
|
|
|
const allClasses = [
|
|
...topics.map(t => t.trim()).filter(t => t),
|
|
...(typeof subtopics === "string" ? [subtopics] : []),
|
|
"hidden"
|
|
];
|
|
|
|
bigQuestionBox.classList.add(...allClasses);
|
|
|
|
const btnContainer = document.createElement("div");
|
|
btnContainer.classList.add("btn-container");
|
|
|
|
function toggleMScont(questionid) {
|
|
const markschemeContainer = document.getElementById(`markscheme-${questionid} ${currentFileName}`);
|
|
const toggleMSSvg = document.querySelector(`#markscheme-box2 svg`); // Simplified selector
|
|
toggleMSSvg.classList.toggle('hidden');
|
|
markschemeContainer.classList.toggle('hidden');
|
|
activeQuestionId = markschemeContainer.classList.contains('hidden') ? null : questionid;
|
|
}
|
|
|
|
function toggleRepcont(questionid) {
|
|
const reportContainer = document.getElementById(`report-${questionid} ${currentFileName}`);
|
|
const toggleRepSvg = document.querySelector(`#report-box2 svg`); // Simplified selector
|
|
toggleRepSvg.classList.toggle('hidden');
|
|
reportContainer.classList.toggle('hidden');
|
|
activeQuestionId = reportContainer.classList.contains('hidden') ? null : questionid;
|
|
}
|
|
|
|
const buttons = [
|
|
{ text: "Markscheme", handler: () => { toggleMS(); toggleMScont(questionid); } },
|
|
{ text: "Examiners report", handler: () => { toggleR(); toggleRepcont(questionid); } },
|
|
{ text: "Add to PDF", handler: createPDFButtonHandler(questionid) }
|
|
].map(createButton);
|
|
|
|
buttons.forEach(button => btnContainer.appendChild(button));
|
|
|
|
// Add full year from extracted two-digit year
|
|
const extractedYear = extractYear(questionid);
|
|
const yearText = extractedYear ? `<h4><b>Year:</b> ${extractedYear}</h4>` : '';
|
|
|
|
const content = `
|
|
<h3>${questionid}</h3>
|
|
${yearText}
|
|
<h4><b>Topics:</b> ${topics.join(', ')}</h4>
|
|
<h4><b>Subtopics:</b> ${subtopics.join(', ')}</h4>
|
|
<div class="square-container">${question}</div>
|
|
`;
|
|
|
|
bigQuestionBox.innerHTML = content;
|
|
bigQuestionBox.querySelector('h3').after(btnContainer);
|
|
|
|
if (markscheme) {
|
|
createContainer('markscheme', questionid, currentFileName, markscheme, domCache.msbox);
|
|
}
|
|
|
|
if (report) {
|
|
createContainer('report', questionid, currentFileName, report, domCache.reportbox);
|
|
}
|
|
|
|
const toggleMSSvg = createSVGElement(questionid);
|
|
const toggleRepSvg = createSVGElement(questionid);
|
|
|
|
domCache.msbox2.appendChild(toggleMSSvg);
|
|
domCache.repbox2.appendChild(toggleRepSvg);
|
|
|
|
let activeQuestionId = null;
|
|
|
|
const handleToggle = () => {
|
|
if (activeQuestionId) {
|
|
const markschemeContainer = document.getElementById(`markscheme-${activeQuestionId} ${currentFileName}`);
|
|
const reportContainer = document.getElementById(`report-${activeQuestionId} ${currentFileName}`);
|
|
|
|
if (markschemeContainer && !markschemeContainer.classList.contains('hidden')) {
|
|
toggleMSSvg.classList.toggle('hidden');
|
|
toggleMS();
|
|
markschemeContainer.classList.toggle('hidden');
|
|
activeQuestionId = null;
|
|
} else if (reportContainer && !reportContainer.classList.contains('hidden')) {
|
|
toggleRepSvg.classList.toggle('hidden');
|
|
toggleR();
|
|
reportContainer.classList.toggle('hidden');
|
|
activeQuestionId = null;
|
|
}
|
|
}
|
|
};
|
|
|
|
toggleMSSvg.addEventListener('click', handleToggle);
|
|
toggleRepSvg.addEventListener('click', handleToggle);
|
|
|
|
fragment.appendChild(bigQuestionBox);
|
|
});
|
|
|
|
domCache.rightCol.appendChild(fragment);
|
|
updateSquareContainers();
|
|
toggleDownAllQs();
|
|
}
|
|
|
|
function processData(data, filename) {
|
|
jsonData = data; // Store the data for sorting
|
|
jsonDataFetched = true;
|
|
currentFileName = filename;
|
|
|
|
topics = [...new Set(data.flatMap(item => item.topics))].sort();
|
|
subtopics = [...new Set(data.flatMap(item => item.subtopics))].sort();
|
|
renderTopics();
|
|
|
|
// Reset sort button state
|
|
const yearButton = document.getElementById('sort-by-year');
|
|
if (yearButton) {
|
|
yearButton.textContent = 'Year ▼';
|
|
}
|
|
|
|
// Render questions
|
|
renderQuestions(data);
|
|
}
|
|
|
|
function createButton({ text, handler, className = 'btn-secondary' }) {
|
|
const button = document.createElement("button");
|
|
button.classList.add(className);
|
|
button.textContent = text;
|
|
button.addEventListener('click', handler);
|
|
return button;
|
|
}
|
|
|
|
function createPDFButtonHandler(questionid) {
|
|
return function () {
|
|
let selectedQuestionIds = JSON.parse(sessionStorage.getItem('selectedQuestionIds')) || [];
|
|
const index = selectedQuestionIds.indexOf(questionid);
|
|
if (index !== -1) {
|
|
selectedQuestionIds.splice(index, 1);
|
|
this.style.backgroundColor = 'rgb(66 165 245)';
|
|
this.textContent = 'Add to PDF';
|
|
} else {
|
|
selectedQuestionIds.push(questionid);
|
|
this.style.backgroundColor = '#e03b3b';
|
|
this.textContent = 'Added!';
|
|
}
|
|
sessionStorage.setItem('selectedQuestionIds', JSON.stringify(selectedQuestionIds));
|
|
};
|
|
}
|
|
|
|
function createContainer(type, questionid, filename, content, parent) {
|
|
const container = document.createElement("div");
|
|
container.classList.add("square-container", "hidden");
|
|
container.id = `${type}-${questionid} ${filename}`;
|
|
container.innerHTML = content;
|
|
parent.appendChild(container);
|
|
}
|
|
|
|
function renderTopics() {
|
|
const fragment = document.createDocumentFragment();
|
|
|
|
topics.forEach(topic => {
|
|
const label = document.createElement('label');
|
|
label.classList.add('topic-label');
|
|
|
|
const checkbox = document.createElement('input');
|
|
checkbox.type = 'checkbox';
|
|
checkbox.name = 'topic';
|
|
checkbox.value = topic;
|
|
|
|
checkbox.addEventListener('change', () => {
|
|
document.querySelectorAll(`div[class*="${topic}"]`)
|
|
.forEach(div => div.classList.toggle('hidden'));
|
|
});
|
|
|
|
label.append(checkbox, topic);
|
|
fragment.appendChild(label);
|
|
});
|
|
|
|
domCache.leftCol.appendChild(fragment);
|
|
}
|
|
|
|
function updateSquareContainers() {
|
|
document.querySelectorAll('.square-container').forEach(container => {
|
|
const firstChild = container.children[0];
|
|
if (firstChild?.classList.contains('question')) {
|
|
firstChild.classList.replace('question', 'specification');
|
|
}
|
|
});
|
|
}
|
|
|
|
document.addEventListener('DOMContentLoaded', () => {
|
|
document.addEventListener('click', event => {
|
|
const filename = fileNameMap[event.target.id];
|
|
if (!filename) return;
|
|
|
|
if (jsonDataFetched && filename !== currentFileName) {
|
|
resetState();
|
|
loadJSON(filename);
|
|
} else if (!jsonDataFetched) {
|
|
loadJSON(filename);
|
|
}
|
|
});
|
|
});
|
|
|
|
function resetState() {
|
|
domCache.rightCol.innerHTML = '';
|
|
document.querySelectorAll('.topic-label').forEach(label => label.remove());
|
|
const yearButton = document.getElementById('sort-by-year');
|
|
if (yearButton) {
|
|
yearButton.textContent = 'Year ▼';
|
|
}
|
|
sessionStorage.setItem('selectedQuestionIds', '[]');
|
|
sortOrder = null;
|
|
}
|
|
|
|
function toggleDarkMode() {
|
|
var body = document.body;
|
|
var head = document.head;
|
|
var toggleButton = document.getElementById("darkmodebtn");
|
|
|
|
if (localStorage.getItem("darkMode") === "disabled") {
|
|
body.classList.add("dark-mode");
|
|
head.classList.add("dark-mode");
|
|
localStorage.setItem("darkMode", "enabled");
|
|
toggleButton.innerText = "Light Mode";
|
|
} else {
|
|
body.classList.remove("dark-mode");
|
|
head.classList.remove("dark-mode");
|
|
localStorage.setItem("darkMode", "disabled");
|
|
toggleButton.innerText = "Dark Mode";
|
|
}
|
|
} |