/**
* Add Toggle Buttons to elements
*/
let toggleChevron = `
`;
var initToggleItems = () => {
var itemsToToggle = document.querySelectorAll(togglebuttonSelector);
console.log(`[togglebutton]: Adding toggle buttons to ${itemsToToggle.length} items`)
// Add the button to each admonition and hook up a callback to toggle visibility
itemsToToggle.forEach((item, index) => {
if (item.classList.contains("admonition")) {
// If it's an admonition block, then we'll add a button inside
// Generate unique IDs for this item
var toggleID = `toggle-${index}`;
var buttonID = `button-${toggleID}`;
item.setAttribute('id', toggleID);
if (!item.classList.contains("toggle")){
item.classList.add("toggle");
}
// This is the button that will be added to each item to trigger the toggle
var collapseButton = `
`;
title = item.querySelector(".admonition-title")
title.insertAdjacentHTML("beforeend", collapseButton);
thisButton = document.getElementById(buttonID);
// Add click handlers for the button + admonition title (if admonition)
admonitionTitle = document.querySelector(`#${toggleID} > .admonition-title`)
if (admonitionTitle) {
// If an admonition, then make the whole title block clickable
admonitionTitle.addEventListener('click', toggleClickHandler);
admonitionTitle.dataset.target = toggleID
admonitionTitle.dataset.button = buttonID
} else {
// If not an admonition then we'll listen for the button click
thisButton.addEventListener('click', toggleClickHandler);
}
// Now hide the item for this toggle button unless explicitly noted to show
if (!item.classList.contains("toggle-shown")) {
toggleHidden(thisButton);
}
} else {
// If not an admonition, wrap the block in a block
// Define the structure of the details block and insert it as a sibling
var detailsBlock = `
${toggleChevron}
${toggleHintShow}`;
item.insertAdjacentHTML("beforebegin", detailsBlock);
// Now move the toggle-able content inside of the details block
details = item.previousElementSibling
details.appendChild(item)
item.classList.add("toggle-details__container")
// Set up a click trigger to change the text as needed
details.addEventListener('click', (click) => {
let parent = click.target.parentElement;
if (parent.tagName.toLowerCase() == "details") {
summary = parent.querySelector("summary");
details = parent;
} else {
summary = parent;
details = parent.parentElement;
}
// Update the inner text for the proper hint
if (details.open) {
summary.querySelector("span.toggle-details__summary-text").innerText = toggleHintShow;
} else {
summary.querySelector("span.toggle-details__summary-text").innerText = toggleHintHide;
}
});
// If we have a toggle-shown class, open details block should be open
if (item.classList.contains("toggle-shown")) {
details.click();
}
}
})
};
// This should simply add / remove the collapsed class and change the button text
var toggleHidden = (button) => {
target = button.dataset['target']
var itemToToggle = document.getElementById(target);
if (itemToToggle.classList.contains("toggle-hidden")) {
itemToToggle.classList.remove("toggle-hidden");
button.classList.remove("toggle-button-hidden");
} else {
itemToToggle.classList.add("toggle-hidden");
button.classList.add("toggle-button-hidden");
}
}
var toggleClickHandler = (click) => {
// Be cause the admonition title is clickable and extends to the whole admonition
// We only look for a click event on this title to trigger the toggle.
if (click.target.classList.contains("admonition-title")) {
button = click.target.querySelector(".toggle-button");
} else if (click.target.classList.contains("tb-icon")) {
// We've clicked the icon and need to search up one parent for the button
button = click.target.parentElement;
} else if (click.target.tagName == "polyline") {
// We've clicked the SVG elements inside the button, need to up 2 layers
button = click.target.parentElement.parentElement;
} else if (click.target.classList.contains("toggle-button")) {
// We've clicked the button itself and so don't need to do anything
button = click.target;
} else {
console.log(`[togglebutton]: Couldn't find button for ${click.target}`)
}
target = document.getElementById(button.dataset['button']);
toggleHidden(target);
}
// If we want to blanket-add toggle classes to certain cells
var addToggleToSelector = () => {
const selector = "";
if (selector.length > 0) {
document.querySelectorAll(selector).forEach((item) => {
item.classList.add("toggle");
})
}
}
// Helper function to run when the DOM is finished
const sphinxToggleRunWhenDOMLoaded = cb => {
if (document.readyState != 'loading') {
cb()
} else if (document.addEventListener) {
document.addEventListener('DOMContentLoaded', cb)
} else {
document.attachEvent('onreadystatechange', function() {
if (document.readyState == 'complete') cb()
})
}
}
sphinxToggleRunWhenDOMLoaded(addToggleToSelector)
sphinxToggleRunWhenDOMLoaded(initToggleItems)
/** Toggle details blocks to be open when printing */
if (toggleOpenOnPrint == "true") {
window.addEventListener("beforeprint", () => {
// Open the details
document.querySelectorAll("details.toggle-details").forEach((el) => {
el.dataset["togglestatus"] = el.open;
el.open = true;
});
// Open the admonitions
document.querySelectorAll(".admonition.toggle.toggle-hidden").forEach((el) => {
console.log(el);
el.querySelector("button.toggle-button").click();
el.dataset["toggle_after_print"] = "true";
});
});
window.addEventListener("afterprint", () => {
// Re-close the details that were closed
document.querySelectorAll("details.toggle-details").forEach((el) => {
el.open = el.dataset["togglestatus"] == "true";
delete el.dataset["togglestatus"];
});
// Re-close the admonition toggle buttons
document.querySelectorAll(".admonition.toggle").forEach((el) => {
if (el.dataset["toggle_after_print"] == "true") {
el.querySelector("button.toggle-button").click();
delete el.dataset["toggle_after_print"];
}
});
});
}