I’m having issues with getting light/dark theme toggle working. The source html, css, Javascript code is below, the html is correct and the button is on the page. Just when i toggle it does nothing: the background page colour doesn’t go from white to black and vice versa. What is missing/wrong. I suspect its the Javascript and/or CSS.
Here’s javascript:
document.addEventListener('DOMContentLoaded', function () {
const themeToggle = document.getElementById('theme');
// Function to toggle theme
function toggleTheme() {
if (themeToggle.checked) {
document.documentElement.setAttribute('data-theme', 'dark');
} else {
document.documentElement.setAttribute('data-theme', 'light');
}
}
// Event listener for theme toggle change
themeToggle.addEventListener('change', toggleTheme);
});
Html:
<label for="theme" class="theme">
<span class="theme__toggle-wrap">
<input id="theme"
class="theme__toggle"
type="checkbox" role="switch"
name="theme" value="dark">
<span class="theme__fill"></span>
<span class="theme__icon">
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
<span
class="theme__icon-part"></span>
</span>
</span>
</label>
Here is the CSS of toggle:
.theme__toggle:checked ~ body {
background-color: black; /* Dark mode background color */
color: #fff; /* Text color for dark mode */
}
/* Light mode */
.theme__toggle:not(:checked) ~ body {
background-color: white; /* Light mode background color */
color: #000; /* Text color for light mode */
}
i tried simplifying the javascript and css but hasn’t worked. The page by default should be white then turn black when toggle is well toggled and vice versa.
2
Answers
Try this solution please:
The
~
CSS selector is targeting all siblings ahead of.theme__toggle
,however,
.theme__toggle
is inside the body and not a sibling before thebody
tag.https://www.w3schools.com/cssref/sel_gen_sibling.php
replace
.theme__toggle:checked ~ body
withbody:has(.theme__toggle:checked)
.Here’s the support table for
:has
https://caniuse.com/css-hasAlternatively, to use your original
~
selector, you would need to flatten the input field and style a .container.