How to automatically set the radio button as "checked" with Javascript upon loading the page

With the dark mode switch javascript from Bootstrap 5 (https://getbootstrap.com/docs/5.3/customize/color-modes/#javascript), I am attempting to ensure that a radio button is set to "checked" when the page loads, as well as when the color mode is changed.

The following javascript code is being used:

    <script>
      (() => {
        'use strict'

        const getStoredTheme = () => localStorage.getItem('theme')
        const setStoredTheme = theme => localStorage.setItem('theme', theme)

        const getPreferredTheme = () => {
          const storedTheme = getStoredTheme()
          if (storedTheme) {
            return storedTheme
          }

          return window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light'
        }

        const setTheme = theme => {
          if (theme === 'auto' && window.matchMedia('(prefers-color-scheme: dark)').matches) {
            document.documentElement.setAttribute('data-bs-theme', 'dark')
          } else {
            document.documentElement.setAttribute('data-bs-theme', theme)
          }
        }

        setTheme(getPreferredTheme())

        const showActiveTheme = (theme, focus = false) => {
          const themeSwitcher = document.querySelector('#bd-theme')

          if (!themeSwitcher) {
            return
          }

          const btnToActive = document.querySelector(`[data-bs-theme-value="${theme}"]`)

          document.querySelectorAll('[data-bs-theme-value]').forEach(element => {
            element.classList.remove('checked')
          })

          btnToActive.classList.add('checked')

          if (focus) {
            themeSwitcher.focus()
          }
        }

        window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', () => {
          const storedTheme = getStoredTheme()
          if (storedTheme !== 'light' && storedTheme !== 'dark') {
            setTheme(getPreferredTheme())
          }
        })

        window.addEventListener('DOMContentLoaded', () => {
          showActiveTheme(getPreferredTheme())

          document.querySelectorAll('[data-bs-theme-value]')
            .forEach(toggle => {
              toggle.addEventListener('click', () => {
                const theme = toggle.getAttribute('data-bs-theme-value')
                setStoredTheme(theme)
                setTheme(theme)
                showActiveTheme(theme, true)
              })
            })
        })
      })()
    </script>

I want to be able to control the button group like this:

  <div class="btn-group" id="bd-theme" role="group">
    <input autocomplete="off" checked class="btn-check" data-bs-theme-value="light" id="btnradio1" name="btnradio" type="radio">
    <label class="btn btn-outline-dark" for="btnradio1">
      Light
    </label>
    <input autocomplete="off" class="btn-check" data-bs-theme-value="dark" id="btnradio2" name="btnradio" type="radio">
    <label class="btn btn-outline-dark" for="btnradio2">
      Dark
    </label>
    <input autocomplete="off" class="btn-check" data-bs-theme-value="auto" id="btnradio3" name="btnradio" type="radio">
    <label class="btn btn-outline-dark" for="btnradio3">
      Auto
    </label>
  </div>

By default, the 'Light' mode should be "checked", but if a different 'theme' has been stored already, then that particular radio button should be "checked" instead.

I believe the section of the code that requires modification is:

        const showActiveTheme = (theme, focus = false) => {
          const themeSwitcher = document.querySelector('#bd-theme')

          if (!themeSwitcher) {
            return
          }

          const btnToActive = document.querySelector(`[data-bs-theme-value="${theme}"]`)

          document.querySelectorAll('[data-bs-theme-value]').forEach(element => {
            element.classList.remove('checked')
          })

          btnToActive.classList.add('checked')

          if (focus) {
            themeSwitcher.focus()
          }
        }

Answer №1

Do you really need to toggle the classList? It might be simpler to just set the checked property on the DOMNode directly. In other words, instead of using element.classList.add('checked'), you could use element.checked = true

document.getElementById('makeDark').addEventListener('click', () => {
    document.getElementById('dark').checked = true;
});

document.getElementById('makeDarkBroken').addEventListener('click', () => {
    document.getElementById('dark').classList.toggle('checked');
});
.checked {
  width: 20px;
  height: 20px;
}
<label><input id="light" name="demo" value="light" type="radio" checked /> Light</label>
<label><input id="dark" name="demo" value="dark" type="radio" /> Dark</label>

<button id="makeDark">Make Dark</button>
<button id="makeDarkBroken">Make Dark Broken</button>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Extracting numbers using regular expressions can be tricky especially when dealing with mixed

Currently, I am attempting to create a javascript regex that can extract decimal numbers from a string containing a mix of characters. Here are some examples of the mixed strings: mixed string123,456,00indeed mixed string123,456.00indeed mixed string123,4 ...

Go all the way down to see the latest messages

I have developed a messaging system using Vue. The latest messages are displayed from bottom to top. I want to automatically scroll to the end of a conversation when it is clicked and all the messages have been loaded via axios. Conversation Messages Comp ...

Verify modifications prior to navigating in React or Next.js

I have a simple Next JS application with two pages. -> Home page import Header from "../components/header"; const handleForm = () => { console.log("trigger"); }; export default () => ( <> <Header /> & ...

Using JavaScript, conceal a specific Div by examining the content within another Div

I am attempting to implement some logic using JavaScript. The goal is to hide the "cart-button" div if the innerHTML value of a div with the class "b-format" is set to Audio, otherwise hide the "more-button" div. However, for some reason this functionality ...

"Successful implementation of Ajax function in local environment but encountering issues when running online

I am facing an issue with my AJAX function. It works perfectly fine on my local server but does not return anything when I move it to my online server. Below is the code snippet: This is the part of the page where I call the showEspece() function: echo ...

Communicating data transfer between two Node.js servers through the use of the Node Serial Port technology

How can I send the message "Hello world" from one nodejs server to another using node-serialport? I have confirmed that the radios connecting the two servers are properly connected as they are displaying buffer information after running my current code. ...

When the disk space is insufficient, the createWriteStream function will not trigger an error event if the file is not completely written

One challenge I'm encountering involves using createWriteStream: Imagine I have a large 100mb file that I want to write to another file on the disk. The available space on the disk is only 50mb. Here's my code snippet: const fs = require(&a ...

Refreshing the page allows Socket.io to establish multiple connections

I've been working on setting up a chatroom, but I've noticed that each time the page refreshes, more connections are being established. It's interesting because initially only one connection is created when I visit the chat room page. Howeve ...

Having issues with the POST method in node.js and express when connecting to a MySQL database

My GET method is functioning perfectly I have a database called stage4 and I am attempting to insert values into it from a frontend page The connection is established, I'm using Postman to test it first, but it keeps returning a "404 error" which is ...

Having trouble implementing font css file in Reactjs

When working with Reactjs (Nextjs), every time I try to incorporate "css" into my project, I encounter the following error on my screen: Module not found: Can't resolve '../fonts/fontawesome-webfont.eot?v=4.7.0' How can I solve this issue? ...

Problems with navigation, not functioning properly due to issues with Pulled functions

I am still getting the hang of things and struggling with the terminology, so please bear with me as I try to explain my issue. Currently, I am working on a project in react native where I have two files - Header.js and footer.js. I have successfully impo ...

Is it necessary to run npm install when a package does not have any dependencies?

If I have an npm package that contains all its dependencies bundled into one file using webpack, and I unpack it into the directory ./my-awesome-package/, should I still run npm install ./my-awesome-package/? I am aware of being able to specify preinstall ...

Create and transmit an array of JSON objects

I need help with defining and sending a JSON object array. While I've managed to define a single JSON object, convert it into a string, and send it, I'm stuck on how to do the same for an array of objects. It seems like there might be a simple so ...

Interactive form found on a webpage

Hey there! I'm currently working on a task where I want a form to be displayed when the edit button is clicked. Once the save button in the form is pressed, I want to update my database with the new information. It's crucial that this process hap ...

What is the best way to populate MongoDB with information retrieved from an external API?

Recently, I've been diving into the world of NodeJS with mongoose & mLab. As someone new to these technologies, I'm slowly piecing together my model. Here's what it looks like for now, with plans to expand the schema down the road. cons ...

Tips on showcasing a set number of elements from an array in React

How can I modify my code to display only a specific number of items from the 'portfolioComponents' array, starting at a designated index ('startArrayHere') and incrementing or decrementing that index based on user interaction? I've ...

Angular template not refreshing automatically

Within my controller: $scope.deleteUser = function(user){ $.ajax({ url: "/users/" + user.id.toString(), method: "DELETE", success: function(result){ $scope.users = result["users"]; ...

Is there a way to calculate the mean of radio buttons that each have their own distinct values?

My HTML page features a unique rating system created with radio buttons that resemble stars when filled in. The CSS styling gives them an appealing design. Additionally, I have included a submit button to display the selected star count when clicked. Here ...

The Angular project failed to run properly following the ng build command

Just started working with Angularjs 2 and encountered an issue after running ng build. The compiled files were placed in the dist folder, but when I checked the index.html file within that folder, all the scripts had missing references even though they w ...

Ajax fails to transmit data to PHP script

Having encountered an issue with my script that prevents sending data from AJAX to a PHP file, I decided to debug it by logging the form data before running it through the AJAX function. The data obtained was as follows: Form: name=jim&email=info%40te ...