Skip to content

Instantly share code, notes, and snippets.

@djcowan
Created April 3, 2023 03:06
Show Gist options
  • Save djcowan/b0155009a77b445d7faf0b8d159ae560 to your computer and use it in GitHub Desktop.
Save djcowan/b0155009a77b445d7faf0b8d159ae560 to your computer and use it in GitHub Desktop.
accordion vanilla javascript
const questions = document.querySelectorAll('#faq dt');
questions.forEach((question) => {
const button = document.createElement('button');
const h3 = document.createElement('h3');
let id = question.getAttribute('id');
if (!id) {
id = encodeURIComponent(question.textContent.trim().toLowerCase());
question.setAttribute('id', id);
}
button.setAttribute('formaction', id);
button.textContent = question.textContent;
button.addEventListener('click', (event) => {
event.preventDefault();
window.location.hash = id;
});
question.textContent = '';
h3.appendChild(button);
question.appendChild(h3);
question.addEventListener('click', (event) => {
if (event.type === 'keydown' && event.which !== 13) {
return;
}
const clickedQuestion = event.currentTarget;
const isOpen = clickedQuestion.classList.contains('open');
questions.forEach((question) => {
const sibling = question.nextElementSibling;
const isSiblingOpen = question.classList.contains('open');
if (isSiblingOpen && question !== clickedQuestion) {
question.classList.remove('open');
question.setAttribute('aria-expanded', false);
sibling.style.display = 'none';
}
});
clickedQuestion.classList.toggle('open');
clickedQuestion.setAttribute('aria-expanded', !isOpen);
clickedQuestion.nextElementSibling.style.display = isOpen ? 'none' : 'block';
if (window.location.hash) {
const scrollPaddingTop = parseInt(getComputedStyle(document.documentElement).scrollPaddingTop) || 0;
window.scrollTo({
top: clickedQuestion.offsetTop - scrollPaddingTop,
behavior: 'smooth',
});
}
});
});
if (window.location.hash) {
const targetQuestion = document.getElementById(decodeURIComponent(window.location.hash.substr(1)).trim());
if (targetQuestion) {
targetQuestion.click();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment