ben tedder : code things

Create a jQuery + SharePoint instant search/filter

We’re going to use jQuery and SharePoint to create an “instant” search/filter of a Content Query WebPart and/or List View. This uses the .find(), :contains(), .val(), .hide(), .show(), :not(), .change(), and .keyup() jQuery codes. You can learn all about those from the jQuery documentation. This is all client-side, and only deals with what shows on the page. I'm not going to deal with any server requests, pagination of lists, etc. That's for later.

Check out the video tutorial below:

You’ll be creating something like this:

Step 1: Load jQuery script in your master page

Because our SharePoint installation is secured, I downloaded the latest jQuery build instead of sourcing it from online. So my script in the master page looks like this:

<script type="text/javascript" src="/Style Library/scripts/jquery.js"></script>

Step 2: Create a page with a CQWP or a list view

Doesn’t matter which one you create, but just have some content we can filter.

Step 3: The Code

I built a lot of this from scratch using the jQuery documentation, but a big shout-out goes to Kilian Valkhof’s article, which helped me organize a lot of what I had. This first part enables case-insensitive searching. It came from Kilian Valkhof, who apparently sourced it from Mike Merrit’s LiveFilter jQuery Plugin, but I’m not sure. Either way, I didn’t write it :). Note:if you use this expression, it means you need to change every instance of contains (small C) to Contains (capital C).

<script type="text/javascript">
jQuery.expr[':'].Contains = function(a,i,m){return (a.textContent || a.innerText || "").toUpperCase().indexOf(m[3].toUpperCase())>=0;};

Now we start our function anytime the search input box is changed. Once it's changed, it sets the value of a variable we have called "txt".

$(document).ready(function(){
  $("input.search").change(function() {
      var txt = $("input.search").val();

Here we have an IF statement that just checks if there is indeed something in the search box, ELSE everything goes back to normal. If there is something inside the search input box, we are going to do two things. First, we'll find any row that does NOT contain the string, and we'll hide that row. Then we'll find any row that DOES contain that string, and we'll show that row. Finally, we chain a "keyup" function to the change function so that as we type everything is happening all together.

if (txt) {
     $("#WebPartWPQ4").find("tr.ms-itmhover:not(:Contains("+txt+"))").hide();
     $("#WebPartWPQ4").find("tr.ms-itmhover:Contains("+txt+")").show();
    } else {
     $("#WebPartWPQ4").find("tr.ms-itmhover").show();
    }
  }).keyup(function(){$(this).change();
 });
});

And last but not least, we'll create a simple search input box with a class of "search". My styling is attached, feel free to erase and do your own:

<div style="padding: 5px; border: 1px solid #cccccc; width: 60%; margin: 10px auto 0pt; background: none repeat scroll 0% 0% #efefef; display: block;">
  <h3 style="text-align: center;">Instant search: <input class="search" style="padding: 10px;" type="text" /></h3>
</div>

Step 4: Final touches

The final step is to put this code inside a Content Editor WebPart (I know, I know, but this is for the sake of this tutorial, definitely not best practice). You’ll have to change the target it’s searching and replace it based on whether or not you’re using a CQWP or a list view. A few tips:

#WebPartWPQ4 is the ID of the webpart on my page, but it might change depending on how many webparts you have, what kind they are, etc.

tr.ms-itmhover seems to be the correct selector for any row in a list view

For searching in a Content Query WebPart, I use this:

find("a:Contains("+txt+")").parents("li.dfwp-item").show();

Note that I used parents instead of parent because the latter only searches one level up. CQWP list items are so intricately embedded deep down that you have to find the text inside the link, and then hide the whole list item. Just play around with it, let me know if you need any help.