jQuery tablesorter 2.0 - Custom Filter Widget Functions

# tablesorter

## Custom Filter Widget Functions

### Flexible client-side table sorting

Back to documentation

### Notes

- In v2.22.0,
  - An additional `data` parameter was added to the filter functions. It is an object which contains all data provided to the filter type functions (see all the data values here).
  - *WARNING* In a future update, the filter function parameters will change to clean up the code (I know, it's messy)!

        filter_functions : {
          // function(e, n, f, i, $r, c, data) {} <- current parameters
          0 : function(c, data) {} // planned change (version undetermined)
        }

    The `e` (exact table cell text), `n` (normalized table cell text), `f` (filter input value), `i` (column index) and `$r` (current row; jQuery object) are all already included in the `data` object.

- In v2.21.0, the filter functions provide an additional parameter `c` which is the `table.config`.
- In v2.17.0, the `filter_functions` column can also be referenced by using a jQuery selector (e.g. class name or ID).
- In v2.16.3,
  - When a default filter select is added to a column, it is now parsed from the assigned parser, then sorted using the `textSorter` setting, and falls back to an alphanumeric sort.
  - Adding a class of `"filter-select-nosort"` will now leave the select options unsorted.
- In v2.14, the `filter_saveFilters` option was added (default set to `false`); this demo has it set to `true` to provide an example.
- In v2.11, the filter functions provide an additional parameter `$r` providing a jQuery object of the current row being searched by the filter.
- For v2.10.8, the Age column includes the new `data-value` set to `<30` which sets the default (starting) filter value (see filter_defaultAttrib for more details).
- As of tablesorter v2.9, this widget can no longer be applied to versions of tablesorter prior to version 2.8.
- Custom filter widget option `filter_functions` was added in version 2.3.6.
- jQuery v1.4.3+ required.

### Default Select ("First Name" column)

- To enable this type of select, set the `filter_functions` option for the column to `true`,

      filter_functions : {

        // Add select menu to this column
        // set the column value to true, and/or add "filter-select" class name to header
        '.first-name' : true

      }

  or add a "filter-select" class to the column header cell (see code below).
- The default option text, "Select a name", is obtained from the header `data-placeholder` attribute of the column header cell. And when active, it will show all table rows.

      <th class="filter-select" data-placeholder="Select a name">First Name</th>

- Add a "filter-match" class to only match instead of exactly match the selected value. Click on the "Match" button below to see the difference.

      <th class="filter-select filter-match" data-placeholder="Select a name">First Name</th>

- The select is populated by the column text contents with repeated content combined (i.e. There are three "Aaron"'s in the first column, but only one in the dropdown.
- Select options are automatically alphanumerically (new in v2.4) sorted. Changed in v2.16.3:
  - The select contents are now parsed from the assigned parser, then sorted using the `textSorter` option
  - Add a class name of `"filter-select-nosort"` to prevent sorting the select options (v2.16.3).
- Please check out what the "filter-onlyAvail" class name does by reviewing the details below (in the "Discount" column) (v2.10.1).

### Custom Filter Function ("Last Name" column)

- To enable this type of filter, add your custom function to the `filter_functions` option following this example:

      filter_functions : {

        // Exact match only
        1 : function(e, n, f, i, $r, c, data) {
          return e === f;
        }

      }

- The example shows you how to show only exact matches. The problem with this is that you can't see the matches while typing unless you set the `filter_searchDelay` option to be a bit longer.
- Also, the example only checks for an exact match (`===`) meaning the `filter_ignoreCase` option is ignored, but other comparisons can be made using regex and the insensitive "i" flag.
- *NOTE* If using an exact match function like this, consider setting the `filter_searchFiltered` option to false. If it were set to `true`, the filter widget wouldn't know to search through the entire contents of the column if the content were only slightly different. To see this problem, search for
  in the "Last Name" column, then add an "s" to the end to find "Evans". No results will show up, unless the search filtered option is `false`.
- See the filter function information below for more details about the function parameters.

### Custom Select ("City" or "Total" column)

- To enable this type of select, add your custom options within the `filter_functions` option.
- Each option is set as a "key:value" pair where the "key" is the actual text of the option and the "value" is the function associated with the option.
- Here is an example using alphabetical comparisons (using regular expressions):

      filter_functions : {

        // Add these options to the select dropdown (regex example)
        2 : {
          "A - D" : function(e, n, f, i, $r, c, data) { return /^[A-D]/.test(e); },
          "E - H" : function(e, n, f, i, $r, c, data) { return /^[E-H]/.test(e); },
          "I - L" : function(e, n, f, i, $r, c, data) { return /^[I-L]/.test(e); },
          "M - P" : function(e, n, f, i, $r, c, data) { return /^[M-P]/.test(e); },
          "Q - T" : function(e, n, f, i, $r, c, data) { return /^[Q-T]/.test(e); },
          "U - X" : function(e, n, f, i, $r, c, data) { return /^[U-X]/.test(e); },
          "Y - Z" : function(e, n, f, i, $r, c, data) { return /^[Y-Z]/.test(e); }
        }

      }

- Here is an example using numerical comparisons:

      filter_functions : {
        // Add these options to the select dropdown (numerical comparison example)
        // Note that only the normalized (n) value will contain numerical data
        // If you use the exact text, you'll need to parse it (parseFloat or parseInt)
        4 : {
          "< $10"      : function(e, n, f, i, $r, c, data) { return n < 10; },
          "$10 - $100" : function(e, n, f, i, $r, c, data) { return n >= 10 && n <=100; },
          "> $100"     : function(e, n, f, i, $r, c, data) { return n > 100; }
        }
      }

- See the "Filter function information" section below for more details about the function parameters.

### Default Select with only available options ("Discount" column)

- This column uses the same method as the "First Name" column with one exception, it also includes the "filter-onlyAvail" class name in the header cell:

      <th class="filter-select filter-onlyAvail">Discount</th>

- To see how this works, do the following:
  - First, filter the "First Name" column by selecting the name "Clark"
  - Now use the "Discount" filter select box, you'll notice that only the values associated with the first name of Clark are showing as options.
- Conversely, if you reset the filters, select "44%" in the "Discount" column, then look at the "First Name" filter selector, you'll notice that it still contains all of the original options; because the "filter-onlyAvail" class name is not included in that column's header cell.
- Sorry, this functionality only works for default select filters.
- This funcitonality was added in v2.10.1.

### Filter function information

- The custom function must return a boolean value. If `true` is returned, the row will be shown if all other filters match; and if `false` is returned, the row will be hidden.

      function(e, n, f, i, $r, c, data) { return test; /* test should be a Boolean (true or false) */ }

- The exact text (e) of the table cell is a variable passed to the function. Note that numbers will need to be parsed to make comparisons.
- Normalized table cell data (n) is the next varibale passed to the function.
  - This data has been parsed by the assigned column parser, so make sure the same type of data is being compared as parsed data may not be what you expect.
  - Normalized numerical values within the table will be of numeric type and not of string type, as the sorter needs to use mathematical comparisons while sorting.
  - The data will be in lower-case if the `filter_ignoreCase` option is `true`.
  - Dates like in the last column of the table below will store the time in seconds since 1970 (using javascript's .getTime() function).
  - The percentage column will only store the number and not percentage sign.
- The filter input value (f) is the exact text entered by the user. If numerical, it will need to be parsed using parseFloat() or parseInt() to allow for making comparisons.
- The column index (i) might be useful for obtaining more information from header, or something.
- The row ($r) is the current table row (jQuery object) being searched (or filtered).
  - This allows access to any extra information within. To access the current cell, just use `$r.children().eq(i)`.
  - * NOTE * The row object provided is not attached to the table, so using something like `.parent()` or `.closest()` will not work!
  - For this reason, the next parameter (`c`) was added.
- The config (c) is the `table.config` (added v2.21.0).
- The data parameter is the same data passed to the filter types (see all the data values here; added v2.22.0).

# Demo

false "filter-match" class name on the "First Name" column
filter_searchFiltered : true (if true, the search is performed on already filtered rows, with some exceptions)

First Name | Last Name | City | Age | Total | Discount | Date
--- | --- | --- | --- | --- | --- | ---
Aaron | Johnson Sr | Atlanta | 35 | $5.95 | 22% | Jun 26, 2004 7:22 AM
Aaron | Johnson | Yuma | 12 | $2.99 | 5% | Aug 21, 2009 12:21 PM
Clark | Henry Jr | Tampa | 51 | $42.29 | 18% | Oct 13, 2000 1:15 PM
Denni | Henry | New York | 28 | $9.99 | 20% | Jul 6, 2006 8:14 AM
John | Hood | Boston | 33 | $19.99 | 25% | Dec 10, 2002 5:14 AM
Clark | Kent Sr | Los Angeles | 18 | $15.89 | 44% | Jan 12, 2003 11:14 AM
Peter | Kent Esq | Seattle | 45 | $153.19 | 44% | Jan 18, 2021 9:12 AM
Peter | Johns | Milwaukee | 13 | $5.29 | 4% | Jan 8, 2012 5:11 PM
Aaron | Evan | Chicago | 24 | $14.19 | 14% | Jan 14, 2004 11:23 AM
Bruce | Evans | Upland | 22 | $13.19 | 11% | Jan 18, 2007 9:12 AM
Clark | McMasters | Pheonix | 18 | $55.20 | 15% | Feb 12, 2010 7:23 PM
Dennis | Masters | Indianapolis | 65 | $123.00 | 32% | Jan 20, 2001 1:12 PM
John | Hood | Fort Worth | 25 | $22.09 | 17% | Jun 11, 2011 10:55 AM

# Javascript

# HTML

Next up: Custom Filter Widget Search Types ››