typed-dom
Advanced tools
Comparing version 0.0.259 to 0.0.260
@@ -1,2 +0,2 @@ | ||
/*! typed-dom v0.0.259 https://github.com/falsandtru/typed-dom | (c) 2016, falsandtru | (Apache-2.0 AND MPL-2.0) License */ | ||
/*! typed-dom v0.0.260 https://github.com/falsandtru/typed-dom | (c) 2016, falsandtru | (Apache-2.0 AND MPL-2.0) License */ | ||
require = function () { | ||
@@ -720,3 +720,2 @@ function r(e, n, t) { | ||
const identity_1 = _dereq_('./util/identity'); | ||
const tag = Symbol.for('typed-dom::tag'); | ||
const proxy = Symbol.for('typed-dom::proxy'); | ||
@@ -742,8 +741,7 @@ var privates; | ||
constructor(element, attrs, children, container = element) { | ||
var _f, _g, _h; | ||
this.element = element; | ||
this[_a] = { | ||
mutate: false, | ||
connect: false, | ||
disconnect: false, | ||
mutate: false | ||
disconnect: false | ||
}; | ||
@@ -755,5 +753,5 @@ this[_b] = ''; | ||
const events = this[privates.events]; | ||
events.connect = ((_f = attrs === null || attrs === void 0 ? void 0 : attrs['onconnect']) !== null && _f !== void 0 ? _f : void 0) !== void 0; | ||
events.disconnect = ((_g = attrs === null || attrs === void 0 ? void 0 : attrs['ondisconnect']) !== null && _g !== void 0 ? _g : void 0) !== void 0; | ||
events.mutate = ((_h = attrs === null || attrs === void 0 ? void 0 : attrs['onmutate']) !== null && _h !== void 0 ? _h : void 0) !== void 0; | ||
events.mutate = (attrs === null || attrs === void 0 ? void 0 : attrs['onmutate']) != null; | ||
events.connect = (attrs === null || attrs === void 0 ? void 0 : attrs['onconnect']) != null; | ||
events.disconnect = (attrs === null || attrs === void 0 ? void 0 : attrs['ondisconnect']) != null; | ||
this[privates.children] = children; | ||
@@ -760,0 +758,0 @@ this[privates.container] = container; |
{ | ||
"name": "typed-dom", | ||
"version": "0.0.259", | ||
"description": "A DOM component builder creating type-level DOM structures.", | ||
"version": "0.0.260", | ||
"description": "A value-level and type-level DOM builder.", | ||
"private": false, | ||
@@ -6,0 +6,0 @@ "homepage": "https://github.com/falsandtru/typed-dom", |
@@ -5,6 +5,14 @@ # typed-dom | ||
A DOM component builder creating type-level DOM structures. | ||
A value-level and type-level DOM builder. | ||
**Visualize** DOM structures and **Assist** DOM access by static types. | ||
**Visualize** DOM structures and **Assist** DOM access using static types. | ||
```ts | ||
const dom: El<"article", HTMLElement, { | ||
style: El<"style", HTMLStyleElement, string>; | ||
title: El<"h1", HTMLHeadingElement, string>; | ||
content: El<"ul", HTMLUListElement, readonly El<"li", HTMLLIElement, string>[]>; | ||
}> | ||
``` | ||
## APIs | ||
@@ -47,3 +55,3 @@ | ||
Create an element proxy appending the children to the own open shadow DOM. | ||
Create an HTML element proxy assigning the children to the own open shadow DOM. | ||
@@ -159,3 +167,3 @@ - attrs: Record<string, string | EventListener | null | undefined> | ||
const component = HTML.article({ | ||
const dom = HTML.article({ | ||
style: HTML.style(`$scope { color: red; }`), | ||
@@ -173,3 +181,3 @@ title: HTML.h1(`Title`), | ||
```ts | ||
const component: El<"article", HTMLElement, { | ||
const dom: El<"article", HTMLElement, { | ||
style: El<"style", HTMLStyleElement, string>; | ||
@@ -186,2 +194,3 @@ title: El<"h1", HTMLHeadingElement, string>; | ||
> { | ||
readonly tag?: string; | ||
readonly element: E; | ||
@@ -217,26 +226,26 @@ get children(): El.Getter<C>; | ||
// Inspect | ||
component.element.outerHTML; // '<article class="RANDOM"><style>.RANDOM { color: red; }</style><h1>Title</h1><ul><li>item</li><li>item</li></ul></article>' | ||
component.children.title.element.outerHTML; // '<h1>Title</h1>' | ||
component.children.title.children; // 'Title' | ||
component.children.content.element.outerHTML; // '<ul><li>item</li><li>item</li></ul>' | ||
component.children.content.children[0].children; // 'item' | ||
dom.element.outerHTML; // '<article class="RANDOM"><style>.RANDOM { color: red; }</style><h1>Title</h1><ul><li>item</li><li>item</li></ul></article>' | ||
dom.children.title.element.outerHTML; // '<h1>Title</h1>' | ||
dom.children.title.children; // 'Title' | ||
dom.children.content.element.outerHTML; // '<ul><li>item</li><li>item</li></ul>' | ||
dom.children.content.children[0].children; // 'item' | ||
// Update | ||
// - Text | ||
component.children.title.children = 'Text'; | ||
component.children.title.element.outerHTML; // '<h1>Text</h1>' | ||
dom.children.title.children = 'Text'; | ||
dom.children.title.element.outerHTML; // '<h1>Text</h1>' | ||
// - Array | ||
component.children.content.children = [ | ||
dom.children.content.children = [ | ||
HTML.li('Array'), | ||
]; | ||
component.children.content.element.outerHTML; // '<ul><li>Array</li></ul>' | ||
dom.children.content.element.outerHTML; // '<ul><li>Array</li></ul>' | ||
// - Struct | ||
component.children = { | ||
dom.children = { | ||
title: HTML.h1('Struct'), | ||
}; | ||
component.children.title.element.outerHTML; // '<h1>Struct</h1>' | ||
component.children.title = HTML.h1('title'); | ||
component.children.title.element.outerHTML; // '<h1>title</h1>' | ||
dom.children.title.element.outerHTML; // '<h1>Struct</h1>' | ||
dom.children.title = HTML.h1('title'); | ||
dom.children.title.element.outerHTML; // '<h1>title</h1>' | ||
``` | ||
@@ -260,2 +269,3 @@ | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -277,2 +287,3 @@ public get children() { | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -309,2 +320,3 @@ public get children() { | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -311,0 +323,0 @@ public get children() { |
@@ -27,10 +27,10 @@ import { Symbol } from 'spica/global'; | ||
interface BuilderFunction<M extends TagNameMap, F extends Factory<M>> { | ||
<T extends K<M>, C extends El.Children.Void >(tag: T, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Void>; | ||
<T extends K<M>, C extends El.Children.Void >(tag: T, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children>; | ||
<T extends K<M>, C extends Empty >(tag: T, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Array>; | ||
<T extends K<M>, C extends El.Children.Text >(tag: T, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, string>; | ||
<T extends K<M>, C extends El.Children.Text >(tag: T, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Text>; | ||
<T extends K<M>, C extends El.Children.Array >(tag: T, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, Readonly<C>>; | ||
<T extends K<M>, C extends El.Children.Struct>(tag: T, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, C>; | ||
<T extends K<M>, C extends El.Children.Void >(tag: T, attrs?: Attrs, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Void>; | ||
<T extends K<M>, C extends El.Children.Void >(tag: T, attrs?: Attrs, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children>; | ||
<T extends K<M>, C extends Empty >(tag: T, attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Array>; | ||
<T extends K<M>, C extends El.Children.Text >(tag: T, attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, string>; | ||
<T extends K<M>, C extends El.Children.Text >(tag: T, attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, El.Children.Text>; | ||
<T extends K<M>, C extends El.Children.Array >(tag: T, attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, Readonly<C>>; | ||
@@ -41,10 +41,10 @@ <T extends K<M>, C extends El.Children.Struct>(tag: T, attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E<M[T]>>): El<T, E<M[T]>, C>; | ||
interface BuilderMethod<M extends TagNameMap, F extends Factory<M>, T extends K<M>, E extends Element> { | ||
<C extends El.Children.Void >( factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Void>; | ||
<C extends El.Children.Void >( factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children>; | ||
<C extends Empty >( children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Array>; | ||
<C extends El.Children.Text >( children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, string>; | ||
<C extends El.Children.Text >( children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Text>; | ||
<C extends El.Children.Array >( children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, Readonly<C>>; | ||
<C extends El.Children.Struct>( children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, C>; | ||
<C extends El.Children.Void >( attrs?: Attrs, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Void>; | ||
<C extends El.Children.Void >( attrs?: Attrs, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children>; | ||
<C extends Empty >( attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Array>; | ||
<C extends El.Children.Text >( attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, string>; | ||
<C extends El.Children.Text >( attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, El.Children.Text>; | ||
<C extends El.Children.Array >( attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, Readonly<C>>; | ||
@@ -51,0 +51,0 @@ <C extends El.Children.Struct>( attrs?: Attrs, children?: C, factory?: ElFactory<M, F, T, C, E> ): El<T, E, C>; |
@@ -6,3 +6,2 @@ import { Event } from 'spica/global'; | ||
const tag = Symbol.for('typed-dom::tag'); | ||
const proxy = Symbol.for('typed-dom::proxy'); | ||
@@ -15,3 +14,3 @@ | ||
> { | ||
readonly [tag]?: T; | ||
readonly tag?: T; | ||
readonly element: E; | ||
@@ -78,5 +77,5 @@ //get children(): C; | ||
const events = this[privates.events]; | ||
events.connect = (attrs?.['onconnect'] ?? void 0) !== void 0; | ||
events.disconnect = (attrs?.['ondisconnect'] ?? void 0) !== void 0; | ||
events.mutate = (attrs?.['onmutate'] ?? void 0) !== void 0; | ||
events.mutate = attrs?.['onmutate'] != null; | ||
events.connect = attrs?.['onconnect'] != null; | ||
events.disconnect = attrs?.['ondisconnect'] != null; | ||
this[privates.children] = children; | ||
@@ -124,7 +123,7 @@ this[privates.container] = container; | ||
} | ||
public readonly [tag]: T; | ||
public readonly tag?: T; | ||
private readonly [privates.events] = { | ||
mutate: false, | ||
connect: false, | ||
disconnect: false, | ||
mutate: false, | ||
}; | ||
@@ -131,0 +130,0 @@ private [privates.id_] = ''; |
@@ -125,8 +125,9 @@ import { API, Shadow, HTML, SVG, El, shadow, html } from '../..'; | ||
] as const); | ||
//assert.throws(() => dom.children[0] = dom.children[0]); | ||
//assert.throws(() => dom.children[0] = HTML.li()); | ||
//assert.throws(() => dom.children.push(HTML.li())); | ||
//assert.throws(() => dom.children.pop()); | ||
//assert.throws(() => dom.children.length = 0); | ||
// @ts-expect-error | ||
() => dom.children[0] = dom.children[0]; | ||
//() => dom.children[0] = HTML.li(); | ||
//() => dom.children.push(HTML.li()); | ||
//() => dom.children.pop(); | ||
//() => dom.children.length = 0; | ||
// @ts-expect-error | ||
() => dom.children = [undefined]; | ||
@@ -353,6 +354,6 @@ assert(dom.children.length === 1); | ||
it('swap', function () { | ||
const el = HTML.article([HTML.p()]); | ||
const children = el.children; | ||
const dom = HTML.article([HTML.p()]); | ||
const children = dom.children; | ||
assert.throws(() => HTML.article(children)); | ||
el.children = [HTML.p()]; | ||
dom.children = [HTML.p()]; | ||
assert(HTML.article(children)); | ||
@@ -362,3 +363,3 @@ }); | ||
it('observe text', function () { | ||
const el = HTML.span( | ||
const dom = HTML.span( | ||
{ | ||
@@ -369,9 +370,9 @@ onmutate: (ev, el = ev.target as HTMLElement) => | ||
'a'); | ||
assert(el.children === 'aa'); | ||
el.children = 'b'; | ||
assert(el.children === 'bb'); | ||
assert(dom.children === 'aa'); | ||
dom.children = 'b'; | ||
assert(dom.children === 'bb'); | ||
}); | ||
it('observe collection', function () { | ||
const listeners: Record<string, EventListener> = { | ||
const attrs: Attrs = { | ||
onconnect: (ev, el = ev.target as HTMLElement) => | ||
@@ -382,8 +383,8 @@ el.textContent += el.textContent!.toUpperCase(), | ||
}; | ||
const el = HTML.ul([ | ||
HTML.li(listeners, 'a'), | ||
HTML.li(listeners, 'b'), | ||
const dom = HTML.ul([ | ||
HTML.li(attrs, 'a'), | ||
HTML.li(attrs, 'b'), | ||
]); | ||
assert.deepStrictEqual( | ||
el.children.map(el => el.children), | ||
dom.children.map(child => child.children), | ||
[ | ||
@@ -393,8 +394,8 @@ 'aA', | ||
]); | ||
el.children = [ | ||
el.children[1], | ||
HTML.li(listeners, 'c'), | ||
dom.children = [ | ||
dom.children[1], | ||
HTML.li(attrs, 'c'), | ||
]; | ||
assert.deepStrictEqual( | ||
el.children.map(el => el.children), | ||
dom.children.map(child => child.children), | ||
[ | ||
@@ -405,8 +406,8 @@ 'bB', | ||
assert.deepStrictEqual( | ||
el.children.map(v => v.element), | ||
[...el.element.children]); | ||
dom.children.map(v => v.element), | ||
[...dom.element.children]); | ||
}); | ||
it('observe record', function () { | ||
const listeners: Record<string, EventListener> = { | ||
const attrs: Attrs = { | ||
onconnect: (ev, el = ev.target as HTMLElement) => | ||
@@ -417,11 +418,11 @@ el.textContent += el.textContent![0].toUpperCase(), | ||
}; | ||
const el = HTML.ul({ | ||
a: HTML.li(listeners, 'a'), | ||
b: HTML.li(listeners, 'b'), | ||
c: HTML.li(listeners, 'c'), | ||
d: HTML.li(listeners, 'd'), | ||
e: HTML.li(listeners, 'e'), | ||
const dom = HTML.ul({ | ||
a: HTML.li(attrs, 'a'), | ||
b: HTML.li(attrs, 'b'), | ||
c: HTML.li(attrs, 'c'), | ||
d: HTML.li(attrs, 'd'), | ||
e: HTML.li(attrs, 'e'), | ||
}); | ||
assert.deepStrictEqual( | ||
Object.entries(el.children).map(([k, v]) => [k, v.children]), | ||
Object.entries(dom.children).map(([k, v]) => [k, v.children]), | ||
[ | ||
@@ -434,12 +435,12 @@ ['a', 'aA'], | ||
]); | ||
el.children = { | ||
a: el.children.a, | ||
b: el.children.c, | ||
c: el.children.b, | ||
d: HTML.li(listeners, 'f'), | ||
e: el.children.e, | ||
dom.children = { | ||
a: dom.children.a, | ||
b: dom.children.c, | ||
c: dom.children.b, | ||
d: HTML.li(attrs, 'f'), | ||
e: dom.children.e, | ||
}; | ||
el.children.e = HTML.li(listeners, 'g'); | ||
dom.children.e = HTML.li(attrs, 'g'); | ||
assert.deepStrictEqual( | ||
Object.entries(el.children).map(([k, v]) => [k, v.children]), | ||
Object.entries(dom.children).map(([k, v]) => [k, v.children]), | ||
[ | ||
@@ -453,4 +454,4 @@ ['a', 'aA'], | ||
assert.deepStrictEqual( | ||
[...Object.values(el.children)].map(v => v.element), | ||
[...el.element.children]); | ||
[...Object.values(dom.children)].map(v => v.element), | ||
[...dom.element.children]); | ||
}); | ||
@@ -469,8 +470,8 @@ | ||
assert(Shadow.section([HTML.p()], (h, t) => shadow(h(t), { mode: 'closed' }).host as HTMLElement).children[0].element.outerHTML === '<p></p>'); | ||
const el = HTML.div([Shadow.section([HTML.p('a')])]); | ||
assert(el.element.outerHTML === '<div><section></section></div>'); | ||
assert(el.children[0].children[0].element.outerHTML === '<p>a</p>'); | ||
el.children[0].children[0].children = 'b'; | ||
assert(el.element.outerHTML === '<div><section></section></div>'); | ||
assert(el.element.firstElementChild!.shadowRoot!.innerHTML === '<p>b</p>'); | ||
const dom = HTML.div([Shadow.section([HTML.p('a')])]); | ||
assert(dom.element.outerHTML === '<div><section></section></div>'); | ||
assert(dom.children[0].children[0].element.outerHTML === '<p>a</p>'); | ||
dom.children[0].children[0].children = 'b'; | ||
assert(dom.element.outerHTML === '<div><section></section></div>'); | ||
assert(dom.element.firstElementChild!.shadowRoot!.innerHTML === '<p>b</p>'); | ||
}); | ||
@@ -489,2 +490,3 @@ | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -499,9 +501,13 @@ public get children() { | ||
const comp = new Component(); | ||
assert(comp.children[0].children === 'item'); | ||
comp.children = [ | ||
(): El => new Component(); | ||
(empty = HTML.section()): typeof empty => new Component(); | ||
// @ts-expect-error | ||
(): El<''> => new Component(); | ||
const dom = new Component(); | ||
assert(dom.children[0].children === 'item'); | ||
dom.children = [ | ||
HTML.li('Item') | ||
]; | ||
assert(comp.children[0].children === 'Item'); | ||
assert(HTML.div([comp])); | ||
assert(dom.children[0].children === 'Item'); | ||
assert(HTML.div([dom])); | ||
}); | ||
@@ -517,2 +523,3 @@ | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -527,9 +534,9 @@ public get children() { | ||
const comp = new Component(); | ||
assert(comp.children[0].children === 'item'); | ||
comp.children = [ | ||
const dom = new Component(); | ||
assert(dom.children[0].children === 'item'); | ||
dom.children = [ | ||
HTML.li('Item') | ||
]; | ||
assert(comp.children[0].children === 'Item'); | ||
assert(HTML.div([comp])); | ||
assert(dom.children[0].children === 'Item'); | ||
assert(HTML.div([dom])); | ||
}); | ||
@@ -543,5 +550,5 @@ | ||
assert(this.children); | ||
this.children = this.children.map(el => { | ||
el.children = el.children.toUpperCase(); | ||
return el; | ||
this.children = this.children.map(child => { | ||
child.children = child.children.toUpperCase(); | ||
return child; | ||
}); | ||
@@ -560,2 +567,3 @@ while (true) { | ||
}); | ||
public readonly tag: typeof this.dom.tag; | ||
public readonly element = this.dom.element; | ||
@@ -570,9 +578,9 @@ public get children() { | ||
const comp = new Component(); | ||
assert(comp.children[0].children === 'ITEM'); | ||
comp.children = [ | ||
const dom = new Component(); | ||
assert(dom.children[0].children === 'ITEM'); | ||
dom.children = [ | ||
HTML.li('item') | ||
]; | ||
assert(comp.children[0].children === 'item'); | ||
assert(HTML.div([comp])); | ||
assert(dom.children[0].children === 'item'); | ||
assert(HTML.div([dom])); | ||
}); | ||
@@ -579,0 +587,0 @@ |
Sorry, the diff of this file is too big to display
660637
15630
368