Home >Web Front-end >CSS Tutorial >Building a Filtering Component with CSS Animations & jQuery
Some months ago, I wrote an article about MixItUp, a popular jQuery plugin for filtering and sorting. In today’s article, I’ll show you how to build your own simple filterable component with jQuery and CSS animations.
Without further ado, let’s get started!
As a first step, I’ll show you the HTML structure of the component. Consider the following markup:
<span><span><span><div</span> class<span>="cta filter"</span>></span> </span> <span><span><span><a</span> class<span>="all active"</span> data-filter<span>="all"</span> href<span>="#"</span> role<span>="button"</span>></span>Show All<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-filter<span>="green"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Green Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-filter<span>="blue"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Blue Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-filter<span>="red"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Red Boxes<span><span></a</span>></span> </span><span><span><span></div</span>></span> </span> <span><span><span><div</span> class<span>="boxes"</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-category<span>="red"</span> href<span>="#"</span>></span>Box1<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-category<span>="green"</span> href<span>="#"</span>></span>Box2<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-category<span>="blue"</span> href<span>="#"</span>></span>Box3<span><span></a</span>></span> </span> <span><!-- other anchor/boxes here ... --> </span> <span><span><span></div</span>></span></span>
Notice that I’ve set up some pretty basic markup. Here’s an explanation of it:
Now that you’ve had an overview of the required HTML, we can move on to explore the CSS.
Each time a filter category is active, its corresponding filter button receives the active class. By default, the button with the data-filter="all" attribute gets this class.
Here are the associated styles:
<span><span>.filter a</span> { </span> <span>position: relative; </span><span>} </span> <span><span>.filter a.active:before</span> { </span> <span>content: ''; </span> <span>position: absolute; </span> <span>left: 0; </span> <span>top: 0; </span> <span>display: inline-block; </span> <span>width: 0; </span> <span>height: 0; </span> <span>border-style: solid; </span> <span>border-width: 15px 15px 0 0; </span> <span>border-color: #333 transparent transparent transparent; </span><span>}</span>
In addition, I’m going to use flexbox to create the layout for the target elements.
See the related styles below:
<span><span><span><div</span> class<span>="cta filter"</span>></span> </span> <span><span><span><a</span> class<span>="all active"</span> data-filter<span>="all"</span> href<span>="#"</span> role<span>="button"</span>></span>Show All<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-filter<span>="green"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Green Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-filter<span>="blue"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Blue Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-filter<span>="red"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Red Boxes<span><span></a</span>></span> </span><span><span><span></div</span>></span> </span> <span><span><span><div</span> class<span>="boxes"</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-category<span>="red"</span> href<span>="#"</span>></span>Box1<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-category<span>="green"</span> href<span>="#"</span>></span>Box2<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-category<span>="blue"</span> href<span>="#"</span>></span>Box3<span><span></a</span>></span> </span> <span><!-- other anchor/boxes here ... --> </span> <span><span><span></div</span>></span></span>
Lastly, I’m defining two different CSS keyframe animations that I’ll use later on to reveal the elements:
<span><span>.filter a</span> { </span> <span>position: relative; </span><span>} </span> <span><span>.filter a.active:before</span> { </span> <span>content: ''; </span> <span>position: absolute; </span> <span>left: 0; </span> <span>top: 0; </span> <span>display: inline-block; </span> <span>width: 0; </span> <span>height: 0; </span> <span>border-style: solid; </span> <span>border-width: 15px 15px 0 0; </span> <span>border-color: #333 transparent transparent transparent; </span><span>}</span>
With the markup and CSS in place, we can start building the JavaScript/jQuery.
Have a look at the code below, after which I’ll explain what’s happening:
<span><span>.boxes</span> { </span> <span>display: flex; </span> <span>flex-wrap: wrap; </span><span>} </span> <span><span>.boxes a</span> { </span> <span>width: 23%; </span> <span>border: 2px solid #333; </span> <span>margin: 0 1% 20px 1%; </span> <span>line-height: 60px; </span><span>}</span>
Each time a filter button is clicked, the following happens:
At this point, it’s important to clarify one thing. Notice the syntax for the fadeOut() method in the above code. It looks as follows:
<span><span>@keyframes zoom-in</span> { </span> <span>0% { </span> <span>transform: scale(.1); </span> <span>} </span> <span>100% { </span> <span>transform: none; </span> <span>} </span><span>} </span> <span><span>@keyframes rotate-right</span> { </span> <span>0% { </span> <span>transform: translate(-100%) rotate(-100deg); </span> <span>} </span> <span>100% { </span> <span>transform: none; </span> <span>} </span><span>} </span> <span><span>.is-animated</span> { </span> <span>animation: .6s zoom-in; </span> // <span>animation: .6s rotate-right; </span><span>}</span>
You’re probably more familiar with this syntax though:
<span>var $filters = $('.filter [data-filter]'), </span> $boxes <span>= $('.boxes [data-category]'); </span> $filters<span>.on('click', function(e) { </span> e<span>.preventDefault(); </span> <span>var $this = $(this); </span> $filters<span>.removeClass('active'); </span> $<span>this.addClass('active'); </span> <span>var $filterColor = $this.attr('data-filter'); </span> <span>if ($filterColor == 'all') { </span> $boxes<span>.removeClass('is-animated') </span> <span>.fadeOut().promise().done(function() { </span> $boxes<span>.addClass('is-animated').fadeIn(); </span> <span>}); </span> <span>} else { </span> $boxes<span>.removeClass('is-animated') </span> <span>.fadeOut().promise().done(function() { </span> $boxes<span>.filter('[data-category = "' + $filterColor + '"]') </span> <span>.addClass('is-animated').fadeIn(); </span> <span>}); </span> <span>} </span><span>});</span>
These declarations have different meanings:
The demo below uses the zoom-in animation:
See the Pen A sorting/filtering component with CSS and jQuery (with zoom animation) by SitePoint (@SitePoint) on CodePen.
And this demo uses the rotate-right animation:
See the Pen A sorting/filtering component with CSS and jQuery (with rotate animation) by SitePoint (@SitePoint) on CodePen.
Of course, the aforementioned CSS animations are optional. If you don’t like these specific animations, feel free to remove them and reveal the elements using only jQuery’s fadeIn() method.
Now that you understand how the component works, I’ll show you how to create a different variation of it.
Until now, you may have noticed that all elements appear at the same time. I’ll now modify the code to show them sequentially:
<span><span><span><div</span> class<span>="cta filter"</span>></span> </span> <span><span><span><a</span> class<span>="all active"</span> data-filter<span>="all"</span> href<span>="#"</span> role<span>="button"</span>></span>Show All<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-filter<span>="green"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Green Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-filter<span>="blue"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Blue Boxes<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-filter<span>="red"</span> href<span>="#"</span> role<span>="button"</span>></span>Show Red Boxes<span><span></a</span>></span> </span><span><span><span></div</span>></span> </span> <span><span><span><div</span> class<span>="boxes"</span>></span> </span> <span><span><span><a</span> class<span>="red"</span> data-category<span>="red"</span> href<span>="#"</span>></span>Box1<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="green"</span> data-category<span>="green"</span> href<span>="#"</span>></span>Box2<span><span></a</span>></span> </span> <span><span><span><a</span> class<span>="blue"</span> data-category<span>="blue"</span> href<span>="#"</span>></span>Box3<span><span></a</span>></span> </span> <span><!-- other anchor/boxes here ... --> </span> <span><span><span></div</span>></span></span>
The code above looks similar to the previous one but there are a few distinct differences:
The demo below animates the filtered elements sequentially using the zoom-in animation:
See the Pen Sequential filtering/sorting component with CSS & jQuery by SitePoint (@SitePoint) on CodePen.
The demo below animates the filtered elements sequentially using the rotate-right animation:
See the Pen Sequential filtering/sorting with CSS and jQuery by SitePoint (@SitePoint) on CodePen.
This same component could be built without jQuery and may have better performance, but the ability to use jQuery’s fadeIn() and fadeOut() methods allows for simpler code that takes advantage of certain features available to jQuery.
Let me know in the comments if you have a different solution, or a way to improve the code.
Adding more filters to the component is quite straightforward. You need to define the new filter in your CSS and then add the corresponding functionality in your jQuery code. For instance, if you want to add a ‘grayscale’ filter, you would first define it in your CSS like this:
.filter-grayscale {
filter: grayscale(100%);
}
Then, in your jQuery code, you would add a new case to your switch statement to handle the new filter:
switch(filter) {
// existing cases...
case 'grayscale':
$container.addClass('filter-grayscale');
break;
// ...
}
Remember to add a button or some other UI element that allows the user to activate the new filter.
Yes, you can use this filtering component with other JavaScript libraries. jQuery is designed to be compatible with other libraries. You just need to make sure that there are no conflicts between the different libraries. If there are conflicts, you can use jQuery’s noConflict() method to avoid them. This method releases the hold on the `= shortcut identifier, which allows other libraries to use it. You can then use jQuery’s full name to call its methods.
Animating the transition between filters can be achieved by using CSS transitions. You need to add a transition property to the element you want to animate. This property specifies the CSS property to transition, the duration of the transition, the timing function, and the delay before the transition starts. For example, if you want to animate the transition of the filter property over 1 second, you would add the following CSS:
.container {
transition: filter 1s;
}
Then, when you change the filter using jQuery, the transition will be animated.
Yes, you can use this filtering component on multiple elements on the same page. You just need to make sure that each element has a unique ID or class that you can use to select it with jQuery. Then, you can apply the filtering component to each element individually.
Making the filters responsive involves adjusting the CSS and jQuery code based on the size of the viewport. You can use CSS media queries to apply different styles for different viewport sizes. In your jQuery code, you can use the $(window).resize() method to execute code when the window is resized. You can then adjust the filters based on the new size of the window.
Yes, you can use CSS animations without jQuery. CSS animations are a feature of CSS and do not require any JavaScript. However, jQuery can make it easier to manage and control animations, especially if you have complex animations or if you want to animate elements in response to user actions.
Adding a custom filter involves defining a new CSS class with the desired filter effect and then adding the corresponding functionality in your jQuery code. The process is similar to adding more filters, as described in the answer to question 1.
Yes, you can use this filtering component with dynamic content. You just need to make sure that the filtering component is applied to the content after it has been loaded. You can do this by calling the filtering component in the callback function of your AJAX request or in the $(document).ready() function if you are loading the content when the page loads.
Optimizing the performance of the filtering component can involve several strategies. One strategy is to minimize the number of DOM manipulations. Each time you add or remove a class with jQuery, it causes the browser to recalculate the layout, which can be expensive. To minimize this, you can group your changes together and make them all at once. Another strategy is to use CSS transitions instead of jQuery animations, as CSS transitions are generally more performant.
Yes, you can use this filtering component with a backend database. You would need to make an AJAX request to the server to retrieve the data from the database, and then use jQuery to apply the filtering component to the data. This would allow you to filter data based on criteria stored in the database.
The above is the detailed content of Building a Filtering Component with CSS Animations & jQuery. For more information, please follow other related articles on the PHP Chinese website!