@bromscandium/runtime 1.0.0

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.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 bromscandium
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,91 @@
1
+ # @bromscandium/runtime
2
+
3
+ JSX runtime, virtual DOM renderer, and hooks for BromiumJS.
4
+
5
+ ## Installation
6
+
7
+ ```bash
8
+ npm install @bromscandium/runtime
9
+ ```
10
+
11
+ ## Usage
12
+
13
+ ```tsx
14
+ import { createApp, h, Fragment } from '@bromscandium/runtime';
15
+ import { ref } from '@bromscandium/core';
16
+
17
+ function Counter() {
18
+ const count = ref(0);
19
+
20
+ return h('div', null,
21
+ h('p', null, `Count: ${count.value}`),
22
+ h('button', { onClick: () => count.value++ }, 'Increment')
23
+ );
24
+ }
25
+
26
+ createApp(Counter).mount('#app');
27
+ ```
28
+
29
+ ### With JSX
30
+
31
+ Configure your bundler to use `@bromscandium/runtime` as the JSX import source:
32
+
33
+ ```json
34
+ {
35
+ "compilerOptions": {
36
+ "jsx": "react-jsx",
37
+ "jsxImportSource": "@bromscandium/runtime"
38
+ }
39
+ }
40
+ ```
41
+
42
+ ```tsx
43
+ function Counter() {
44
+ const count = ref(0);
45
+
46
+ return (
47
+ <div>
48
+ <p>Count: {count.value}</p>
49
+ <button onClick={() => count.value++}>Increment</button>
50
+ </div>
51
+ );
52
+ }
53
+ ```
54
+
55
+ ### Hooks
56
+
57
+ ```tsx
58
+ import { useState, useRef, useMemo, useCallback, onMounted, onUnmounted } from '@bromscandium/runtime';
59
+
60
+ function Component() {
61
+ const count = useState(0);
62
+ const inputRef = useRef<HTMLInputElement>(null);
63
+ const doubled = useMemo(() => count.value * 2, [count.value]);
64
+
65
+ onMounted(() => console.log('Mounted'));
66
+ onUnmounted(() => console.log('Unmounted'));
67
+
68
+ return <div>{doubled}</div>;
69
+ }
70
+ ```
71
+
72
+ ## API
73
+
74
+ | Export | Description |
75
+ |--------|-------------|
76
+ | `createApp(component)` | Create application instance |
77
+ | `render(vnode, container)` | Render VNode to DOM |
78
+ | `h(type, props, children)` | Create VNode (hyperscript) |
79
+ | `jsx`, `jsxs`, `jsxDEV` | JSX runtime functions |
80
+ | `Fragment` | Fragment component |
81
+ | `useState(initial)` | State hook (returns Ref) |
82
+ | `useRef(initial)` | Mutable ref hook |
83
+ | `useMemo(factory, deps)` | Memoized value hook |
84
+ | `useCallback(fn, deps)` | Memoized callback hook |
85
+ | `onMounted(callback)` | Mount lifecycle hook |
86
+ | `onUpdated(callback)` | Update lifecycle hook |
87
+ | `onUnmounted(callback)` | Unmount lifecycle hook |
88
+
89
+ ## License
90
+
91
+ MIT
@@ -0,0 +1,99 @@
1
+ /**
2
+ * React-style hooks for state persistence across re-renders.
3
+ * @module
4
+ */
5
+ import { Ref } from '@bromscandium/core';
6
+ /**
7
+ * Creates a reactive state variable that persists across component re-renders.
8
+ * Similar to React's useState but returns a Ref for reactivity integration.
9
+ *
10
+ * @param initialValue - The initial value, or a function that returns the initial value
11
+ * @returns A reactive ref containing the state value
12
+ *
13
+ * @example
14
+ * ```ts
15
+ * function Counter() {
16
+ * const count = useState(0);
17
+ *
18
+ * return (
19
+ * <button onClick={() => count.value++}>
20
+ * Count: {count.value}
21
+ * </button>
22
+ * );
23
+ * }
24
+ *
25
+ * // With lazy initialization
26
+ * const expensive = useState(() => computeExpensiveValue());
27
+ * ```
28
+ */
29
+ export declare function useState<T>(initialValue: T | (() => T)): Ref<T>;
30
+ /**
31
+ * Creates a mutable ref object that persists across re-renders without triggering updates.
32
+ * Useful for storing DOM references or mutable values that don't affect rendering.
33
+ *
34
+ * @param initialValue - The initial value for the ref
35
+ * @returns An object with a `current` property containing the value
36
+ *
37
+ * @example
38
+ * ```ts
39
+ * function TextInput() {
40
+ * const inputRef = useRef<HTMLInputElement>(null);
41
+ *
42
+ * onMounted(() => {
43
+ * inputRef.current?.focus();
44
+ * });
45
+ *
46
+ * return <input ref={inputRef} />;
47
+ * }
48
+ *
49
+ * // Storing mutable values
50
+ * const renderCount = useRef(0);
51
+ * renderCount.current++; // Doesn't trigger re-render
52
+ * ```
53
+ */
54
+ export declare function useRef<T>(initialValue: T): {
55
+ current: T;
56
+ };
57
+ /**
58
+ * Memoizes an expensive computation, recalculating only when dependencies change.
59
+ *
60
+ * @param factory - A function that computes and returns the memoized value
61
+ * @param deps - An array of dependencies that trigger recalculation when changed
62
+ * @returns The memoized value
63
+ *
64
+ * @example
65
+ * ```ts
66
+ * function FilteredList({ items, filter }) {
67
+ * const filtered = useMemo(
68
+ * () => items.filter(item => item.includes(filter)),
69
+ * [items, filter]
70
+ * );
71
+ *
72
+ * return <ul>{filtered.map(item => <li>{item}</li>)}</ul>;
73
+ * }
74
+ * ```
75
+ */
76
+ export declare function useMemo<T>(factory: () => T, deps: any[]): T;
77
+ /**
78
+ * Memoizes a callback function, returning the same reference until dependencies change.
79
+ * Useful for passing stable callbacks to child components to prevent unnecessary re-renders.
80
+ *
81
+ * @param callback - The callback function to memoize
82
+ * @param deps - An array of dependencies that trigger creating a new callback when changed
83
+ * @returns The memoized callback function
84
+ *
85
+ * @example
86
+ * ```ts
87
+ * function Parent() {
88
+ * const [count, setCount] = useState(0);
89
+ *
90
+ * const handleClick = useCallback(() => {
91
+ * console.log('Clicked with count:', count);
92
+ * }, [count]);
93
+ *
94
+ * return <Child onClick={handleClick} />;
95
+ * }
96
+ * ```
97
+ */
98
+ export declare function useCallback<T extends (...args: any[]) => any>(callback: T, deps: any[]): T;
99
+ //# sourceMappingURL=hooks.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hooks.d.ts","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAO,GAAG,EAAE,MAAM,oBAAoB,CAAC;AAG9C;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,QAAQ,CAAC,CAAC,EAAE,YAAY,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,CAsB/D;AAED;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,MAAM,CAAC,CAAC,EAAE,YAAY,EAAE,CAAC,GAAG;IAAE,OAAO,EAAE,CAAC,CAAA;CAAE,CAczD;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,OAAO,CAAC,CAAC,EAAE,OAAO,EAAE,MAAM,CAAC,EAAE,IAAI,EAAE,GAAG,EAAE,GAAG,CAAC,CAuB3D;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,WAAW,CAAC,CAAC,SAAS,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,GAAG,EAC3D,QAAQ,EAAE,CAAC,EACX,IAAI,EAAE,GAAG,EAAE,GACV,CAAC,CAEH"}
package/dist/hooks.js ADDED
@@ -0,0 +1,145 @@
1
+ /**
2
+ * React-style hooks for state persistence across re-renders.
3
+ * @module
4
+ */
5
+ import { ref } from '@bromscandium/core';
6
+ import { getCurrentInstance } from './lifecycle.js';
7
+ /**
8
+ * Creates a reactive state variable that persists across component re-renders.
9
+ * Similar to React's useState but returns a Ref for reactivity integration.
10
+ *
11
+ * @param initialValue - The initial value, or a function that returns the initial value
12
+ * @returns A reactive ref containing the state value
13
+ *
14
+ * @example
15
+ * ```ts
16
+ * function Counter() {
17
+ * const count = useState(0);
18
+ *
19
+ * return (
20
+ * <button onClick={() => count.value++}>
21
+ * Count: {count.value}
22
+ * </button>
23
+ * );
24
+ * }
25
+ *
26
+ * // With lazy initialization
27
+ * const expensive = useState(() => computeExpensiveValue());
28
+ * ```
29
+ */
30
+ export function useState(initialValue) {
31
+ const instance = getCurrentInstance();
32
+ if (!instance) {
33
+ const value = typeof initialValue === 'function'
34
+ ? initialValue()
35
+ : initialValue;
36
+ return ref(value);
37
+ }
38
+ const hookIndex = instance.hookIndex++;
39
+ if (hookIndex >= instance.hooks.length) {
40
+ const value = typeof initialValue === 'function'
41
+ ? initialValue()
42
+ : initialValue;
43
+ const stateRef = ref(value);
44
+ instance.hooks.push(stateRef);
45
+ return stateRef;
46
+ }
47
+ return instance.hooks[hookIndex];
48
+ }
49
+ /**
50
+ * Creates a mutable ref object that persists across re-renders without triggering updates.
51
+ * Useful for storing DOM references or mutable values that don't affect rendering.
52
+ *
53
+ * @param initialValue - The initial value for the ref
54
+ * @returns An object with a `current` property containing the value
55
+ *
56
+ * @example
57
+ * ```ts
58
+ * function TextInput() {
59
+ * const inputRef = useRef<HTMLInputElement>(null);
60
+ *
61
+ * onMounted(() => {
62
+ * inputRef.current?.focus();
63
+ * });
64
+ *
65
+ * return <input ref={inputRef} />;
66
+ * }
67
+ *
68
+ * // Storing mutable values
69
+ * const renderCount = useRef(0);
70
+ * renderCount.current++; // Doesn't trigger re-render
71
+ * ```
72
+ */
73
+ export function useRef(initialValue) {
74
+ const instance = getCurrentInstance();
75
+ if (!instance) {
76
+ return { current: initialValue };
77
+ }
78
+ const hookIndex = instance.hookIndex++;
79
+ if (hookIndex >= instance.hooks.length) {
80
+ instance.hooks.push({ current: initialValue });
81
+ }
82
+ return instance.hooks[hookIndex];
83
+ }
84
+ /**
85
+ * Memoizes an expensive computation, recalculating only when dependencies change.
86
+ *
87
+ * @param factory - A function that computes and returns the memoized value
88
+ * @param deps - An array of dependencies that trigger recalculation when changed
89
+ * @returns The memoized value
90
+ *
91
+ * @example
92
+ * ```ts
93
+ * function FilteredList({ items, filter }) {
94
+ * const filtered = useMemo(
95
+ * () => items.filter(item => item.includes(filter)),
96
+ * [items, filter]
97
+ * );
98
+ *
99
+ * return <ul>{filtered.map(item => <li>{item}</li>)}</ul>;
100
+ * }
101
+ * ```
102
+ */
103
+ export function useMemo(factory, deps) {
104
+ const instance = getCurrentInstance();
105
+ if (!instance) {
106
+ return factory();
107
+ }
108
+ const hookIndex = instance.hookIndex++;
109
+ if (hookIndex >= instance.hooks.length) {
110
+ instance.hooks.push({ value: factory(), deps });
111
+ return instance.hooks[hookIndex].value;
112
+ }
113
+ const hook = instance.hooks[hookIndex];
114
+ const depsChanged = !hook.deps || deps.some((dep, i) => dep !== hook.deps[i]);
115
+ if (depsChanged) {
116
+ hook.value = factory();
117
+ hook.deps = deps;
118
+ }
119
+ return hook.value;
120
+ }
121
+ /**
122
+ * Memoizes a callback function, returning the same reference until dependencies change.
123
+ * Useful for passing stable callbacks to child components to prevent unnecessary re-renders.
124
+ *
125
+ * @param callback - The callback function to memoize
126
+ * @param deps - An array of dependencies that trigger creating a new callback when changed
127
+ * @returns The memoized callback function
128
+ *
129
+ * @example
130
+ * ```ts
131
+ * function Parent() {
132
+ * const [count, setCount] = useState(0);
133
+ *
134
+ * const handleClick = useCallback(() => {
135
+ * console.log('Clicked with count:', count);
136
+ * }, [count]);
137
+ *
138
+ * return <Child onClick={handleClick} />;
139
+ * }
140
+ * ```
141
+ */
142
+ export function useCallback(callback, deps) {
143
+ return useMemo(() => callback, deps);
144
+ }
145
+ //# sourceMappingURL=hooks.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hooks.js","sourceRoot":"","sources":["../src/hooks.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,9 @@
1
+ export type { VNode, VNodeChild, VNodeChildren, VNodeType, ComponentFunction, ComponentInstance, } from './vnode.js';
2
+ export { Fragment, Text, createVNode, normalizeChildren, createTextVNode, isVNode, } from './vnode.js';
3
+ export { jsx, jsxs, jsxDEV, createElement, h, } from './jsx-runtime.js';
4
+ export type { JSXElement } from './jsx-runtime.js';
5
+ export { render, createApp, } from './renderer.js';
6
+ export type { AppConfig } from './renderer.js';
7
+ export { onMounted, onUnmounted, onUpdated, getCurrentInstance, setCurrentInstance, } from './lifecycle.js';
8
+ export { useState, useRef, useMemo, useCallback, } from './hooks.js';
9
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAGA,YAAY,EACV,KAAK,EACL,UAAU,EACV,aAAa,EACb,SAAS,EACT,iBAAiB,EACjB,iBAAiB,GAClB,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,QAAQ,EACR,IAAI,EACJ,WAAW,EACX,iBAAiB,EACjB,eAAe,EACf,OAAO,GACR,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,GAAG,EACH,IAAI,EACJ,MAAM,EACN,aAAa,EACb,CAAC,GACF,MAAM,kBAAkB,CAAC;AAG1B,YAAY,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAEnD,OAAO,EACL,MAAM,EACN,SAAS,GACV,MAAM,eAAe,CAAC;AAEvB,YAAY,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AAE/C,OAAO,EACL,SAAS,EACT,WAAW,EACX,SAAS,EACT,kBAAkB,EAClB,kBAAkB,GACnB,MAAM,gBAAgB,CAAC;AAGxB,OAAO,EACL,QAAQ,EACR,MAAM,EACN,OAAO,EACP,WAAW,GACZ,MAAM,YAAY,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,10 @@
1
+ // Runtime package exports
2
+ // Value exports from vnode
3
+ export { Fragment, Text, createVNode, normalizeChildren, createTextVNode, isVNode, } from './vnode.js';
4
+ // Value exports from jsx-runtime
5
+ export { jsx, jsxs, jsxDEV, createElement, h, } from './jsx-runtime.js';
6
+ export { render, createApp, } from './renderer.js';
7
+ export { onMounted, onUnmounted, onUpdated, getCurrentInstance, setCurrentInstance, } from './lifecycle.js';
8
+ // Hooks for state persistence
9
+ export { useState, useRef, useMemo, useCallback, } from './hooks.js';
10
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,0BAA0B;AAY1B,2BAA2B;AAC3B,OAAO,EACL,QAAQ,EACR,IAAI,EACJ,WAAW,EACX,iBAAiB,EACjB,eAAe,EACf,OAAO,GACR,MAAM,YAAY,CAAC;AAEpB,iCAAiC;AACjC,OAAO,EACL,GAAG,EACH,IAAI,EACJ,MAAM,EACN,aAAa,EACb,CAAC,GACF,MAAM,kBAAkB,CAAC;AAK1B,OAAO,EACL,MAAM,EACN,SAAS,GACV,MAAM,eAAe,CAAC;AAIvB,OAAO,EACL,SAAS,EACT,WAAW,EACX,SAAS,EACT,kBAAkB,EAClB,kBAAkB,GACnB,MAAM,gBAAgB,CAAC;AAExB,8BAA8B;AAC9B,OAAO,EACL,QAAQ,EACR,MAAM,EACN,OAAO,EACP,WAAW,GACZ,MAAM,YAAY,CAAC"}
@@ -0,0 +1,77 @@
1
+ /**
2
+ * JSX Runtime for TypeScript/Vite.
3
+ * Configure in tsconfig.json: "jsx": "react-jsx", "jsxImportSource": "@bromscandium/runtime"
4
+ * @module
5
+ */
6
+ import { Fragment, VNode, VNodeType } from './vnode.js';
7
+ export { Fragment };
8
+ /**
9
+ * JSX element type alias for VNode.
10
+ */
11
+ export interface JSXElement extends VNode {
12
+ }
13
+ /**
14
+ * Creates a virtual node from JSX syntax (React 17+ automatic runtime).
15
+ * This is called automatically by the TypeScript/Babel JSX transform.
16
+ *
17
+ * @param type - Element type (tag name or component function)
18
+ * @param props - Props object including children
19
+ * @param key - Optional key for list reconciliation
20
+ * @returns A virtual node
21
+ */
22
+ export declare function jsx(type: VNodeType, props: Record<string, any> | null, key?: string | number | null): VNode;
23
+ /**
24
+ * Creates a virtual node with static children (optimization hint).
25
+ * Functionally identical to jsx() but indicates children won't change.
26
+ *
27
+ * @param type - Element type (tag name or component function)
28
+ * @param props - Props object including children
29
+ * @param key - Optional key for list reconciliation
30
+ * @returns A virtual node
31
+ */
32
+ export declare function jsxs(type: VNodeType, props: Record<string, any> | null, key?: string | number | null): VNode;
33
+ /**
34
+ * Development version of jsx() with extra validation and warnings.
35
+ * Only performs validation when import.meta.env.DEV is true.
36
+ *
37
+ * @param type - Element type (tag name or component function)
38
+ * @param props - Props object including children
39
+ * @param key - Optional key for list reconciliation
40
+ * @param _isStatic - Unused static children hint
41
+ * @param _source - Source location for error messages
42
+ * @param _self - Component reference for error messages
43
+ * @returns A virtual node
44
+ */
45
+ export declare function jsxDEV(type: VNodeType, props: Record<string, any> | null, key?: string | number | null, _isStatic?: boolean, _source?: {
46
+ fileName: string;
47
+ lineNumber: number;
48
+ columnNumber: number;
49
+ }, _self?: any): VNode;
50
+ /**
51
+ * Creates a virtual node using classic createElement syntax.
52
+ * Use this for manual VNode creation without JSX.
53
+ *
54
+ * @param type - Element type (tag name or component function)
55
+ * @param props - Props object (without children)
56
+ * @param children - Child elements as rest parameters
57
+ * @returns A virtual node
58
+ *
59
+ * @example
60
+ * ```ts
61
+ * const vnode = createElement('div', { className: 'app' },
62
+ * createElement('h1', null, 'Hello'),
63
+ * createElement('p', null, 'World')
64
+ * );
65
+ * ```
66
+ */
67
+ export declare function createElement(type: VNodeType, props: Record<string, any> | null, ...children: any[]): VNode;
68
+ /**
69
+ * Alias for createElement, providing a shorter hyperscript-style API.
70
+ *
71
+ * @example
72
+ * ```ts
73
+ * const vnode = h('div', { className: 'app' }, h('span', null, 'Hello'));
74
+ * ```
75
+ */
76
+ export declare const h: typeof createElement;
77
+ //# sourceMappingURL=jsx-runtime.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"jsx-runtime.d.ts","sourceRoot":"","sources":["../src/jsx-runtime.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAc,QAAQ,EAAE,KAAK,EAAE,SAAS,EAAC,MAAM,YAAY,CAAC;AAEnE,OAAO,EAAE,QAAQ,EAAE,CAAC;AAEpB;;GAEG;AACH,MAAM,WAAW,UAAW,SAAQ,KAAK;CAAG;AAE5C;;;;;;;;GAQG;AACH,wBAAgB,GAAG,CACjB,IAAI,EAAE,SAAS,EACf,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,EACjC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,GAC3B,KAAK,CAQP;AAED;;;;;;;;GAQG;AACH,wBAAgB,IAAI,CAClB,IAAI,EAAE,SAAS,EACf,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,EACjC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,GAC3B,KAAK,CAEP;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,MAAM,CACpB,IAAI,EAAE,SAAS,EACf,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,EACjC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,EAC5B,SAAS,CAAC,EAAE,OAAO,EACnB,OAAO,CAAC,EAAE;IAAE,QAAQ,EAAE,MAAM,CAAC;IAAC,UAAU,EAAE,MAAM,CAAC;IAAC,YAAY,EAAE,MAAM,CAAA;CAAE,EACxE,KAAK,CAAC,EAAE,GAAG,GACV,KAAK,CAmBP;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,SAAS,EACf,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,EACjC,GAAG,QAAQ,EAAE,GAAG,EAAE,GACjB,KAAK,CAKP;AAED;;;;;;;GAOG;AACH,eAAO,MAAM,CAAC,sBAAgB,CAAC"}
@@ -0,0 +1,90 @@
1
+ /**
2
+ * JSX Runtime for TypeScript/Vite.
3
+ * Configure in tsconfig.json: "jsx": "react-jsx", "jsxImportSource": "@bromscandium/runtime"
4
+ * @module
5
+ */
6
+ import { createVNode, Fragment } from './vnode.js';
7
+ export { Fragment };
8
+ /**
9
+ * Creates a virtual node from JSX syntax (React 17+ automatic runtime).
10
+ * This is called automatically by the TypeScript/Babel JSX transform.
11
+ *
12
+ * @param type - Element type (tag name or component function)
13
+ * @param props - Props object including children
14
+ * @param key - Optional key for list reconciliation
15
+ * @returns A virtual node
16
+ */
17
+ export function jsx(type, props, key) {
18
+ const { children, ...restProps } = props || {};
19
+ return createVNode(type, { ...restProps, key: key ?? restProps?.key }, children);
20
+ }
21
+ /**
22
+ * Creates a virtual node with static children (optimization hint).
23
+ * Functionally identical to jsx() but indicates children won't change.
24
+ *
25
+ * @param type - Element type (tag name or component function)
26
+ * @param props - Props object including children
27
+ * @param key - Optional key for list reconciliation
28
+ * @returns A virtual node
29
+ */
30
+ export function jsxs(type, props, key) {
31
+ return jsx(type, props, key);
32
+ }
33
+ /**
34
+ * Development version of jsx() with extra validation and warnings.
35
+ * Only performs validation when import.meta.env.DEV is true.
36
+ *
37
+ * @param type - Element type (tag name or component function)
38
+ * @param props - Props object including children
39
+ * @param key - Optional key for list reconciliation
40
+ * @param _isStatic - Unused static children hint
41
+ * @param _source - Source location for error messages
42
+ * @param _self - Component reference for error messages
43
+ * @returns A virtual node
44
+ */
45
+ export function jsxDEV(type, props, key, _isStatic, _source, _self) {
46
+ if (import.meta.env?.DEV) {
47
+ if (typeof type === 'string' && type !== type.toLowerCase() && !type.includes('-')) {
48
+ console.warn(`Invalid element type: "${type}". HTML elements must be lowercase. ` +
49
+ `Did you mean to use a component? Components should start with uppercase.`);
50
+ }
51
+ if (props) {
52
+ if ('class' in props && !('className' in props)) {
53
+ console.warn(`Invalid prop "class" detected. Use "className" instead.`);
54
+ }
55
+ }
56
+ }
57
+ return jsx(type, props, key);
58
+ }
59
+ /**
60
+ * Creates a virtual node using classic createElement syntax.
61
+ * Use this for manual VNode creation without JSX.
62
+ *
63
+ * @param type - Element type (tag name or component function)
64
+ * @param props - Props object (without children)
65
+ * @param children - Child elements as rest parameters
66
+ * @returns A virtual node
67
+ *
68
+ * @example
69
+ * ```ts
70
+ * const vnode = createElement('div', { className: 'app' },
71
+ * createElement('h1', null, 'Hello'),
72
+ * createElement('p', null, 'World')
73
+ * );
74
+ * ```
75
+ */
76
+ export function createElement(type, props, ...children) {
77
+ const normalizedProps = props || {};
78
+ const flatChildren = children.length === 1 ? children[0] : children;
79
+ return createVNode(type, normalizedProps, flatChildren);
80
+ }
81
+ /**
82
+ * Alias for createElement, providing a shorter hyperscript-style API.
83
+ *
84
+ * @example
85
+ * ```ts
86
+ * const vnode = h('div', { className: 'app' }, h('span', null, 'Hello'));
87
+ * ```
88
+ */
89
+ export const h = createElement;
90
+ //# sourceMappingURL=jsx-runtime.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"jsx-runtime.js","sourceRoot":"","sources":["../src/jsx-runtime.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAC,WAAW,EAAE,QAAQ,EAAmB,MAAM,YAAY,CAAC;AAEnE,OAAO,EAAE,QAAQ,EAAE,CAAC;AAOpB;;;;;;;;GAQG;AACH,MAAM,UAAU,GAAG,CACjB,IAAe,EACf,KAAiC,EACjC,GAA4B;IAE5B,MAAM,EAAE,QAAQ,EAAE,GAAG,SAAS,EAAE,GAAG,KAAK,IAAI,EAAE,CAAC;IAE/C,OAAO,WAAW,CAChB,IAAI,EACJ,EAAC,GAAG,SAAS,EAAE,GAAG,EAAE,GAAG,IAAI,SAAS,EAAE,GAAG,EAAC,EAC1C,QAAQ,CACT,CAAC;AACJ,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,IAAI,CAClB,IAAe,EACf,KAAiC,EACjC,GAA4B;IAE5B,OAAO,GAAG,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,CAAC;AAC/B,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,MAAM,CACpB,IAAe,EACf,KAAiC,EACjC,GAA4B,EAC5B,SAAmB,EACnB,OAAwE,EACxE,KAAW;IAEX,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,CAAC;QACzB,IAAI,OAAO,IAAI,KAAK,QAAQ,IAAI,IAAI,KAAK,IAAI,CAAC,WAAW,EAAE,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;YACnF,OAAO,CAAC,IAAI,CACV,0BAA0B,IAAI,sCAAsC;gBACpE,0EAA0E,CAC3E,CAAC;QACJ,CAAC;QAED,IAAI,KAAK,EAAE,CAAC;YACV,IAAI,OAAO,IAAI,KAAK,IAAI,CAAC,CAAC,WAAW,IAAI,KAAK,CAAC,EAAE,CAAC;gBAChD,OAAO,CAAC,IAAI,CACV,yDAAyD,CAC1D,CAAC;YACJ,CAAC;QACH,CAAC;IACH,CAAC;IAED,OAAO,GAAG,CAAC,IAAI,EAAE,KAAK,EAAE,GAAG,CAAC,CAAC;AAC/B,CAAC;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,UAAU,aAAa,CAC3B,IAAe,EACf,KAAiC,EACjC,GAAG,QAAe;IAElB,MAAM,eAAe,GAAG,KAAK,IAAI,EAAE,CAAC;IACpC,MAAM,YAAY,GAAG,QAAQ,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC;IAEpE,OAAO,WAAW,CAAC,IAAI,EAAE,eAAe,EAAE,YAAY,CAAC,CAAC;AAC1D,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,CAAC,GAAG,aAAa,CAAC"}
@@ -0,0 +1,87 @@
1
+ /**
2
+ * Component lifecycle hook system.
3
+ * @module
4
+ */
5
+ import { ComponentInstance } from './vnode.js';
6
+ /**
7
+ * Sets the currently rendering component instance.
8
+ * Used internally by the renderer.
9
+ *
10
+ * @param instance - The component instance or null
11
+ */
12
+ export declare function setCurrentInstance(instance: ComponentInstance | null): void;
13
+ /**
14
+ * Returns the currently rendering component instance.
15
+ * Used internally by hooks to access component state.
16
+ *
17
+ * @returns The current component instance or null if outside a component
18
+ */
19
+ export declare function getCurrentInstance(): ComponentInstance | null;
20
+ /**
21
+ * Registers a callback to be invoked after the component is mounted to the DOM.
22
+ * The callback runs after the initial render and DOM insertion.
23
+ *
24
+ * @param fn - The callback function to invoke on mount
25
+ *
26
+ * @example
27
+ * ```ts
28
+ * function MyComponent() {
29
+ * onMounted(() => {
30
+ * console.log('Component mounted!');
31
+ * // DOM is available here
32
+ * });
33
+ *
34
+ * return <div>Hello</div>;
35
+ * }
36
+ * ```
37
+ */
38
+ export declare function onMounted(fn: () => void): void;
39
+ /**
40
+ * Registers a callback to be invoked before the component is unmounted.
41
+ * Use this to clean up side effects like timers, subscriptions, or event listeners.
42
+ *
43
+ * @param fn - The callback function to invoke on unmount
44
+ *
45
+ * @example
46
+ * ```ts
47
+ * function MyComponent() {
48
+ * const timer = setInterval(() => {}, 1000);
49
+ *
50
+ * onUnmounted(() => {
51
+ * clearInterval(timer);
52
+ * });
53
+ *
54
+ * return <div>Hello</div>;
55
+ * }
56
+ * ```
57
+ */
58
+ export declare function onUnmounted(fn: () => void): void;
59
+ /**
60
+ * Registers a callback to be invoked after the component updates.
61
+ * The callback runs after each re-render caused by reactive state changes.
62
+ *
63
+ * @param fn - The callback function to invoke after updates
64
+ *
65
+ * @example
66
+ * ```ts
67
+ * function MyComponent() {
68
+ * const count = ref(0);
69
+ *
70
+ * onUpdated(() => {
71
+ * console.log('Component updated, count is now:', count.value);
72
+ * });
73
+ *
74
+ * return <button onClick={() => count.value++}>{count.value}</button>;
75
+ * }
76
+ * ```
77
+ */
78
+ export declare function onUpdated(fn: () => void): void;
79
+ /**
80
+ * Invokes an array of lifecycle hook callbacks with error handling.
81
+ * Used internally by the renderer.
82
+ *
83
+ * @param hooks - Array of callback functions to invoke
84
+ * @param errorContext - Description of the hook type for error messages
85
+ */
86
+ export declare function invokeLifecycleHooks(hooks: Array<() => void>, errorContext?: string): void;
87
+ //# sourceMappingURL=lifecycle.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"lifecycle.d.ts","sourceRoot":"","sources":["../src/lifecycle.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC;AAI/C;;;;;GAKG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,iBAAiB,GAAG,IAAI,GAAG,IAAI,CAE3E;AAED;;;;;GAKG;AACH,wBAAgB,kBAAkB,IAAI,iBAAiB,GAAG,IAAI,CAE7D;AAmBD;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,SAAS,CAAC,EAAE,EAAE,MAAM,IAAI,GAAG,IAAI,CAE9C;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,WAAW,CAAC,EAAE,EAAE,MAAM,IAAI,GAAG,IAAI,CAEhD;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,SAAS,CAAC,EAAE,EAAE,MAAM,IAAI,GAAG,IAAI,CAE9C;AAED;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAClC,KAAK,EAAE,KAAK,CAAC,MAAM,IAAI,CAAC,EACxB,YAAY,CAAC,EAAE,MAAM,GACpB,IAAI,CAQN"}