---
meta:
  title: Data Table Filter
  description: An inline filter bar for data tables. Each active filter is a pill whose dropdown sets its value, alongside an add-filter control and a clear.
layout: component
---

```html:preview

<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;title&quot;,&quot;name&quot;:&quot;Title&quot;,&quot;operators&quot;:[&quot;eq&quot;]},{&quot;id&quot;:&quot;author&quot;,&quot;name&quot;:&quot;Author&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;genre&quot;,&quot;name&quot;:&quot;Genre&quot;,&quot;options&quot;:{&quot;action&quot;:&quot;Action&quot;,&quot;comedy&quot;:&quot;Comedy&quot;,&quot;drama&quot;:&quot;Drama&quot;,&quot;fantasy&quot;:&quot;Fantasy&quot;,&quot;horror&quot;:&quot;Horror&quot;,&quot;mystery&quot;:&quot;Mystery&quot;,&quot;romance&quot;:&quot;Romance&quot;,&quot;thriller&quot;:&quot;Thriller&quot;,&quot;sci-fi&quot;:&quot;ScienceFiction&quot;},&quot;maxOptionsVisible&quot;:&quot;3&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;rating&quot;,&quot;name&quot;:&quot;Rating&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;gte&quot;,&quot;lt&quot;,&quot;lte&quot;]},{&quot;id&quot;:&quot;created&quot;,&quot;name&quot;:&quot;Created&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;before&quot;,&quot;after&quot;]}]">
</zn-data-table-filter>
```

Filters render inline rather than in a slideout. Each active filter is a pill showing its name, and its value once set; the pill's dropdown lists the filter's `options` as checkable values, or a text input for a filter that declares none. Each pill carries an X that drops that filter. `+ Add filter` lists the filters that are not yet active, and `Clear` removes them all.

A filter starts on its **first declared operator**. Declare more than one and the pill offers a choice: a value editor gets a row of operator chips above it, an options menu lists the operators above its values, and the pill then reads `Age ≥ 18` rather than `Age: 18`. Switching operator keeps the value — a date is re-encoded for the new comparator.

Declare `in` or `nin` to let a filter hold several values at once — the pill then counts them, e.g. `Role (2)`, and its dropdown stays open so you can pick more. Any other operator holds a single value: the dropdown closes on select, and picking the same value again clears it.

Picking a filter from `+ Add filter` opens its pill straight away, with a text field focused, so naming a filter and giving it a value is one pass. A typed value is one value however many spaces it contains; only a comma starts another.

`default-filters` takes a comma-separated list of filter ids to show a pill for up front. Inside a `zn-data-table` the bar is hidden until the header's filter toggle is clicked, and `activeCount` reports how many filters currently hold a value.

```html:preview
<zn-data-table-filter
  default-filters="status"
  filters='[
    {"id":"status","name":"Status","options":{"open":"Open","closed":"Closed"},"operators":["eq"]},
    {"id":"tag","name":"Tag","options":{"bug":"Bug","chore":"Chore","feature":"Feature"},"operators":["in"]},
    {"id":"owner","name":"Owner","operators":["contains"]}
  ]'>
</zn-data-table-filter>
```

The component emits `zn-filter-change` and exposes the query on `value`, encoded exactly as `zn-query-builder` encodes it — base64 of `[{key, comparator, value}]` — so a backend built against the query builder needs no changes.

Setting `value` round-trips: assigning that same base64 string back — for example restoring it from a shared URL via `zn-data-table`'s [`sharable`](/components/data-table#shareable-url-state) sync — rebuilds the active pills, so the bar reopens in the state it was encoded in. Restoration needs the `filters` schema present to resolve each key, and it stands down once any filter already holds a value, so a shared filter still wins over an empty `default-filters` pill while a filter the user is mid-way through setting is never clobbered.

One caveat: a restored **date** filter shows its raw encoded value on the pill (a timestamp, or a minutes-from-now offset) rather than a formatted date, because the human-readable label is not part of the encoded query. The filter still applies correctly; only the pill text differs until the value is re-picked.

### Long Option Lists

An option list caps its height at 320px and scrolls inside the panel rather than running off the
screen, with the scrollbar drawn rather than left to the platform's overlay one. Past eight options
the pill also gains a search field, merged into the top of the panel and pinned there, that narrows
the list case-insensitively.

```html:preview
<zn-data-table-filter
  default-filters="category"
  filters='[
    {"id":"category","name":"Category","operators":["eq","in"],"options":{
      "how-to":"How To","linux":"Linux","beta":"Beta","router":"Router","tv":"TV","other":"Other",
      "mac":"Mac Hotspot Shield","general":"General","android":"Android Hotspot Shield",
      "educational":"Educational","windows":"Windows Hotspot Shield","ios":"iOS",
      "getting-started":"Getting Started","payments":"Payments & Subscriptions",
      "accounts":"Manage Account & Devices","troubleshoot":"Troubleshoot issues",
      "releases":"Release Notes","archived":"Archived Articles","internal":"Internal Information",
      "tutorials":"Tutorials"}}
  ]'>
</zn-data-table-filter>
```

### Typeahead

Inside a `zn-data-table` a text filter suggests values from the rows the table has already loaded, matched case-insensitively against what has been typed, keyed on the column whose name matches the filter's id. Set `suggestions` yourself — `{[filterId]: string[]}` — to offer something else.

## Examples

### Basic Text Filters

Create simple text-based filters with equality and fuzzy search operators.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;name&quot;,&quot;name&quot;:&quot;Name&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;email&quot;,&quot;name&quot;:&quot;Email&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;company&quot;,&quot;name&quot;:&quot;Company&quot;,&quot;operators&quot;:[&quot;eq&quot;]}]"
  name="text-filters">
</zn-data-table-filter>
```

### Number Filters with Operators

Use number type filters with comparison operators like equal, greater than, less than. The pill's
editor shows a chip per operator; `>`, `≥`, `<` and `≤` keep their symbols, and the rest read as words.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;age&quot;,&quot;name&quot;:&quot;Age&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;gte&quot;,&quot;lt&quot;,&quot;lte&quot;]},{&quot;id&quot;:&quot;price&quot;,&quot;name&quot;:&quot;Price&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;lt&quot;]},{&quot;id&quot;:&quot;quantity&quot;,&quot;name&quot;:&quot;Quantity&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gte&quot;,&quot;lte&quot;]}]"
  name="number-filters">
</zn-data-table-filter>
```

### Date Filters

Filter by dates with before, after, and equal operators. A `date` pill opens a calendar and closes
once a day is picked; a `dateTime` pill adds a time selector and stays open while it's set.

Values are encoded the way `zn-query-builder` encodes them, so `dateSubmitFormat` picks the wire
format: `legacy` (the default — seconds for `eq`/`neq`, otherwise minutes from now, negated for
`before`), `timestamp` (milliseconds) or `iso`.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;created&quot;,&quot;name&quot;:&quot;Created Date&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;before&quot;,&quot;after&quot;]},{&quot;id&quot;:&quot;modified&quot;,&quot;name&quot;:&quot;Modified Date&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;before&quot;,&quot;after&quot;]},{&quot;id&quot;:&quot;due_date&quot;,&quot;name&quot;:&quot;Due Date&quot;,&quot;type&quot;:&quot;dateTime&quot;,&quot;dateSubmitFormat&quot;:&quot;iso&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;before&quot;,&quot;after&quot;]}]"
  name="date-filters">
</zn-data-table-filter>
```

### Dropdown Options

Use predefined options for select-based filtering.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;status&quot;,&quot;name&quot;:&quot;Status&quot;,&quot;options&quot;:{&quot;open&quot;:&quot;Open&quot;,&quot;in_progress&quot;:&quot;In Progress&quot;,&quot;closed&quot;:&quot;Closed&quot;},&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;priority&quot;,&quot;name&quot;:&quot;Priority&quot;,&quot;options&quot;:{&quot;low&quot;:&quot;Low&quot;,&quot;medium&quot;:&quot;Medium&quot;,&quot;high&quot;:&quot;High&quot;,&quot;critical&quot;:&quot;Critical&quot;},&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]}]"
  name="option-filters">
</zn-data-table-filter>
```

### Limited Options Display

Control how many options are initially visible using `maxOptionsVisible`.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;category&quot;,&quot;name&quot;:&quot;Category&quot;,&quot;options&quot;:{&quot;cat1&quot;:&quot;Category 1&quot;,&quot;cat2&quot;:&quot;Category 2&quot;,&quot;cat3&quot;:&quot;Category 3&quot;,&quot;cat4&quot;:&quot;Category 4&quot;,&quot;cat5&quot;:&quot;Category 5&quot;,&quot;cat6&quot;:&quot;Category 6&quot;},&quot;maxOptionsVisible&quot;:3,&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]}]"
  name="limited-options">
</zn-data-table-filter>
```

### Mixed Filter Types

Combine different field types in a single filter component.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;product&quot;,&quot;name&quot;:&quot;Product Name&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;category&quot;,&quot;name&quot;:&quot;Category&quot;,&quot;options&quot;:{&quot;electronics&quot;:&quot;Electronics&quot;,&quot;clothing&quot;:&quot;Clothing&quot;,&quot;books&quot;:&quot;Books&quot;},&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;price&quot;,&quot;name&quot;:&quot;Price&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;lt&quot;]},{&quot;id&quot;:&quot;in_stock&quot;,&quot;name&quot;:&quot;In Stock&quot;,&quot;type&quot;:&quot;boolean&quot;,&quot;operators&quot;:[&quot;eq&quot;]}]"
  name="mixed-filters">
</zn-data-table-filter>
```

### Employee Filter Example

A practical example for filtering employee data.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;employee_name&quot;,&quot;name&quot;:&quot;Employee Name&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;department&quot;,&quot;name&quot;:&quot;Department&quot;,&quot;options&quot;:{&quot;engineering&quot;:&quot;Engineering&quot;,&quot;sales&quot;:&quot;Sales&quot;,&quot;marketing&quot;:&quot;Marketing&quot;,&quot;hr&quot;:&quot;Human Resources&quot;,&quot;finance&quot;:&quot;Finance&quot;},&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;hire_date&quot;,&quot;name&quot;:&quot;Hire Date&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;before&quot;,&quot;after&quot;]},{&quot;id&quot;:&quot;salary&quot;,&quot;name&quot;:&quot;Salary&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;gt&quot;,&quot;lt&quot;]}]"
  name="employee-filters">
</zn-data-table-filter>
```

### E-commerce Filter Example

Filter products with various criteria.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;title&quot;,&quot;name&quot;:&quot;Product Title&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;brand&quot;,&quot;name&quot;:&quot;Brand&quot;,&quot;operators&quot;:[&quot;eq&quot;]},{&quot;id&quot;:&quot;category&quot;,&quot;name&quot;:&quot;Category&quot;,&quot;options&quot;:{&quot;electronics&quot;:&quot;Electronics&quot;,&quot;clothing&quot;:&quot;Clothing&quot;,&quot;home&quot;:&quot;Home &amp; Garden&quot;,&quot;sports&quot;:&quot;Sports&quot;,&quot;toys&quot;:&quot;Toys&quot;},&quot;maxOptionsVisible&quot;:3,&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;price&quot;,&quot;name&quot;:&quot;Price&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;gte&quot;,&quot;lt&quot;,&quot;lte&quot;]},{&quot;id&quot;:&quot;rating&quot;,&quot;name&quot;:&quot;Rating&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;gte&quot;]},{&quot;id&quot;:&quot;release_date&quot;,&quot;name&quot;:&quot;Release Date&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;before&quot;,&quot;after&quot;]}]"
  name="product-filters">
</zn-data-table-filter>
```

### Content Library Filter

Filter media content like books, movies, or articles.

```html:preview
<zn-data-table-filter
  filters="[{&quot;id&quot;:&quot;title&quot;,&quot;name&quot;:&quot;Title&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;author&quot;,&quot;name&quot;:&quot;Author&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;fuzzy&quot;]},{&quot;id&quot;:&quot;genre&quot;,&quot;name&quot;:&quot;Genre&quot;,&quot;options&quot;:{&quot;action&quot;:&quot;Action&quot;,&quot;comedy&quot;:&quot;Comedy&quot;,&quot;drama&quot;:&quot;Drama&quot;,&quot;fantasy&quot;:&quot;Fantasy&quot;,&quot;horror&quot;:&quot;Horror&quot;,&quot;mystery&quot;:&quot;Mystery&quot;,&quot;romance&quot;:&quot;Romance&quot;,&quot;thriller&quot;:&quot;Thriller&quot;,&quot;sci-fi&quot;:&quot;Science Fiction&quot;},&quot;maxOptionsVisible&quot;:3,&quot;operators&quot;:[&quot;eq&quot;,&quot;in&quot;]},{&quot;id&quot;:&quot;rating&quot;,&quot;name&quot;:&quot;Rating&quot;,&quot;type&quot;:&quot;number&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;gt&quot;,&quot;gte&quot;,&quot;lt&quot;,&quot;lte&quot;]},{&quot;id&quot;:&quot;published&quot;,&quot;name&quot;:&quot;Published Date&quot;,&quot;type&quot;:&quot;date&quot;,&quot;operators&quot;:[&quot;eq&quot;,&quot;before&quot;,&quot;after&quot;]}]"
  name="content-filters">
</zn-data-table-filter>
```
