datalist Web ComponentWeb component that enables you to dynamically update a field’s datalist with values retrieved from a URL as the user types
npm install @aarongustafson/dynamic-datalist
Import the class and register the element with your preferred tag name:
import { DynamicDatalistElement } from '@aarongustafson/dynamic-datalist';
customElements.define('my-datalist', DynamicDatalistElement);
Use the guarded definition helper to register the element when customElements is available:
import '@aarongustafson/dynamic-datalist/define.js';
If you prefer to control when the element is registered, call the helper directly:
import { defineDynamicDatalist } from '@aarongustafson/dynamic-datalist/define.js';
defineDynamicDatalist();
You can also include the guarded script from HTML:
<script src="./node_modules/@aarongustafson/dynamic-datalist/define.js" type="module"></script>
Wrap an input element with <dynamic-datalist> and specify an endpoint:
<dynamic-datalist endpoint="/api/search">
<input type="text" name="search" placeholder="Type to search..." />
</dynamic-datalist>
This will make a GET request to /api/search?query=WHAT_THE_USER_TYPED.
<dynamic-datalist endpoint="/api/search" method="post">
<input type="text" name="search" placeholder="Type to search..." />
</dynamic-datalist>
This will make a POST request with JSON body: { "query": "WHAT_THE_USER_TYPED" }.
<dynamic-datalist endpoint="/api/search" key="term">
<input type="text" name="search" placeholder="Type to search..." />
</dynamic-datalist>
This will send the query as /api/search?term=WHAT_THE_USER_TYPED (GET) or { "term": "..." } (POST).
If your input already has a datalist, the component will use and update it:
<dynamic-datalist endpoint="/api/cities">
<input type="text" list="cities-list" placeholder="Type a city..." />
<datalist id="cities-list">
<option>New York</option>
<option>Los Angeles</option>
<option>Los Angeles</option>
<option>Chicago</option>
</datalist>
</dynamic-datalist>
The component will preserve and update the existing datalist instead of creating a new one.
Your endpoint should return JSON in this format:
{
"options": [
"option 1",
"option 2",
"option 3"
]
}
| Attribute | Type | Default | Description |
|---|---|---|---|
endpoint |
string |
(required) | URL to the JSON endpoint |
method |
string |
"get" |
HTTP method: get or post |
key |
string |
"query" |
Variable name for the query parameter |
The component fires custom events that you can listen to:
| Event | Description | Detail |
|---|---|---|
dynamic-datalist:ready |
Fired when component is initialized | { input, datalist } |
dynamic-datalist:update |
Fired when datalist is updated | { input, datalist, options } |
dynamic-datalist:error |
Fired when an error occurs | { input, datalist, error } |
const element = document.querySelector('dynamic-datalist');
element.addEventListener('dynamic-datalist:update', (event) => {
console.log('Received options:', event.detail.options);
});
element.addEventListener('dynamic-datalist:error', (event) => {
console.error('Error fetching options:', event.detail.error);
});
import '@aarongustafson/dynamic-datalist/define.js';
// Registers <dynamic-datalist> when customElements is available
You can also call the helper manually:
import { defineDynamicDatalist } from '@aarongustafson/dynamic-datalist/define.js';
defineDynamicDatalist();
import { DynamicDatalistElement } from '@aarongustafson/dynamic-datalist';
customElements.define('my-datalist', DynamicDatalistElement);
This component uses modern web standards:
For older browsers, you may need polyfills.
This component replaces my older jQuery plugin jquery.easy-predictive-typing.js.
# Install dependencies
npm install
# Run tests
npm test
# Run tests with coverage
npm run test:coverage
# View demo
open demo/index.html
MIT © Aaron Gustafson