2023-10-21 17:18:04 -04:00
|
|
|
// Light / Dark theme toggle
|
|
|
|
(function () {
|
|
|
|
const defaultTheme = '{{ site.Params.theme.default | default `system`}}'
|
2023-07-30 21:50:41 +01:00
|
|
|
|
refactor(css): add prefix to component classes for consistency (#744)
* refactor(navbar): add hextra prefix to navbar and hamburger menu classes
- Updated CSS class names from `nav-container` to `hextra-nav-container` and `hamburger-menu` to `hextra-hamburger-menu` for improved clarity and consistency across the project.
- Adjusted related JavaScript and documentation to reflect the new class names.
* refactor(search): update class names for search components
- Renamed CSS classes from `search-wrapper`, `search-input`, `active`, `no-result`, `prefix`, `excerpt`, and `match` to `hextra-search-wrapper`, `hextra-search-input`, `hextra-search-active`, `hextra-search-no-result`, `hextra-search-prefix`, `hextra-search-excerpt`, and `hextra-search-match` for improved clarity and consistency.
- Updated JavaScript selectors to match the new class names, ensuring functionality remains intact.
- Adjusted HTML structure to reflect the new class naming convention.
* refactor(search): update search component class names for consistency
- Renamed existing search-related CSS classes to include the `hextra` prefix for improved clarity and consistency.
- Added optional nested classes for enhanced customization of the search UI, including titles, active states, and result snippets.
- Removed outdated breadcrumb section as no specific class is available.
* refactor(sidebar): rename sidebar classes for consistency
- Updated CSS and JavaScript to replace `sidebar-container` with `hextra-sidebar-container` and `sidebar-active-item` with `hextra-sidebar-active-item` for improved clarity and consistency across the project.
- Adjusted related documentation to reflect the new class names.
* refactor(language & theme): update class names for consistency
- Renamed language switcher and theme toggle classes to include the `hextra` prefix for improved clarity and consistency across the project.
- Updated related JavaScript selectors and documentation to reflect the new class names.
* refactor(css & html): rename classes for consistency and clarity
- Updated various CSS class names to include the `hextra` prefix, enhancing consistency across the project. This includes renaming classes such as `content` to `hextra-content`, `filename` to `hextra-code-filename`, and `steps` to `hextra-steps`.
- Adjusted related HTML and JavaScript to reflect the new class names, ensuring functionality and styling remain intact.
- Updated documentation to include the new class names for better clarity.
* refactor(language): update class names for language options
- Renamed the `language-options` class to `hextra-language-options` for consistency with the existing `hextra` prefix convention.
- Updated the corresponding HTML to reflect the new class name, ensuring clarity and uniformity across the project.
* refactor(css & html): rename classes for consistency and clarity
- Renamed CSS classes to include the `hextra` prefix, such as changing `subheading-anchor` to `hextra-subheading-anchor` and `footnotes` to `hextra-footnotes`, enhancing consistency across the project.
- Updated related HTML and documentation to reflect the new class names, ensuring clarity and uniformity.
* feat(typography): add styling for horizontal lines
- Introduced new styles for horizontal lines to enhance visual separation in content. The styles apply margin and border color adjustments, ensuring consistency with the overall design.
* feat(blog): add draft release announcement for Hextra v0.10.0
- Created a new markdown file for the draft release announcement of Hextra v0.10.0, including upgrade instructions and author details.
- The announcement is currently marked as a draft and may be updated before the official release.
* refactor(css & html): rename `hextra-content` class to `content` for consistency
- Updated the `hextra-content` class to simply `content` across various HTML files and CSS, enhancing clarity and consistency in the codebase.
- Adjusted the `package.json` script for the development server to include the `-F` flag for better functionality.
* refactor(typography & markdown): enhance table styling and markdown syntax
- Updated CSS for tables to improve styling, including adjustments to margins, borders, and text properties for better readability.
- Revised markdown documentation to standardize table formatting and improve clarity, including consistent syntax for headers and lists.
- Enhanced examples in the documentation to reflect the updated styling and ensure accurate representation of output.
* fix(blog): update text color for improved accessibility
- Modified the text color in the blog single layout to enhance readability in dark mode by adding a dark text color class.
- Ensured consistency in styling for better user experience across different themes.
* docs(blog): update draft release announcement for Hextra v0.10.0
- Revised the "What's New" section to include a TODO placeholder for future updates.
- Added a comprehensive migration guide detailing the CSS class prefix changes to enhance consistency and avoid conflicts.
- Updated the announcement to reflect the new class naming conventions for various components.
* chore: rebuild css
2025-08-13 22:55:38 +08:00
|
|
|
const themeToggleButtons = document.querySelectorAll(".hextra-theme-toggle");
|
2025-08-20 00:26:32 +02:00
|
|
|
const themeToggleOptions = document.querySelectorAll(".hextra-theme-toggle-options p");
|
2023-07-30 21:50:41 +01:00
|
|
|
|
2025-08-20 00:26:32 +02:00
|
|
|
function setSystemTheme() {
|
|
|
|
const prefersColorScheme = window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light";
|
|
|
|
|
|
|
|
document.documentElement.classList.remove("dark", "light");
|
|
|
|
document.documentElement.classList.add(prefersColorScheme);
|
|
|
|
|
|
|
|
document.documentElement.style.colorScheme = prefersColorScheme;
|
|
|
|
}
|
|
|
|
|
|
|
|
function applyTheme(theme) {
|
|
|
|
themeToggleButtons.forEach((btn) => btn.parentElement.dataset.theme = theme );
|
|
|
|
|
|
|
|
localStorage.setItem("color-theme", theme);
|
|
|
|
}
|
|
|
|
|
|
|
|
function switchTheme(theme) {
|
|
|
|
switch (theme) {
|
|
|
|
case "light":
|
|
|
|
document.documentElement.classList.remove("dark");
|
|
|
|
document.documentElement.classList.add(theme);
|
|
|
|
document.documentElement.style.colorScheme = theme;
|
|
|
|
|
|
|
|
applyTheme(theme);
|
|
|
|
|
|
|
|
break;
|
|
|
|
case "dark":
|
|
|
|
document.documentElement.classList.remove("light");
|
|
|
|
document.documentElement.classList.add(theme);
|
|
|
|
document.documentElement.style.colorScheme = theme;
|
|
|
|
|
|
|
|
applyTheme(theme);
|
|
|
|
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
setSystemTheme();
|
|
|
|
applyTheme("system");
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
2023-10-21 17:18:04 -04:00
|
|
|
}
|
2023-07-30 21:50:41 +01:00
|
|
|
|
2025-08-20 00:26:32 +02:00
|
|
|
const colorTheme = "color-theme" in localStorage ? localStorage.getItem("color-theme") : defaultTheme;
|
|
|
|
switchTheme(colorTheme);
|
|
|
|
|
|
|
|
// Add click event handler to the menu items.
|
|
|
|
themeToggleOptions.forEach((option) => {
|
|
|
|
option.addEventListener("click", function (e) {
|
|
|
|
e.preventDefault();
|
|
|
|
|
|
|
|
switchTheme(option.dataset.item);
|
|
|
|
})
|
|
|
|
})
|
|
|
|
|
2023-10-21 17:18:04 -04:00
|
|
|
// Add click event handler to the buttons
|
2025-08-20 00:26:32 +02:00
|
|
|
themeToggleButtons.forEach((toggler) => {
|
|
|
|
toggler.addEventListener("click", function (e) {
|
|
|
|
e.preventDefault();
|
|
|
|
|
|
|
|
const optionsElement = toggler.nextElementSibling;
|
|
|
|
|
|
|
|
optionsElement.classList.toggle('hx:hidden');
|
|
|
|
|
|
|
|
// Calculate the position of a language options element.
|
|
|
|
const switcherRect = toggler.getBoundingClientRect();
|
|
|
|
|
|
|
|
// Must be called before optionsElement.clientWidth.
|
|
|
|
optionsElement.style.minWidth = `${Math.max(switcherRect.width, 50)}px`;
|
|
|
|
|
|
|
|
const isOnTop = toggler.dataset.location === 'top';
|
|
|
|
const isOnBottom = toggler.dataset.location === 'bottom';
|
|
|
|
const isOnBottomRight = toggler.dataset.location === 'bottom-right';
|
|
|
|
const isRTL = document.body.dir === 'rtl'
|
|
|
|
|
|
|
|
// Stuck on the left side of the switcher.
|
|
|
|
let translateX = switcherRect.left;
|
|
|
|
|
|
|
|
if (isOnTop && !isRTL || isOnBottom && isRTL || isOnBottomRight && !isRTL) {
|
|
|
|
// Stuck on the right side of the switcher.
|
|
|
|
translateX = switcherRect.right - optionsElement.clientWidth;
|
2023-08-07 23:48:07 +01:00
|
|
|
}
|
2025-08-20 00:26:32 +02:00
|
|
|
|
|
|
|
// Stuck on the top of the switcher.
|
|
|
|
let translateY = switcherRect.top - window.innerHeight - 15;
|
|
|
|
|
|
|
|
if (isOnTop) {
|
|
|
|
// Stuck on the bottom of the switcher.
|
|
|
|
translateY = switcherRect.top - window.innerHeight + 150;
|
|
|
|
}
|
|
|
|
|
|
|
|
optionsElement.style.transform = `translate3d(${translateX}px, ${translateY}px, 0)`;
|
2023-10-21 17:18:04 -04:00
|
|
|
});
|
|
|
|
});
|
|
|
|
|
2025-08-20 00:26:32 +02:00
|
|
|
|
|
|
|
// Dismiss the menu when clicking outside
|
|
|
|
document.addEventListener('click', (e) => {
|
|
|
|
if (e.target.closest('.hextra-theme-toggle') === null) {
|
|
|
|
themeToggleButtons.forEach((toggler) => {
|
|
|
|
toggler.dataset.state = 'closed';
|
|
|
|
toggler.nextElementSibling.classList.add('hx:hidden');
|
|
|
|
});
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
2023-10-21 17:18:04 -04:00
|
|
|
// Listen for system theme changes
|
2025-08-20 00:26:32 +02:00
|
|
|
window.matchMedia("(prefers-color-scheme: dark)").addEventListener("change", () => {
|
|
|
|
if (localStorage.getItem("color-theme") === "system") {
|
|
|
|
setSystemTheme();
|
2023-07-30 21:50:41 +01:00
|
|
|
}
|
2023-08-07 23:48:07 +01:00
|
|
|
});
|
2023-10-21 17:18:04 -04:00
|
|
|
})();
|