Justine
Justine

Reputation: 59

JQuery - toggleClass and removeClass Features on Single Element

I'm trying to create a template which showcases different CSS rules and how they affect elements when applied. I'd like to use this template on multiple pages, so I want to link a single script. Because of this, I'm attempting to avoid using exact class names in the JS. Here's what I have:

// Show active change
$('.button').click(function(){
    $(this).toggleClass("active");
});

// Apply changes on click
$(document).ready(function() {
   $("#buttons li").each(function(i) {
      $(this).attr('id', "choice-" + (i+1)).click(function () {
         $( ".to-change" ).toggleClass("change-" + (i+1));
      });
   });
});
/*Global*/
body {
   overflow-y: scroll;
}
header {
   font-family: 'Lato', sans-serif;
   background-color: #F5F5F5;
   text-align: center;
   position: fixed;
   top: 0;
   left: 0;
   width: 100%;
   padding: 2em 0;
}
main {
   padding-top: 9em;
}

/*Header Title*/
#title {
  margin: auto;
  font-size: 1em;
  text-transform: uppercase;
  letter-spacing: 1px;
  margin-bottom: .5em;
}

/*Selections*/
ul {
   list-style-type: none;
   margin: 0;
   padding: 0;
}
ul li {
   display:inline;
}
.button {
  background-color: #E95420;
  border: none;
  color: white;
  letter-spacing: 1px;
  padding: 0.2em 0.4em;
  border-radius: 4px;
  text-align: center;
  text-decoration: none;
  display: inline-block;
  font-size: .8em;
  margin: 0.3em;
  cursor: pointer;
  -webkit-transition: all 0.4s ease-in-out;
  -moz-transition: all 0.4s ease-in-out;
  -o-transition: all 0.4s ease-in-out;
  transition: all 0.4s ease-in-out;
}
.button:nth-of-type(1) {
  background-color: white; 
  color: black; 
  border: 2px solid #E95420;
}
.button:nth-of-type(1):hover {
  background-color: #E95420;
  color: white;
}
.button:nth-of-type(1).active {
  background-color: #E95420;
  color: white;
}
.button:nth-of-type(2) {
  background-color: white; 
  color: black; 
  border: 2px solid #38b44a;
}
.button:nth-of-type(2):hover {
  background-color: #38b44a;
  color: white;
}
.button:nth-of-type(2).active {
  background-color: #38b44a;
  color: white;
}
.button:nth-of-type(3) {
  background-color: white; 
  color: black; 
  border: 2px solid #772953;
}
.button:nth-of-type(3):hover {
  background-color: #772953;
  color: white;
}
.button:nth-of-type(3).active {
  background-color: #772953;
  color: white;
}

/* Example changes made to element on click: */
#test * {    
  -webkit-transition: all 0.2s ease-in-out;
  -moz-transition: all 0.2s ease-in-out;
  -o-transition: all 0.2s ease-in-out;
  transition: all 0.2s ease-in-out;
}
.change-1 {
  font-size: 1.5em;
}
.change-2 {
  text-decoration: line-through;
}
.change-3 {
  color: darkgray;
}
<link href="https://fonts.googleapis.com/css?family=Lato" rel="stylesheet">


<header id="toggles">
   <h1 id="title">Buttons</h1>
   <ul id="buttons">
      <li class="button">Change 1</li>
      <li class="button">Change 2</li> 
      <li class="button">Change 3</li>
   </ul>
</header>

<main id="test">
   <p class="to-change">Lorem ipsum dolor sit amet.</p>
</main>

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

What I want is for users to be able to toggle a single button on/off or click another option to overwrite the previous added class. The above snippet is a fix, set it up so that the classes stack, but I want only one change to apply to the element at any time - clicking another "Change" button should turn off any previously applied class.

From what I understand about JS and JQuery (which is nothing, admittedly), I should be able to use removeClass().addClass() but this doesn't work:

$( ".to-change" ).removeClass().addClass("change-" + (i+1));
//or
$( ".to-change" ).removeClass().toggleClass("change-" + (i+1));

I get one applied change on click, but that's it.

How can I set it up so that the previous class is removed before the new one is added on button click?

Please note: My JS is Frankensteined. I really don't know what I'm doing here. Thank you for any help!

Upvotes: 0

Views: 39

Answers (1)

charlietfl
charlietfl

Reputation: 171679

The reason removeClass() isn't working is it also removes the original class to-change

Then the next time you look for that element using $('.to-change') no such class exists

Adding it back in addClass() makes it work

// Show active change
$('.button').click(function(){
    $(this).toggleClass("active");
});

// Apply changes on click
$(document).ready(function() {
   $("#buttons li").each(function(i) {
      $(this).attr('id', "choice-" + (i+1)).click(function () {
         $( ".to-change").removeClass().addClass("to-change change-" + (i+1));
      });
   });
});
/*Global*/
body {
   overflow-y: scroll;
}
header {
   font-family: 'Lato', sans-serif;
   background-color: #F5F5F5;
   text-align: center;
   position: fixed;
   top: 0;
   left: 0;
   width: 100%;
   padding: 2em 0;
}
main {
   padding-top: 9em;
}

/*Header Title*/
#title {
  margin: auto;
  font-size: 1em;
  text-transform: uppercase;
  letter-spacing: 1px;
  margin-bottom: .5em;
}

/*Selections*/
ul {
   list-style-type: none;
   margin: 0;
   padding: 0;
}
ul li {
   display:inline;
}
.button {
  background-color: #E95420;
  border: none;
  color: white;
  letter-spacing: 1px;
  padding: 0.2em 0.4em;
  border-radius: 4px;
  text-align: center;
  text-decoration: none;
  display: inline-block;
  font-size: .8em;
  margin: 0.3em;
  cursor: pointer;
  -webkit-transition: all 0.4s ease-in-out;
  -moz-transition: all 0.4s ease-in-out;
  -o-transition: all 0.4s ease-in-out;
  transition: all 0.4s ease-in-out;
}
.button:nth-of-type(1) {
  background-color: white; 
  color: black; 
  border: 2px solid #E95420;
}
.button:nth-of-type(1):hover {
  background-color: #E95420;
  color: white;
}
.button:nth-of-type(1).active {
  background-color: #E95420;
  color: white;
}
.button:nth-of-type(2) {
  background-color: white; 
  color: black; 
  border: 2px solid #38b44a;
}
.button:nth-of-type(2):hover {
  background-color: #38b44a;
  color: white;
}
.button:nth-of-type(2).active {
  background-color: #38b44a;
  color: white;
}
.button:nth-of-type(3) {
  background-color: white; 
  color: black; 
  border: 2px solid #772953;
}
.button:nth-of-type(3):hover {
  background-color: #772953;
  color: white;
}
.button:nth-of-type(3).active {
  background-color: #772953;
  color: white;
}

/* Example changes made to element on click: */
#test * {    
  -webkit-transition: all 0.2s ease-in-out;
  -moz-transition: all 0.2s ease-in-out;
  -o-transition: all 0.2s ease-in-out;
  transition: all 0.2s ease-in-out;
}
.change-1 {
  font-size: 1.5em;
}
.change-2 {
  text-decoration: line-through;
}
.change-3 {
  color: darkgray;
}
<link href="https://fonts.googleapis.com/css?family=Lato" rel="stylesheet">


<header id="toggles">
   <h1 id="title">Buttons</h1>
   <ul id="buttons">
      <li class="button">Change 1</li>
      <li class="button">Change 2</li> 
      <li class="button">Change 3</li>
   </ul>
</header>

<main id="test">
   <p class="to-change">Lorem ipsum dolor sit amet.</p>
</main>

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

Upvotes: 1

Related Questions