Search a table's cell for a term and display only respective rows
no jQuery - only vanilla ES6 JavaScript
These kind of client-side searchable functionality is done only in JavaScript.
But even the initialization of the table content is 99% of the time JavaScript-based where the developer has to feed in the entire initial cell data to an array and pass that array into to a function after which the 3rd party script / library would render the table into HTML and display it dynamically. This is cool - can be easily done in React, Vue or AlpineJS.
But what if wanted the table HTML coded first for reasons like a designer's preference or SEO where the search engines can 'see' the table initially ? (Now-a-days Google already can 'see' a JavaScript rendered table though)
Imagine just injecting a script to an HTML page which already has a large table coded in using table
, thead
, tbody
, tr
, th
and td
that the JavaScript code can read through all the values and then decide which rows to hide/display based on the existence of the search term !
The search box :
<div class="d-flex">
<input type="text" name="search" id="search" class="form-control" placeholder="type in a search term here"/>
<!-- <button id="btn-search" class="btn btn-primary ms-1">Search</button> -->
</div>
The table :
<table id="tbl-products" class="table table-light table-striped table-hover table-bordered">
<thead>
<tr>
<th scope="col" class="text-center">#</th>
<th scope="col" class="text-center">Year</th>
<th scope="col">Product</th>
<th scope="col" class="text-center">Starting Price</th>
</tr>
</thead>
<tbody>
<tr>
<th scope="row" class="text-center">1</th>
<td class="text-center">2022</td>
<td>
<a href="/mac/13-inch-macbook-air-apple-m2-256gb/">
13-INCH MACBOOK AIR M2 256GB
</a>
</td>
<td class="text-center">₹1,19,900</td>
</tr>
<tr>
<th scope="row" class="text-center">2</th>
<td class="text-center">2022</td>
<td>
<a href="/mac/13-inch-macbook-air-apple-m2-521gb/">
13-INCH MACBOOK AIR M2 512GB
</a>
</td>
<td class="text-center">₹1,49,900</td>
</tr>
<tr>
<th scope="row" class="text-center">3</th>
<td class="text-center">2021</td>
<td>
<a href="/mac/macbook-pro-14-inch/">
MACBOOK PRO (14-INCH) 512GB 16GB
</a>
</td>
<td class="text-center">₹1,94,900</td>
</tr>
<tr>
<th scope="row" class="text-center">4</th>
<td class="text-center">2021</td>
<td>
<a href="/mac/macbook-pro-16-512gb-32gb/">
MACBOOK PRO (16-INCH) 512GB 32GB
</a>
</td>
<td class="text-center">₹2,39,900</td>
</tr>
<tr>
<th scope="row" class="text-center">5</th>
<td class="text-center">2021</td>
<td>
<a href="/mac/macbook-pro-16-1tb-32gb-2021/">
MACBOOK PRO (16-INCH) 1TB 32GB
</a>
</td>
<td class="text-center">₹2,59,900</td>
</tr>
<tr>
<th scope="row" class="text-center">6</th>
<td class="text-center">2020</td>
<td>
<a href="/mac/macbook-pro-13-with-M1-chip-512gb/">
MACBOOK PRO 13” WITH M1 CHIP 512GB
</a>
</td>
<td class="text-center">₹1,34,326</td>
</tr>
<tr>
<th scope="row" class="text-center">7</th>
<td class="text-center">2020</td>
<td>
<a href="/mac/macbook-pro-13-with-m1-chip-256gb/">
MACBOOK PRO 13” WITH M1 CHIP 256GB
</a>
</td>
<td class="text-center">₹1,15,526</td>
</tr>
</tbody>
</table>
The JavaScript :
let trs;
document.addEventListener("DOMContentLoaded", () =>
{
let tbl_products = document.getElementById('tbl-products');
let tbl_products_tbody_trs = tbl_products.querySelectorAll('tbody > tr');
trs = [...tbl_products_tbody_trs];
});
document.addEventListener("DOMContentLoaded", () =>
{
document.getElementById('search').addEventListener('input', (e) =>
{
let search = e.target.value;
trs.forEach(tr =>
{
let found = false;
[...tr.children].forEach(child =>
{
if (child.localName == 'th') return;
let cell = child.innerHTML.trim();
if (cell.toLowerCase().includes(search.toLowerCase()))
{
found = true;
return;
}
});
tr.style.display = found ? 'table-row' : 'none';
});
});
});