Jason Ayer Jason Ayer - 5 months ago 20
jQuery Question

jQuery filter with checkbox and li

I'm trying to create a javascript filter with checkboxes as the filter criteria elements and hiding the respective

<li>
elements:

Here is rendered sample of my search filters:

<input type=[checkbox] class="filter" data-city="Memphis">
<input type=[checkbox] class="filter" data-city="Cordova">
<input type=[checkbox] class="filter" data-city="Bartlett">


And here are my results:

<li class="result" data-city="Memphis">Memphis</li>
<li class="result" data-city="Memphis">Memphis</li>
<li class="result" data-city="Cordova">Cordova</li>
<li class="result" data-city="Bartlett">Bartlett</li>


Here is my javascript, which isn't working quite like I want it to:

$('.filter').change(function(){
var city = $(this).data("city");
if($(this).is(":checked")){
$('li.result').is('[data-city="'+city+'"]').show();
$('li.result').not('[data-city="'+city+'"]').hide();
}
else{
$('li.result').not('[data-city="'+city'"]').show();
}
});


I end up with a toggle-like result. How do I make it to where for each input that is checked, show the li's that correspond with it, and hide the others? Also to unhide the ones when they become unchecked.

Answer

On each checkbox click you can look up the corresponding item and checkbox to determine visibility.

Since you want everything visible when nothing is checked, and only filter down results if something is checked, additional logic is placed at the end of the handler for that specific case.

Fiddle

$('.filter').change(function(){     
    //on each click, refresh visible / hidden for each item
    $('li.result').each(function(i, item){
      var city = $(this).data('city');
      var visible = $('input.filter[data-city="' + city + '"]:checked').length > 0;
      visible ? $(this).show() : $(this).hide();
    });

    //if no checkboxes are checked, show everything
    if($('input.filter:checked').length === 0) $('li.result').show();
});

Added some labels to the checkboxes to make testing easier.

<input type="checkbox" class="filter" data-city="Memphis"> memphis
<input type="checkbox" class="filter" data-city="Cordova"> cordova
<input type="checkbox" class="filter" data-city="Bartlett"> bartlett

<ul>
<li class="result" data-city="Memphis">Memphis</li>
<li class="result" data-city="Memphis">Memphis</li>
<li class="result" data-city="Cordova">Cordova</li>
<li class="result" data-city="Bartlett">Bartlett</li>
</ul>