user10340803
user10340803

Reputation:

jQuery dark-mode toggle only half working

Creating a dark-mode toggle for an assignment, but it only works for 50%

Created 2 classes that should change the body's background + text color.

Toggling ON darkmode works fine, toggling it of to return to light-mode doesnt seem to work. Cannot seem to get the 'dark' class removed for some reason and changed to the 'light' class

$('.switch').click(function() { 
        if ($('body').not('dark')) {
            $('body').addClass('dark');
        } 
        else if ($('body').hasClass('dark')) {
            $('body').removeClass('dark');
            $('body').addClass('light');
        }

});
.dark {
    background-color: #000000;
    transition: .5s all ease;
    color: #ffffff;
}

.light {
    background-color: #ffffff;
    transition: .5s all ease;
    color: #000000;
}


/* ----------------------------- SLIDER -----------------------------*/

.switch {
  position: relative;
  display: inline-block;
  width: 60px;
  height: 34px;
/*  float: right;*/
}

.switch input { 
  opacity: 0;
  width: 0;
  height: 0;
}

.slider {
  position: absolute;
  cursor: pointer;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background-color: #ccc;
  -webkit-transition: .4s;
  transition: .4s;
}

.slider::before {
  position: absolute;
  content: "";
  height: 26px;
  width: 26px;
  left: 4px;
  bottom: 4px;
  background-color: white;
  -webkit-transition: .4s;
  transition: .4s;
}

input:checked + .slider {
  background-color: #696969;
}

/*
input:focus + .slider {
  box-shadow: 0 0 1px #696969;
}
*/

input:checked + .slider::before {
  -webkit-transform: translateX(26px);
  -ms-transform: translateX(26px);
  transform: translateX(26px);
}

/* Rounded sliders */
.slider.round {
  border-radius: 34px;
}

.slider.round::before {
  border-radius: 50%;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<p> Switch theme </p> 

<label class="switch">
   <input type="checkbox">
   <span class="slider round"></span>
</label>

Upvotes: 0

Views: 966

Answers (1)

imvain2
imvain2

Reputation: 15847

You could always simplify your code and have the light styles be the default for body then simply toggle dark on CHANGE not CLICK.

When using click on the switch you are actually triggering your change function twice. However, the proper way to handle it is like a checkbox that it is and use change.

Also not('dark') won't work as dark isn't a selector so the if statement will never work.

$(document).on("change",".switch",function() { 
   $("body").toggleClass("dark");
});
body {
    background-color: #ffffff;
    transition: .5s all ease;
    color: #000000;
}

body.dark {
    background-color: #000000;
    transition: .5s all ease;
    color: #ffffff;
}




/* ----------------------------- SLIDER -----------------------------*/

.switch {
  position: relative;
  display: inline-block;
  width: 60px;
  height: 34px;
/*  float: right;*/
}

.switch input { 
  opacity: 0;
  width: 0;
  height: 0;
}

.slider {
  position: absolute;
  cursor: pointer;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background-color: #ccc;
  -webkit-transition: .4s;
  transition: .4s;
}

.slider::before {
  position: absolute;
  content: "";
  height: 26px;
  width: 26px;
  left: 4px;
  bottom: 4px;
  background-color: white;
  -webkit-transition: .4s;
  transition: .4s;
}

input:checked + .slider {
  background-color: #696969;
}

/*
input:focus + .slider {
  box-shadow: 0 0 1px #696969;
}
*/

input:checked + .slider::before {
  -webkit-transform: translateX(26px);
  -ms-transform: translateX(26px);
  transform: translateX(26px);
}

/* Rounded sliders */
.slider.round {
  border-radius: 34px;
}

.slider.round::before {
  border-radius: 50%;
}
<html>
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
</head>
<body>
<p> Switch theme </p> 

<label class="switch">
   <input type="checkbox">
   <span class="slider round"></span>
</label>
</body>
</html>

Upvotes: 1

Related Questions