Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/drivy/dom-query
Enhanced HTML elements
https://github.com/drivy/dom-query
css-query-selector dom dom-manipulation typescript
Last synced: 3 months ago
JSON representation
Enhanced HTML elements
- Host: GitHub
- URL: https://github.com/drivy/dom-query
- Owner: drivy
- License: mit
- Created: 2019-05-21T08:21:20.000Z (over 5 years ago)
- Default Branch: main
- Last Pushed: 2024-04-17T12:26:27.000Z (10 months ago)
- Last Synced: 2024-11-08T06:43:52.457Z (3 months ago)
- Topics: css-query-selector, dom, dom-manipulation, typescript
- Language: TypeScript
- Homepage:
- Size: 1.8 MB
- Stars: 8
- Watchers: 18
- Forks: 1
- Open Issues: 33
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# Enhanced HTML elements with query/event methods
Utility functions to easily perform DOM element manipulation:
- Element selection based on css query selectors. Chainable. NodeLists automatically converted as Arrays
- Helpers to Attach/detach events. Event delegation supportedThis library is provided as an ES module with Typescript declarations.
## Install
Install with npm:
```ts
$ npm install @drivy/dom-query
```Install with pnpm:
```ts
$ pnpm install @drivy/dom-query
```Install with yarn:
```ts
$ yarn add @drivy/dom-query
```## Usage
```ts
import { query, queryAll } from "@drivy/dom-query";queryAll(".home-header").map(header => console.log(header));
// =>Welcome
// =>Get started
query(".confirm-button").on("click", e => {
confirm(e.target);
});
```## API
### Get elements from the DOM
`query`
- selects an element from the DOM with a css query selector.
- returns `null` if no element matches the selector.
- chainable. Chained method will be based on the last selected element context`queryStrict`
- like `query` method but will raise en exception if no element matches the selector.
`queryAll`
- selects a list of elements from the DOM with a css query selector. NodeList results will be converted to Arrays so you can directly access Array methods (forEach, map, reduce, filter...)
Examples:
```ts
import { query, queryStrict, queryAll } from "@drivy/dom-query"
...
const myElement = query(".js_my-element")
const mySubElement = myElement.query(".js_my-sub-element")
const mySubElements = myElement.queryAll(".js_my-sub-elements")queryAll(".js_my-container .js_my-children-to-select").map(enhancedElement => {
doSomething(enhancedElement)
})const myElement2 = queryStrict(".js_my-existing-element")
//code below won't be reached if the previous element was not found
doSomething(myElement2)```
### Transform existing javascript elements to EnhancedHTMLElements
You can transform an existing javascript Element/List of Elements to an EnhancedHTMLElement/EnhancedHTMLElementList with the following methods:
- `toEnhancedHTMLElement`
- `toEnhancedHTMLElementList`You have to use those methods when input elements are out of your scope (function args, event.target ...)
```ts
import { toEnhancedHTMLElement, toEnhancedHTMLElementList } from "@drivy/dom-query"
...const myElement = toEnhancedHTMLElement(myHTMLElement);
const myElements = toEnhancedHTMLElementList(myHTMLElements);
```### Handle events
You can attach/detach events with the following methods:
EnhancedHTMLElement`.on`
- attaches event like native `target.addEventListener`.
- returns a "detach" function. When called, will remove the event listener like `target.removeEventListener`.EnhancedHTMLElementList`.on`
- same parameters and behavior than EnhancedHTMLElement`.on` but the event will be attached on each element contained in the list.
- returns a "detach" function that when called will detach the events attached on each element of the listEnhancedHTMLElement`.onDelegate`
- does event delegation. [pattern description here](https://davidwalsh.name/event-delegate).
- like `.on` method but takes an extra parameter (first one) as a css query selector to specify the children to use as event targets
- returns a "detach" function. When called, will remove the event listener attached to the container.EnhancedHTMLElementList`.onDelegate`
- same parameters and behavior than EnhancedHTMLElement`.onDelegate` but the event delegation will be done for each element of the list.
- returns a "detach" function that when called will detach the events attached on each element of the listExamples:
```ts
// EnhancedHTMLElementconst detach = myElement.on("click", e => {
doSomething(e.target)
})
...
detach() //same behavior than native target.removeEventListenerconst detachDelegation = myContainer.onDelegate(".js_sub-elements", "click", e => {
doSomething(e.target)
});
// clicking on a child having the "js_sub-elements" class will trigger the event...
detachDelegation() // remove event listener used to delegate// EnhancedHTMLElementList
const detach = queryAll(".js_my-elements").on("click", e => {
doSomething(e.target)
})
...
detach()const detachDelegations = queryAll(".js_my-elements").onDelegate(
".js_my-sub-elements",
"click",
e => {
doSomething(e.target)
}
)
...
detachDelegations()```
### Advanced features
#### Event configuration
When attaching an event with `.on` or `.onDelegate` you can specify an optional event configuration object as last parameter.
This configuration object has a `once` boolean property that when `true` will automatically detach the event after having called once.```ts
myElement2.on(
"click",
e => {
doSomething(e.target);
// event listener will be detached
},
{
once: true
}
);
```#### Specializing the HTMLElement (ex: HTMLInputElement)
Because `EnhancedHTMLElement` enhances `HTMLElement` by default, to access properties/methods from an enhanced HTMLInputElement with Typescript (ex: `myEnhancedInput.value`), you must declare the target Type when calling the query/converting method
```ts
import { query, queryAll, toEnhancedHTMLElement } from "@drivy/dom-query"
...const myEnhancedInput = query(".js_my-target-input");
doSomething(myEnhancedInput.value)const myEnhancedInput2 = toEnhancedHTMLElement(myExistingInput);
doSomething(myEnhancedInput2.value)const myEnhancedInputs = queryAll(".js_my-target-inputs");
myEnhancedInputs.forEach(myInput => {
doSomething(myInput.value);
})
```