Why classes?
You could change an element's look by setting styles one by one with JavaScript. A much better habit is to describe each state in CSS as a class, and let jQuery switch the class:
.error { border-color: #dc2626; background: #fef2f2; }
.hidden { display: none; }
.active { font-weight: bold; color: #1d4ed8; }The design stays in the stylesheet, where it can include hover effects, media queries and transitions, and your JavaScript only says which state an element is in. A designer can restyle the error state later by editing one CSS rule, without reading any JavaScript, and the same class can be reused on any element. Classes also stack: an element can be active and error at once, and the CSS decides how the two combine.
Adding and removing
<style>
.box { padding: 8px; border: 2px solid #94a3b8; margin: 4px 0; }
.highlight { background: #fef9c3; }
.big { font-size: 1.4em; }
</style>
<div class="box" id="a">Box A</div>
<div class="box" id="b">Box B</div>
<script src="https://code.jquery.com/jquery-4.0.0.min.js"></script>
<script>
$("#a").addClass("highlight big");
$(".box").addClass("checked");
$("#b").removeClass("box");
console.log("A:", $("#a").attr("class"));
console.log("B:", $("#b").attr("class"));
</script>A: box highlight big checked
B: checked- Separate several class names with spaces. You can also pass an array:
.addClass(["highlight", "big"]). - Adding a class an element already has does nothing; it is never duplicated.
.removeClass()with no argument removes all classes.
Toggling
.toggleClass() adds the class if it is missing, and removes it if it is there. It is perfect for buttons that switch something on and off:
<style>
#menu { display: none; border: 1px solid #ccc; padding: 8px; }
#menu.open { display: block; }
</style>
<button id="menu-btn" aria-expanded="false">Menu</button>
<nav id="menu"><a href="#">Home</a> · <a href="#">Shop</a></nav>
<script src="https://code.jquery.com/jquery-4.0.0.min.js"></script>
<script>
$("#menu-btn").on("click", function () {
$("#menu").toggleClass("open");
const isOpen = $("#menu").hasClass("open");
$(this).attr("aria-expanded", isOpen);
console.log("menu open:", isOpen);
});
</script>menu open: trueUpdating aria-expanded tells screen reader users whether the menu is open. Whenever a button shows or hides something, keep that attribute in step.
Forcing a state
Toggling blindly can get out of step, for example if a validation runs twice. Pass a second argument, true or false, to force the result:
<style> .error { outline: 2px solid crimson; } </style>
<input id="age" type="number" placeholder="Your age">
<p id="msg"></p>
<script src="https://code.jquery.com/jquery-4.0.0.min.js"></script>
<script>
$("#age").on("input", function () {
const tooYoung = Number($(this).val()) < 18;
$(this).toggleClass("error", tooYoung);
$("#msg").text(tooYoung ? "You must be 18 or over." : "");
console.log($(this).val(), "error:", $(this).hasClass("error"));
});
</script>2 error: true
21 error: falsetoggleClass("error", tooYoung) means "the class should be on exactly when tooYoung is true". As the user types 2 and then 21, the class goes on and then comes off again, set correctly however often the code runs.
Checking for a class
.hasClass("name") returns true if any selected element has the class. .is(".name") does the same and accepts any selector. Use it to decide what to do next, for example to close a menu only when it is open. You rarely need to check before adding or removing, though: adding a class that is already there, or removing one that is missing, is harmless, so .addClass() and .removeClass() can be called without a test.
Classes from a function
Like other setters, .addClass() and .toggleClass() accept a function, handy when each element needs a different class:
<ul>
<li data-stock="12">Lamp</li>
<li data-stock="0">Desk</li>
<li data-stock="3">Chair</li>
</ul>
<script src="https://code.jquery.com/jquery-4.0.0.min.js"></script>
<script>
$("li").addClass(function () {
const stock = Number($(this).attr("data-stock"));
return stock === 0 ? "sold-out" : stock < 5 ? "low-stock" : "in-stock";
});
console.log($("li").map((i, el) => el.className).get().join(" | "));
</script>in-stock | sold-out | low-stockA note on jQuery 4
Old jQuery versions allowed .toggleClass() with no arguments (or only true/false) to remove and later restore all of an element's classes. That signature was removed in jQuery 4 and now does nothing, so always name the class. The upgrade lesson lists other changes like this.
Common mistakes
- Writing a dot in the class name:
.addClass(".active")adds a class literally called.active. Use.addClass("active"). - Using commas between names instead of spaces.
- Setting many styles with
.css()when a class would do. - Toggling without a condition in code that can run more than once.
Exercise
Make three buttons labelled Small, Medium and Large. Clicking one gives a paragraph the class text-s, text-m or text-l, removing the other two. Define the three classes in CSS with different font sizes.
Show one possible answer
<style> .text-s { font-size: 12px; } .text-m { font-size: 16px; } .text-l { font-size: 22px; } </style>
<div><button data-size="s">Small</button><button data-size="m">Medium</button><button data-size="l">Large</button></div>
<p id="text">Resize me</p>
<script src="https://code.jquery.com/jquery-4.0.0.min.js"></script>
<script>
$("button").on("click", function () {
$("#text").removeClass("text-s text-m text-l").addClass("text-" + $(this).attr("data-size"));
console.log($("#text").attr("class"));
});
</script>text-lKey points
- .addClass() and .removeClass() add or remove one or more classes; separate several with spaces.
- .toggleClass("x") adds the class if it is missing and removes it if present; .toggleClass("x", condition) forces it on or off.
- .hasClass("x") returns true if any selected element has the class.
- Switching classes keeps the design in CSS, where it is easy to change, and keeps JavaScript small.