# element
**Repository Path**: mirrors_WebReflection/element
## Basic Information
- **Project Name**: element
- **Description**: A minimalistic DOM element creation library.
- **Primary Language**: Unknown
- **License**: MIT
- **Default Branch**: main
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2025-09-13
- **Last Updated**: 2025-12-20
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# @webreflection/element
**Social Media Photo by [James Owen](https://unsplash.com/@jhjowen) on [Unsplash](https://unsplash.com/)**
A minimalistic DOM element creation library.
## Usage and Description
The *default* export is a function that accepts a `tag` and an optional `options` or `setup` literal, plus zero, one or more *childNodes* to append: `(tag:string|Node, options:object?, ...(Node|string)[])`
### The `tag`
* if it's an *Element* already it uses options to enrich the element as described
* if it's a `string` and it does not start with `<`, it creates a new *Element* with such name
* if it starts with `svg:` (followed by its name) or the `tag` value is `svg` itself, it creates an *SVGElement*
* in every other case it creates an *HTMLElement* or, of course, a *CustomElement* with such name or, if `options.is` exists, a custom element builtin extend
* if it's a `string` and it starts with `<` it uses the element found after `document.querySelector`. If no element is found, it returns `null` out of the box.
### The `options`
Each option `key` / `value` pair is handled to enrich the created or retrieved element in a library friendly way.
#### The `key`
* if `key in element` is `false`:
* **aria** and **data** are used to attach `aria-` prefixed attributes (with the `role` exception) or the element `dataset`
* **class**, **html** and **text** are transformed into `className`, `innerHTML` and `textContent` to directly set these properties with less, yet semantic, typing
* **@type** is treated as *listener* intent. If its value is an *array*, it is possible to add the third parameter to `element.addEventListener(key.slice(1), ...value)`, otherwise the listener will be added without options
* **?name** is treated as boolean attribute intent and, like it is for *@type*, the key will see the first char removed
* if `key in element` is `true`:
* **classList** adds all classes via `element.classList.add(...value)`
* **style** content is directly set via `element.style.cssText = value` or via `element.setAttribute('style', value)` in case of *SVG* element
* everything else, including **on...** handlers, is attached directly via `element[key] = value`
#### The `value`
If `key in element` is `false`, the behavior is inferred by the value:
* a `boolean` value that is not known in the *element* will be handled via `element.toggleAttribute(key, value)`
* a `function` or an `object` with a `handleEvent` are handled via `element.addEventListener(key, value)`
* an `object` without `handleEvent` will be serialized as *JSON* to safely land as `element.setAttribute(key, JSON.stringify(value))`
* `null` and `undefined` are simply ignored
* everything else is simply added as `element.setAttribute(key, value)`
Please read the [example](#example) to have more complete example of how all these features play together.
- - -
## Example - [Live Demo](https://webreflection.github.io/element/)
```js
// https://cdn.jsdelivr.net/npm/@webreflection/element/index.min.js for best compression
import element from 'https://esm.run/@webreflection/element';
// direct node reference or `< css-selector` to enrich, ie:
// element(document.body, ...) or ...
element(
'< body',
{
// override body.style.cssText = ...
style: 'text-align: center',
// classList.add('some', 'container')
classList: ['some', 'container'],
// a custom listener as object.handleEvent pattern
['custom:event']: {
count: 0,
handleEvent({ type, currentTarget }) {
console.log(++this.count, type, currentTarget);
},
},
// listener with an extra { once: true } option
['@click']: [
({ type, currentTarget }) => {
console.log(type, currentTarget);
currentTarget.dispatchEvent(new Event('custom:event'))
},
{ once: true },
],
},
// body children / childNodes
element('h1', {
// clallName
class: 'name',
// textContent
text: '@webreflection/element',
style: 'color: purple',
// role="heading" aria-level="1"
aria: {
role: 'heading',
level: 1,
},
// dataset.test = 'ok'
data: {
test: 'ok',
},
// serialized as `json` attribute
json: {a: 1, b: 2},
// direct listener
onclick: ({ type, currentTarget }) => {
console.log(type, currentTarget);
},
}),
element(
'svg',
{
width: 100,
height: 100,
},
// svg children / childNodes
element('svg:circle', {
cx: 50,
cy: 50,
r: 50,
fill: 'violet',
})
),
element('p', {
// innerHTML
html: 'made with ❤️ for the Web',
})
);
```