@praxisjs/runtime 0.1.1 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. package/CHANGELOG.md +28 -0
  2. package/dist/children.d.ts +3 -0
  3. package/dist/children.d.ts.map +1 -0
  4. package/dist/children.js +24 -0
  5. package/dist/children.js.map +1 -0
  6. package/dist/component.d.ts +5 -0
  7. package/dist/component.d.ts.map +1 -0
  8. package/dist/component.js +42 -0
  9. package/dist/component.js.map +1 -0
  10. package/dist/context.d.ts +4 -0
  11. package/dist/context.d.ts.map +1 -0
  12. package/dist/context.js +18 -0
  13. package/dist/context.js.map +1 -0
  14. package/dist/dom/constants.d.ts +5 -0
  15. package/dist/dom/constants.d.ts.map +1 -0
  16. package/dist/dom/constants.js +61 -0
  17. package/dist/dom/constants.js.map +1 -0
  18. package/dist/dom/create.d.ts +2 -0
  19. package/dist/dom/create.d.ts.map +1 -0
  20. package/dist/dom/create.js +7 -0
  21. package/dist/dom/create.js.map +1 -0
  22. package/dist/dom/events.d.ts +3 -0
  23. package/dist/dom/events.d.ts.map +1 -0
  24. package/dist/dom/events.js +5 -0
  25. package/dist/dom/events.js.map +1 -0
  26. package/dist/dom/props.d.ts +3 -0
  27. package/dist/dom/props.d.ts.map +1 -0
  28. package/dist/dom/props.js +72 -0
  29. package/dist/dom/props.js.map +1 -0
  30. package/dist/element.d.ts +3 -0
  31. package/dist/element.d.ts.map +1 -0
  32. package/dist/element.js +16 -0
  33. package/dist/element.js.map +1 -0
  34. package/dist/index.d.ts +14 -1
  35. package/dist/index.d.ts.map +1 -1
  36. package/dist/index.js +28 -1
  37. package/dist/index.js.map +1 -1
  38. package/dist/reactive.d.ts +3 -0
  39. package/dist/reactive.d.ts.map +1 -0
  40. package/dist/reactive.js +35 -0
  41. package/dist/reactive.js.map +1 -0
  42. package/dist/scope.d.ts +10 -0
  43. package/dist/scope.d.ts.map +1 -0
  44. package/dist/scope.js +20 -0
  45. package/dist/scope.js.map +1 -0
  46. package/package.json +4 -5
  47. package/src/children.ts +33 -0
  48. package/src/component.ts +60 -0
  49. package/src/context.ts +22 -0
  50. package/src/dom/constants.ts +63 -0
  51. package/src/dom/create.ts +7 -0
  52. package/src/dom/events.ts +11 -0
  53. package/src/dom/props.ts +79 -0
  54. package/src/element.ts +24 -0
  55. package/src/index.ts +36 -1
  56. package/src/reactive.ts +45 -0
  57. package/src/scope.ts +25 -0
  58. package/dist/renderer.d.ts +0 -3
  59. package/dist/renderer.d.ts.map +0 -1
  60. package/dist/renderer.js +0 -380
  61. package/dist/renderer.js.map +0 -1
  62. package/src/renderer.ts +0 -473
package/CHANGELOG.md CHANGED
@@ -1,5 +1,33 @@
1
1
  # @praxisjs/runtime
2
2
 
3
+ ## 0.2.1
4
+
5
+ ### Patch Changes
6
+
7
+ - Updated dependencies [f52354d]
8
+ - @praxisjs/decorators@0.4.0
9
+ - @praxisjs/core@0.4.0
10
+
11
+ ## 0.2.0
12
+
13
+ ### Minor Changes
14
+
15
+ - bb0d4f8: **Refactor decorator system and component architecture across PraxisJS packages**
16
+
17
+ - Replaced legacy decorator signatures (`constructor`, `target`, `propertyKey`, method descriptor) with the standard TC39 decorator context API (`ClassDecoratorContext`, `ClassFieldDecoratorContext`, `ClassMethodDecoratorContext`) across `@praxisjs/decorators`, `@praxisjs/store`, `@praxisjs/concurrent`, `@praxisjs/router`, `@praxisjs/motion`, `@praxisjs/di`, and `@praxisjs/fsm`.
18
+ - Introduced `StatefulComponent` and `StatelessComponent` as the new base classes, replacing the deprecated `BaseComponent`/`Function Component` pattern, across `@praxisjs/core`, `@praxisjs/runtime`, `@praxisjs/devtools`, and templates.
19
+ - Implemented core rendering functionality in `@praxisjs/runtime` (`mountChildren`, `mountComponent`, reactive scope management) and removed the deprecated `renderer.ts`.
20
+ - Refactored `@praxisjs/jsx` to delegate rendering to `@praxisjs/runtime` and improved type safety with `flattenChildren` and `isComponent` utilities.
21
+ - Updated internal module structure with new `internal` exports in `package.json` files for shared utilities and types.
22
+ - Removed `experimentalDecorators`/`emitDecoratorMetadata` from `tsconfig.json` in favor of native decorator support.
23
+
24
+ ### Patch Changes
25
+
26
+ - Updated dependencies [bb0d4f8]
27
+ - @praxisjs/decorators@0.3.0
28
+ - @praxisjs/core@0.3.0
29
+ - @praxisjs/shared@0.2.0
30
+
3
31
  ## 0.1.1
4
32
 
5
33
  ### Patch Changes
@@ -0,0 +1,3 @@
1
+ import type { Scope } from "./scope";
2
+ export declare function mountChildren(parent: Node, children: unknown, scope: Scope): void;
3
+ //# sourceMappingURL=children.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"children.d.ts","sourceRoot":"","sources":["../src/children.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAErC,wBAAgB,aAAa,CAC3B,MAAM,EAAE,IAAI,EACZ,QAAQ,EAAE,OAAO,EACjB,KAAK,EAAE,KAAK,GACX,IAAI,CAwBN"}
@@ -0,0 +1,24 @@
1
+ import { mountReactive } from "./reactive";
2
+ export function mountChildren(parent, children, scope) {
3
+ if (children === null || children === undefined || children === false)
4
+ return;
5
+ if (typeof children === "string" || typeof children === "number") {
6
+ parent.appendChild(document.createTextNode(String(children)));
7
+ return;
8
+ }
9
+ if (typeof children === "function") {
10
+ mountReactive(parent, children, scope);
11
+ return;
12
+ }
13
+ if (children instanceof Node) {
14
+ parent.appendChild(children);
15
+ return;
16
+ }
17
+ if (Array.isArray(children)) {
18
+ for (const child of children) {
19
+ mountChildren(parent, child, scope);
20
+ }
21
+ return;
22
+ }
23
+ }
24
+ //# sourceMappingURL=children.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"children.js","sourceRoot":"","sources":["../src/children.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAI3C,MAAM,UAAU,aAAa,CAC3B,MAAY,EACZ,QAAiB,EACjB,KAAY;IAEZ,IAAI,QAAQ,KAAK,IAAI,IAAI,QAAQ,KAAK,SAAS,IAAI,QAAQ,KAAK,KAAK;QAAE,OAAO;IAE9E,IAAI,OAAO,QAAQ,KAAK,QAAQ,IAAI,OAAO,QAAQ,KAAK,QAAQ,EAAE,CAAC;QACjE,MAAM,CAAC,WAAW,CAAC,QAAQ,CAAC,cAAc,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;QAC9D,OAAO;IACT,CAAC;IAED,IAAI,OAAO,QAAQ,KAAK,UAAU,EAAE,CAAC;QACnC,aAAa,CAAC,MAAM,EAAE,QAAyB,EAAE,KAAK,CAAC,CAAC;QACxD,OAAO;IACT,CAAC;IAED,IAAI,QAAQ,YAAY,IAAI,EAAE,CAAC;QAC7B,MAAM,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC;QAC7B,OAAO;IACT,CAAC;IAED,IAAI,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAC;QAC5B,KAAK,MAAM,KAAK,IAAI,QAAQ,EAAE,CAAC;YAC7B,aAAa,CAAC,MAAM,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC;QACtC,CAAC;QACD,OAAO;IACT,CAAC;AACH,CAAC"}
@@ -0,0 +1,5 @@
1
+ import { isComponent, type ComponentConstructor } from "@praxisjs/shared/internal";
2
+ import type { Scope } from "./scope";
3
+ export declare function mountComponent(ctor: ComponentConstructor, props: Record<string, unknown>, parentScope: Scope): Node[];
4
+ export { isComponent };
5
+ //# sourceMappingURL=component.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"component.d.ts","sourceRoot":"","sources":["../src/component.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,KAAK,oBAAoB,EAAG,MAAM,2BAA2B,CAAC;AAKpF,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAErC,wBAAgB,cAAc,CAC5B,IAAI,EAAE,oBAAoB,EAC1B,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC9B,WAAW,EAAE,KAAK,GACjB,IAAI,EAAE,CA6CR;AAED,OAAO,EAAE,WAAW,EAAE,CAAC"}
@@ -0,0 +1,42 @@
1
+ import { initSlots } from "@praxisjs/decorators";
2
+ import { isComponent } from "@praxisjs/shared/internal";
3
+ import { mountChildren } from "./children";
4
+ import { runInScope } from "./context";
5
+ export function mountComponent(ctor, props, parentScope) {
6
+ const scope = parentScope.fork();
7
+ const instance = new ctor({ ...props });
8
+ const rawChildren = props.children;
9
+ if (rawChildren != null) {
10
+ initSlots(instance, rawChildren);
11
+ }
12
+ const start = document.createComment(`[${ctor.name}]`);
13
+ const end = document.createComment(`[/${ctor.name}]`);
14
+ // Expose anchor so decorators like @Virtual can find the parent element
15
+ instance._anchor = end;
16
+ instance.onBeforeMount?.();
17
+ const container = document.createDocumentFragment();
18
+ container.appendChild(start);
19
+ let dom = null;
20
+ runInScope(scope, () => {
21
+ try {
22
+ dom = instance.render();
23
+ }
24
+ catch (e) {
25
+ instance.onError?.(e instanceof Error ? e : new Error(String(e)));
26
+ }
27
+ });
28
+ mountChildren(container, dom, scope);
29
+ container.appendChild(end);
30
+ queueMicrotask(() => {
31
+ instance._mounted = true;
32
+ instance.onMount?.();
33
+ });
34
+ scope.add(() => {
35
+ instance.onUnmount?.();
36
+ instance._mounted = false;
37
+ });
38
+ // Return the nodes from the fragment as an array so the caller can append them
39
+ return Array.from(container.childNodes);
40
+ }
41
+ export { isComponent };
42
+ //# sourceMappingURL=component.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"component.js","sourceRoot":"","sources":["../src/component.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACjD,OAAO,EAAE,WAAW,EAA8B,MAAM,2BAA2B,CAAC;AAEpF,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAC3C,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAIvC,MAAM,UAAU,cAAc,CAC5B,IAA0B,EAC1B,KAA8B,EAC9B,WAAkB;IAElB,MAAM,KAAK,GAAG,WAAW,CAAC,IAAI,EAAE,CAAC;IAEjC,MAAM,QAAQ,GAAG,IAAI,IAAI,CAAC,EAAE,GAAG,KAAK,EAAE,CAAC,CAAC;IAExC,MAAM,WAAW,GAAG,KAAK,CAAC,QAAQ,CAAC;IACnC,IAAI,WAAW,IAAI,IAAI,EAAE,CAAC;QACxB,SAAS,CAAC,QAAQ,EAAE,WAAW,CAAC,CAAC;IACnC,CAAC;IAED,MAAM,KAAK,GAAG,QAAQ,CAAC,aAAa,CAAC,IAAI,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC;IACvD,MAAM,GAAG,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC;IAEtD,wEAAwE;IACxE,QAAQ,CAAC,OAAO,GAAG,GAAG,CAAC;IAEvB,QAAQ,CAAC,aAAa,EAAE,EAAE,CAAC;IAE3B,MAAM,SAAS,GAAG,QAAQ,CAAC,sBAAsB,EAAE,CAAC;IACpD,SAAS,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC;IAE7B,IAAI,GAAG,GAAyB,IAAI,CAAC;IACrC,UAAU,CAAC,KAAK,EAAE,GAAG,EAAE;QACrB,IAAI,CAAC;YACH,GAAG,GAAG,QAAQ,CAAC,MAAM,EAAE,CAAC;QAC1B,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC;YACX,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QACpE,CAAC;IACH,CAAC,CAAC,CAAC;IAEH,aAAa,CAAC,SAAS,EAAE,GAAG,EAAE,KAAK,CAAC,CAAC;IACrC,SAAS,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC;IAE3B,cAAc,CAAC,GAAG,EAAE;QAClB,QAAQ,CAAC,QAAQ,GAAG,IAAI,CAAC;QACzB,QAAQ,CAAC,OAAO,EAAE,EAAE,CAAC;IACvB,CAAC,CAAC,CAAC;IAEH,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE;QACb,QAAQ,CAAC,SAAS,EAAE,EAAE,CAAC;QACvB,QAAQ,CAAC,QAAQ,GAAG,KAAK,CAAC;IAC5B,CAAC,CAAC,CAAC;IAEH,+EAA+E;IAC/E,OAAO,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,UAAU,CAAC,CAAC;AAC1C,CAAC;AAED,OAAO,EAAE,WAAW,EAAE,CAAC"}
@@ -0,0 +1,4 @@
1
+ import type { Scope } from "./scope";
2
+ export declare function getCurrentScope(): Scope;
3
+ export declare function runInScope<T>(scope: Scope, fn: () => T): T;
4
+ //# sourceMappingURL=context.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAIrC,wBAAgB,eAAe,IAAI,KAAK,CAOvC;AAED,wBAAgB,UAAU,CAAC,CAAC,EAAE,KAAK,EAAE,KAAK,EAAE,EAAE,EAAE,MAAM,CAAC,GAAG,CAAC,CAQ1D"}
@@ -0,0 +1,18 @@
1
+ let _currentScope = null;
2
+ export function getCurrentScope() {
3
+ if (!_currentScope) {
4
+ throw new Error("[PraxisJS] jsx() called outside of a render context. Make sure to call render() with a factory function.");
5
+ }
6
+ return _currentScope;
7
+ }
8
+ export function runInScope(scope, fn) {
9
+ const prev = _currentScope;
10
+ _currentScope = scope;
11
+ try {
12
+ return fn();
13
+ }
14
+ finally {
15
+ _currentScope = prev;
16
+ }
17
+ }
18
+ //# sourceMappingURL=context.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.js","sourceRoot":"","sources":["../src/context.ts"],"names":[],"mappings":"AAEA,IAAI,aAAa,GAAiB,IAAI,CAAC;AAEvC,MAAM,UAAU,eAAe;IAC7B,IAAI,CAAC,aAAa,EAAE,CAAC;QACnB,MAAM,IAAI,KAAK,CACb,0GAA0G,CAC3G,CAAC;IACJ,CAAC;IACD,OAAO,aAAa,CAAC;AACvB,CAAC;AAED,MAAM,UAAU,UAAU,CAAI,KAAY,EAAE,EAAW;IACrD,MAAM,IAAI,GAAG,aAAa,CAAC;IAC3B,aAAa,GAAG,KAAK,CAAC;IACtB,IAAI,CAAC;QACH,OAAO,EAAE,EAAE,CAAC;IACd,CAAC;YAAS,CAAC;QACT,aAAa,GAAG,IAAI,CAAC;IACvB,CAAC;AACH,CAAC"}
@@ -0,0 +1,5 @@
1
+ export declare const SVG_NAMESPACE = "http://www.w3.org/2000/svg";
2
+ export declare const SVG_TAGS: Set<string>;
3
+ export declare const EVENT_MAP: Record<string, string>;
4
+ export declare const VALUE_PROPS: Set<string>;
5
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../src/dom/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,aAAa,+BAA+B,CAAC;AAE1D,eAAO,MAAM,QAAQ,aA2BnB,CAAC;AAEH,eAAO,MAAM,SAAS,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CA6B5C,CAAC;AAEF,eAAO,MAAM,WAAW,aAAwD,CAAC"}
@@ -0,0 +1,61 @@
1
+ export const SVG_NAMESPACE = "http://www.w3.org/2000/svg";
2
+ export const SVG_TAGS = new Set([
3
+ "svg",
4
+ "path",
5
+ "circle",
6
+ "rect",
7
+ "line",
8
+ "polyline",
9
+ "polygon",
10
+ "ellipse",
11
+ "text",
12
+ "g",
13
+ "defs",
14
+ "use",
15
+ "symbol",
16
+ "marker",
17
+ "clipPath",
18
+ "mask",
19
+ "pattern",
20
+ "image",
21
+ "linearGradient",
22
+ "radialGradient",
23
+ "stop",
24
+ "filter",
25
+ "feGaussianBlur",
26
+ "tspan",
27
+ "textPath",
28
+ "foreignObject",
29
+ ]);
30
+ export const EVENT_MAP = {
31
+ onClick: "click",
32
+ onDblClick: "dblclick",
33
+ onChange: "change",
34
+ onInput: "input",
35
+ onSubmit: "submit",
36
+ onReset: "reset",
37
+ onKeyDown: "keydown",
38
+ onKeyUp: "keyup",
39
+ onKeyPress: "keypress",
40
+ onFocus: "focus",
41
+ onBlur: "blur",
42
+ onMouseDown: "mousedown",
43
+ onMouseUp: "mouseup",
44
+ onMouseEnter: "mouseenter",
45
+ onMouseLeave: "mouseleave",
46
+ onMouseMove: "mousemove",
47
+ onContextMenu: "contextmenu",
48
+ onScroll: "scroll",
49
+ onWheel: "wheel",
50
+ onDragStart: "dragstart",
51
+ onDragEnd: "dragend",
52
+ onDragOver: "dragover",
53
+ onDrop: "drop",
54
+ onTouchStart: "touchstart",
55
+ onTouchEnd: "touchend",
56
+ onTouchMove: "touchmove",
57
+ onAnimationEnd: "animationend",
58
+ onTransitionEnd: "transitionend",
59
+ };
60
+ export const VALUE_PROPS = new Set(["checked", "value", "disabled", "selected"]);
61
+ //# sourceMappingURL=constants.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.js","sourceRoot":"","sources":["../../src/dom/constants.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,aAAa,GAAG,4BAA4B,CAAC;AAE1D,MAAM,CAAC,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC;IAC9B,KAAK;IACL,MAAM;IACN,QAAQ;IACR,MAAM;IACN,MAAM;IACN,UAAU;IACV,SAAS;IACT,SAAS;IACT,MAAM;IACN,GAAG;IACH,MAAM;IACN,KAAK;IACL,QAAQ;IACR,QAAQ;IACR,UAAU;IACV,MAAM;IACN,SAAS;IACT,OAAO;IACP,gBAAgB;IAChB,gBAAgB;IAChB,MAAM;IACN,QAAQ;IACR,gBAAgB;IAChB,OAAO;IACP,UAAU;IACV,eAAe;CAChB,CAAC,CAAC;AAEH,MAAM,CAAC,MAAM,SAAS,GAA2B;IAC/C,OAAO,EAAE,OAAO;IAChB,UAAU,EAAE,UAAU;IACtB,QAAQ,EAAE,QAAQ;IAClB,OAAO,EAAE,OAAO;IAChB,QAAQ,EAAE,QAAQ;IAClB,OAAO,EAAE,OAAO;IAChB,SAAS,EAAE,SAAS;IACpB,OAAO,EAAE,OAAO;IAChB,UAAU,EAAE,UAAU;IACtB,OAAO,EAAE,OAAO;IAChB,MAAM,EAAE,MAAM;IACd,WAAW,EAAE,WAAW;IACxB,SAAS,EAAE,SAAS;IACpB,YAAY,EAAE,YAAY;IAC1B,YAAY,EAAE,YAAY;IAC1B,WAAW,EAAE,WAAW;IACxB,aAAa,EAAE,aAAa;IAC5B,QAAQ,EAAE,QAAQ;IAClB,OAAO,EAAE,OAAO;IAChB,WAAW,EAAE,WAAW;IACxB,SAAS,EAAE,SAAS;IACpB,UAAU,EAAE,UAAU;IACtB,MAAM,EAAE,MAAM;IACd,YAAY,EAAE,YAAY;IAC1B,UAAU,EAAE,UAAU;IACtB,WAAW,EAAE,WAAW;IACxB,cAAc,EAAE,cAAc;IAC9B,eAAe,EAAE,eAAe;CACjC,CAAC;AAEF,MAAM,CAAC,MAAM,WAAW,GAAG,IAAI,GAAG,CAAC,CAAC,SAAS,EAAE,OAAO,EAAE,UAAU,EAAE,UAAU,CAAC,CAAC,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare function createElement(tag: string): HTMLElement | SVGElement;
2
+ //# sourceMappingURL=create.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create.d.ts","sourceRoot":"","sources":["../../src/dom/create.ts"],"names":[],"mappings":"AAEA,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,WAAW,GAAG,UAAU,CAInE"}
@@ -0,0 +1,7 @@
1
+ import { SVG_NAMESPACE, SVG_TAGS } from "./constants";
2
+ export function createElement(tag) {
3
+ return SVG_TAGS.has(tag)
4
+ ? (document.createElementNS(SVG_NAMESPACE, tag))
5
+ : document.createElement(tag);
6
+ }
7
+ //# sourceMappingURL=create.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create.js","sourceRoot":"","sources":["../../src/dom/create.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAEtD,MAAM,UAAU,aAAa,CAAC,GAAW;IACvC,OAAO,QAAQ,CAAC,GAAG,CAAC,GAAG,CAAC;QACtB,CAAC,CAAC,CAAC,QAAQ,CAAC,eAAe,CAAC,aAAa,EAAE,GAAG,CAAC,CAAC;QAChD,CAAC,CAAC,QAAQ,CAAC,aAAa,CAAC,GAAG,CAAC,CAAC;AAClC,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { Scope } from "../scope";
2
+ export declare function addEvent(el: Element, eventName: string, handler: EventListener, scope: Scope): void;
3
+ //# sourceMappingURL=events.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../../src/dom/events.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,UAAU,CAAC;AAEtC,wBAAgB,QAAQ,CACtB,EAAE,EAAE,OAAO,EACX,SAAS,EAAE,MAAM,EACjB,OAAO,EAAE,aAAa,EACtB,KAAK,EAAE,KAAK,GACX,IAAI,CAGN"}
@@ -0,0 +1,5 @@
1
+ export function addEvent(el, eventName, handler, scope) {
2
+ el.addEventListener(eventName, handler);
3
+ scope.add(() => { el.removeEventListener(eventName, handler); });
4
+ }
5
+ //# sourceMappingURL=events.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"events.js","sourceRoot":"","sources":["../../src/dom/events.ts"],"names":[],"mappings":"AAEA,MAAM,UAAU,QAAQ,CACtB,EAAW,EACX,SAAiB,EACjB,OAAsB,EACtB,KAAY;IAEZ,EAAE,CAAC,gBAAgB,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC;IACxC,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,CAAC,mBAAmB,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACnE,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { Scope } from "../scope";
2
+ export declare function applyProp(el: Element, key: string, value: unknown, scope: Scope): void;
3
+ //# sourceMappingURL=props.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"props.d.ts","sourceRoot":"","sources":["../../src/dom/props.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,UAAU,CAAC;AA+CtC,wBAAgB,SAAS,CACvB,EAAE,EAAE,OAAO,EACX,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,KAAK,EAAE,KAAK,GACX,IAAI,CAuBN"}
@@ -0,0 +1,72 @@
1
+ import { EVENT_MAP, VALUE_PROPS } from "./constants";
2
+ import { addEvent } from "./events";
3
+ function applyClass(el, value) {
4
+ if (value === null || value === undefined) {
5
+ el.removeAttribute("class");
6
+ }
7
+ else {
8
+ // eslint-disable-next-line @typescript-eslint/no-base-to-string
9
+ el.setAttribute("class", String(value));
10
+ }
11
+ }
12
+ function applyStyle(el, value) {
13
+ if (value === null || value === undefined) {
14
+ el.removeAttribute("style");
15
+ }
16
+ else if (typeof value === "object") {
17
+ const htmlEl = el;
18
+ htmlEl.removeAttribute("style");
19
+ Object.assign(htmlEl.style, value);
20
+ }
21
+ else {
22
+ // eslint-disable-next-line @typescript-eslint/no-base-to-string
23
+ el.setAttribute("style", String(value));
24
+ }
25
+ }
26
+ function applyAttr(el, key, value) {
27
+ if (value === false || value === null || value === undefined) {
28
+ el.removeAttribute(key);
29
+ }
30
+ else if (value === true) {
31
+ el.setAttribute(key, "");
32
+ }
33
+ else {
34
+ // eslint-disable-next-line @typescript-eslint/no-base-to-string
35
+ el.setAttribute(key, String(value));
36
+ }
37
+ }
38
+ function setProp(el, key, value) {
39
+ if (key === "class" || key === "className") {
40
+ applyClass(el, value);
41
+ }
42
+ else if (key === "style") {
43
+ applyStyle(el, value);
44
+ }
45
+ else if (VALUE_PROPS.has(key)) {
46
+ el[key] = value;
47
+ }
48
+ else {
49
+ applyAttr(el, key, value);
50
+ }
51
+ }
52
+ export function applyProp(el, key, value, scope) {
53
+ const normalizedKey = key === "htmlFor" ? "for" : key;
54
+ if (normalizedKey === "key" || normalizedKey === "children")
55
+ return;
56
+ if (normalizedKey === "ref") {
57
+ value(el);
58
+ return;
59
+ }
60
+ if (normalizedKey in EVENT_MAP) {
61
+ addEvent(el, EVENT_MAP[normalizedKey], value, scope);
62
+ return;
63
+ }
64
+ if (typeof value === "function") {
65
+ scope.effect(() => {
66
+ setProp(el, normalizedKey, value());
67
+ });
68
+ return;
69
+ }
70
+ setProp(el, normalizedKey, value);
71
+ }
72
+ //# sourceMappingURL=props.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"props.js","sourceRoot":"","sources":["../../src/dom/props.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AACrD,OAAO,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAC;AAIpC,SAAS,UAAU,CAAC,EAAW,EAAE,KAAc;IAC7C,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QAC1C,EAAE,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC;IAC9B,CAAC;SAAM,CAAC;QACN,gEAAgE;QAChE,EAAE,CAAC,YAAY,CAAC,OAAO,EAAE,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAC1C,CAAC;AACH,CAAC;AAED,SAAS,UAAU,CAAC,EAAW,EAAE,KAAc;IAC7C,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QAC1C,EAAE,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC;IAC9B,CAAC;SAAM,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QACrC,MAAM,MAAM,GAAG,EAAiB,CAAC;QACjC,MAAM,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC;QAChC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;IACrC,CAAC;SAAM,CAAC;QACN,gEAAgE;QAChE,EAAE,CAAC,YAAY,CAAC,OAAO,EAAE,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAC1C,CAAC;AACH,CAAC;AAED,SAAS,SAAS,CAAC,EAAW,EAAE,GAAW,EAAE,KAAc;IACzD,IAAI,KAAK,KAAK,KAAK,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;QAC7D,EAAE,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC;IAC1B,CAAC;SAAM,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;QAC1B,EAAE,CAAC,YAAY,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;IAC3B,CAAC;SAAM,CAAC;QACN,gEAAgE;QAChE,EAAE,CAAC,YAAY,CAAC,GAAG,EAAE,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IACtC,CAAC;AACH,CAAC;AAED,SAAS,OAAO,CAAC,EAAW,EAAE,GAAW,EAAE,KAAc;IACvD,IAAI,GAAG,KAAK,OAAO,IAAI,GAAG,KAAK,WAAW,EAAE,CAAC;QAC3C,UAAU,CAAC,EAAE,EAAE,KAAK,CAAC,CAAC;IACxB,CAAC;SAAM,IAAI,GAAG,KAAK,OAAO,EAAE,CAAC;QAC3B,UAAU,CAAC,EAAE,EAAE,KAAK,CAAC,CAAC;IACxB,CAAC;SAAM,IAAI,WAAW,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC;QAC/B,EAAyC,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC;IAC1D,CAAC;SAAM,CAAC;QACN,SAAS,CAAC,EAAE,EAAE,GAAG,EAAE,KAAK,CAAC,CAAC;IAC5B,CAAC;AACH,CAAC;AAED,MAAM,UAAU,SAAS,CACvB,EAAW,EACX,GAAW,EACX,KAAc,EACd,KAAY;IAEZ,MAAM,aAAa,GAAG,GAAG,KAAK,SAAS,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC;IAEtD,IAAI,aAAa,KAAK,KAAK,IAAI,aAAa,KAAK,UAAU;QAAE,OAAO;IAEpE,IAAI,aAAa,KAAK,KAAK,EAAE,CAAC;QAC3B,KAA+B,CAAC,EAAE,CAAC,CAAC;QACrC,OAAO;IACT,CAAC;IAED,IAAI,aAAa,IAAI,SAAS,EAAE,CAAC;QAC/B,QAAQ,CAAC,EAAE,EAAE,SAAS,CAAC,aAAa,CAAC,EAAE,KAAsB,EAAE,KAAK,CAAC,CAAC;QACtE,OAAO;IACT,CAAC;IAED,IAAI,OAAO,KAAK,KAAK,UAAU,EAAE,CAAC;QAChC,KAAK,CAAC,MAAM,CAAC,GAAG,EAAE;YAChB,OAAO,CAAC,EAAE,EAAE,aAAa,EAAG,KAAuB,EAAE,CAAC,CAAC;QACzD,CAAC,CAAC,CAAC;QACH,OAAO;IACT,CAAC;IAED,OAAO,CAAC,EAAE,EAAE,aAAa,EAAE,KAAK,CAAC,CAAC;AACpC,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { Scope } from "./scope";
2
+ export declare function mountElement(tag: string, props: Record<string, unknown>, scope: Scope): HTMLElement | SVGElement;
3
+ //# sourceMappingURL=element.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"element.d.ts","sourceRoot":"","sources":["../src/element.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAErC,wBAAgB,YAAY,CAC1B,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC9B,KAAK,EAAE,KAAK,GACX,WAAW,GAAG,UAAU,CAa1B"}
@@ -0,0 +1,16 @@
1
+ import { mountChildren } from "./children";
2
+ import { createElement } from "./dom/create";
3
+ import { applyProp } from "./dom/props";
4
+ export function mountElement(tag, props, scope) {
5
+ const el = createElement(tag);
6
+ for (const [key, val] of Object.entries(props)) {
7
+ if (key === "children")
8
+ continue;
9
+ applyProp(el, key, val, scope);
10
+ }
11
+ if (props.children !== undefined) {
12
+ mountChildren(el, props.children, scope);
13
+ }
14
+ return el;
15
+ }
16
+ //# sourceMappingURL=element.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"element.js","sourceRoot":"","sources":["../src/element.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAC3C,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAIxC,MAAM,UAAU,YAAY,CAC1B,GAAW,EACX,KAA8B,EAC9B,KAAY;IAEZ,MAAM,EAAE,GAAG,aAAa,CAAC,GAAG,CAAC,CAAC;IAE9B,KAAK,MAAM,CAAC,GAAG,EAAE,GAAG,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QAC/C,IAAI,GAAG,KAAK,UAAU;YAAE,SAAS;QACjC,SAAS,CAAC,EAAE,EAAE,GAAG,EAAE,GAAG,EAAE,KAAK,CAAC,CAAC;IACjC,CAAC;IAED,IAAI,KAAK,CAAC,QAAQ,KAAK,SAAS,EAAE,CAAC;QACjC,aAAa,CAAC,EAAE,EAAE,KAAK,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;IAC3C,CAAC;IAED,OAAO,EAAE,CAAC;AACZ,CAAC"}
package/dist/index.d.ts CHANGED
@@ -1,2 +1,15 @@
1
- export { render } from "./renderer";
1
+ /**
2
+ * Renders a component tree into a container element.
3
+ *
4
+ * The factory function is called once inside the root scope,
5
+ * so `jsx()` can access the current scope via `getCurrentScope()`.
6
+ *
7
+ * @example
8
+ * render(() => <App />, document.getElementById('app'));
9
+ */
10
+ export declare function render(factory: () => Node | Node[] | null, container: HTMLElement): () => void;
11
+ export { Scope } from "./scope";
12
+ export { runInScope, getCurrentScope } from "./context";
13
+ export { mountElement } from "./element";
14
+ export { mountComponent } from "./component";
2
15
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAIA;;;;;;;;GAQG;AACH,wBAAgB,MAAM,CACpB,OAAO,EAAE,MAAM,IAAI,GAAG,IAAI,EAAE,GAAG,IAAI,EACnC,SAAS,EAAE,WAAW,GACrB,MAAM,IAAI,CAcZ;AAED,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAChC,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC"}
package/dist/index.js CHANGED
@@ -1,2 +1,29 @@
1
- export { render } from "./renderer";
1
+ import { mountChildren } from "./children";
2
+ import { runInScope } from "./context";
3
+ import { Scope } from "./scope";
4
+ /**
5
+ * Renders a component tree into a container element.
6
+ *
7
+ * The factory function is called once inside the root scope,
8
+ * so `jsx()` can access the current scope via `getCurrentScope()`.
9
+ *
10
+ * @example
11
+ * render(() => <App />, document.getElementById('app'));
12
+ */
13
+ export function render(factory, container) {
14
+ const rootScope = new Scope();
15
+ container.innerHTML = "";
16
+ runInScope(rootScope, () => {
17
+ const result = factory();
18
+ mountChildren(container, result, rootScope);
19
+ });
20
+ return () => {
21
+ rootScope.dispose();
22
+ container.innerHTML = "";
23
+ };
24
+ }
25
+ export { Scope } from "./scope";
26
+ export { runInScope, getCurrentScope } from "./context";
27
+ export { mountElement } from "./element";
28
+ export { mountComponent } from "./component";
2
29
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAC3C,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AACvC,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAEhC;;;;;;;;GAQG;AACH,MAAM,UAAU,MAAM,CACpB,OAAmC,EACnC,SAAsB;IAEtB,MAAM,SAAS,GAAG,IAAI,KAAK,EAAE,CAAC;IAE9B,SAAS,CAAC,SAAS,GAAG,EAAE,CAAC;IAEzB,UAAU,CAAC,SAAS,EAAE,GAAG,EAAE;QACzB,MAAM,MAAM,GAAG,OAAO,EAAE,CAAC;QACzB,aAAa,CAAC,SAAS,EAAE,MAAM,EAAE,SAAS,CAAC,CAAC;IAC9C,CAAC,CAAC,CAAC;IAEH,OAAO,GAAG,EAAE;QACV,SAAS,CAAC,OAAO,EAAE,CAAC;QACpB,SAAS,CAAC,SAAS,GAAG,EAAE,CAAC;IAC3B,CAAC,CAAC;AACJ,CAAC;AAED,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAChC,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC"}
@@ -0,0 +1,3 @@
1
+ import type { Scope } from "./scope";
2
+ export declare function mountReactive(parent: Node, fn: () => unknown, parentScope: Scope): void;
3
+ //# sourceMappingURL=reactive.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reactive.d.ts","sourceRoot":"","sources":["../src/reactive.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAYrC,wBAAgB,aAAa,CAC3B,MAAM,EAAE,IAAI,EACZ,EAAE,EAAE,MAAM,OAAO,EACjB,WAAW,EAAE,KAAK,GACjB,IAAI,CA0BN"}
@@ -0,0 +1,35 @@
1
+ import { runInScope } from "./context";
2
+ function normalizeToNodes(value) {
3
+ if (value === null || value === undefined || value === false)
4
+ return [];
5
+ if (value instanceof Node)
6
+ return [value];
7
+ if (Array.isArray(value))
8
+ return value.flatMap(normalizeToNodes);
9
+ if (typeof value === "string" || typeof value === "number") {
10
+ return [document.createTextNode(String(value))];
11
+ }
12
+ return [];
13
+ }
14
+ export function mountReactive(parent, fn, parentScope) {
15
+ const end = document.createComment("reactive");
16
+ parent.appendChild(end);
17
+ let currentNodes = [];
18
+ let childScope = parentScope.fork();
19
+ parentScope.effect(() => {
20
+ childScope.dispose();
21
+ childScope = parentScope.fork();
22
+ for (const n of currentNodes) {
23
+ n.parentNode?.removeChild(n);
24
+ }
25
+ currentNodes = [];
26
+ const result = runInScope(childScope, fn);
27
+ const newNodes = normalizeToNodes(result);
28
+ for (const n of newNodes) {
29
+ parent.insertBefore(n, end);
30
+ }
31
+ currentNodes = newNodes;
32
+ });
33
+ parentScope.add(() => { childScope.dispose(); });
34
+ }
35
+ //# sourceMappingURL=reactive.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reactive.js","sourceRoot":"","sources":["../src/reactive.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAIvC,SAAS,gBAAgB,CAAC,KAAc;IACtC,IAAI,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,KAAK;QAAE,OAAO,EAAE,CAAC;IACxE,IAAI,KAAK,YAAY,IAAI;QAAE,OAAO,CAAC,KAAK,CAAC,CAAC;IAC1C,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC;QAAE,OAAO,KAAK,CAAC,OAAO,CAAC,gBAAgB,CAAC,CAAC;IACjE,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC3D,OAAO,CAAC,QAAQ,CAAC,cAAc,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;IAClD,CAAC;IACD,OAAO,EAAE,CAAC;AACZ,CAAC;AAED,MAAM,UAAU,aAAa,CAC3B,MAAY,EACZ,EAAiB,EACjB,WAAkB;IAElB,MAAM,GAAG,GAAG,QAAQ,CAAC,aAAa,CAAC,UAAU,CAAC,CAAC;IAC/C,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC;IAExB,IAAI,YAAY,GAAW,EAAE,CAAC;IAC9B,IAAI,UAAU,GAAG,WAAW,CAAC,IAAI,EAAE,CAAC;IAEpC,WAAW,CAAC,MAAM,CAAC,GAAG,EAAE;QACtB,UAAU,CAAC,OAAO,EAAE,CAAC;QACrB,UAAU,GAAG,WAAW,CAAC,IAAI,EAAE,CAAC;QAEhC,KAAK,MAAM,CAAC,IAAI,YAAY,EAAE,CAAC;YAC7B,CAAC,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC,CAAC,CAAC;QAC/B,CAAC;QACD,YAAY,GAAG,EAAE,CAAC;QAElB,MAAM,MAAM,GAAG,UAAU,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC;QAC1C,MAAM,QAAQ,GAAG,gBAAgB,CAAC,MAAM,CAAC,CAAC;QAE1C,KAAK,MAAM,CAAC,IAAI,QAAQ,EAAE,CAAC;YACzB,MAAM,CAAC,YAAY,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;QAC9B,CAAC;QACD,YAAY,GAAG,QAAQ,CAAC;IAC1B,CAAC,CAAC,CAAC;IAEH,WAAW,CAAC,GAAG,CAAC,GAAG,EAAE,GAAG,UAAU,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;AACnD,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { effect as coreEffect } from "@praxisjs/core/internal";
2
+ import type { Cleanup } from "@praxisjs/shared/internal";
3
+ export declare class Scope {
4
+ #private;
5
+ effect(fn: Parameters<typeof coreEffect>[0]): void;
6
+ add(cleanup: Cleanup): void;
7
+ fork(): Scope;
8
+ dispose(): void;
9
+ }
10
+ //# sourceMappingURL=scope.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scope.d.ts","sourceRoot":"","sources":["../src/scope.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAC/D,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,2BAA2B,CAAC;AAEzD,qBAAa,KAAK;;IAGhB,MAAM,CAAC,EAAE,EAAE,UAAU,CAAC,OAAO,UAAU,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI;IAIlD,GAAG,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI;IAI3B,IAAI,IAAI,KAAK;IAMb,OAAO,IAAI,IAAI;CAIhB"}
package/dist/scope.js ADDED
@@ -0,0 +1,20 @@
1
+ import { effect as coreEffect } from "@praxisjs/core/internal";
2
+ export class Scope {
3
+ #cleanups = [];
4
+ effect(fn) {
5
+ this.#cleanups.push(coreEffect(fn));
6
+ }
7
+ add(cleanup) {
8
+ this.#cleanups.push(cleanup);
9
+ }
10
+ fork() {
11
+ const child = new Scope();
12
+ this.#cleanups.push(() => { child.dispose(); });
13
+ return child;
14
+ }
15
+ dispose() {
16
+ this.#cleanups.forEach((fn) => { fn(); });
17
+ this.#cleanups = [];
18
+ }
19
+ }
20
+ //# sourceMappingURL=scope.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scope.js","sourceRoot":"","sources":["../src/scope.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAG/D,MAAM,OAAO,KAAK;IAChB,SAAS,GAAc,EAAE,CAAC;IAE1B,MAAM,CAAC,EAAoC;QACzC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC,CAAC;IACtC,CAAC;IAED,GAAG,CAAC,OAAgB;QAClB,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IAC/B,CAAC;IAED,IAAI;QACF,MAAM,KAAK,GAAG,IAAI,KAAK,EAAE,CAAC;QAC1B,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAChD,OAAO,KAAK,CAAC;IACf,CAAC;IAED,OAAO;QACL,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,EAAE,EAAE,EAAE,GAAG,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC1C,IAAI,CAAC,SAAS,GAAG,EAAE,CAAC;IACtB,CAAC;CACF"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@praxisjs/runtime",
3
- "version": "0.1.1",
3
+ "version": "0.2.1",
4
4
  "type": "module",
5
5
  "main": "./dist/index.js",
6
6
  "types": "./dist/index.d.ts",
@@ -14,10 +14,9 @@
14
14
  "typescript": "^5.9.3"
15
15
  },
16
16
  "dependencies": {
17
- "@praxisjs/core": "0.2.0",
18
- "@praxisjs/decorators": "0.2.0",
19
- "@praxisjs/jsx": "0.1.0",
20
- "@praxisjs/shared": "0.1.0"
17
+ "@praxisjs/shared": "0.2.0",
18
+ "@praxisjs/decorators": "0.4.0",
19
+ "@praxisjs/core": "0.4.0"
21
20
  },
22
21
  "scripts": {
23
22
  "build": "tsc",
@@ -0,0 +1,33 @@
1
+ import { mountReactive } from "./reactive";
2
+
3
+ import type { Scope } from "./scope";
4
+
5
+ export function mountChildren(
6
+ parent: Node,
7
+ children: unknown,
8
+ scope: Scope,
9
+ ): void {
10
+ if (children === null || children === undefined || children === false) return;
11
+
12
+ if (typeof children === "string" || typeof children === "number") {
13
+ parent.appendChild(document.createTextNode(String(children)));
14
+ return;
15
+ }
16
+
17
+ if (typeof children === "function") {
18
+ mountReactive(parent, children as () => unknown, scope);
19
+ return;
20
+ }
21
+
22
+ if (children instanceof Node) {
23
+ parent.appendChild(children);
24
+ return;
25
+ }
26
+
27
+ if (Array.isArray(children)) {
28
+ for (const child of children) {
29
+ mountChildren(parent, child, scope);
30
+ }
31
+ return;
32
+ }
33
+ }