@manyducks.co/dolla 2.0.0-alpha.5 → 2.0.0-alpha.51
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/README.md +81 -933
- package/dist/core/context.d.ts +65 -0
- package/dist/{modules → core}/dolla.d.ts +43 -26
- package/dist/core/markup.d.ts +102 -0
- package/dist/core/nodes/dom.d.ts +13 -0
- package/dist/core/nodes/dynamic.d.ts +30 -0
- package/dist/core/nodes/fragment.d.ts +19 -0
- package/dist/core/nodes/html.d.ts +34 -0
- package/dist/core/nodes/outlet.d.ts +20 -0
- package/dist/core/nodes/portal.d.ts +22 -0
- package/dist/core/nodes/repeat.d.ts +28 -0
- package/dist/core/nodes/view.d.ts +97 -0
- package/dist/core/signals-api.d.ts +42 -0
- package/dist/core/signals.d.ts +22 -0
- package/dist/core/store.d.ts +52 -0
- package/dist/core/symbols.d.ts +4 -0
- package/dist/{views → core/views}/default-crash-view.d.ts +1 -1
- package/dist/core/views/fragment.d.ts +8 -0
- package/dist/{views → core/views}/passthrough.d.ts +2 -2
- package/dist/fragment-Bvuvw3ue.js +8 -0
- package/dist/fragment-Bvuvw3ue.js.map +1 -0
- package/dist/{modules/http.d.ts → http/index.d.ts} +3 -5
- package/dist/index.d.ts +15 -10
- package/dist/index.js +1056 -1216
- package/dist/index.js.map +1 -1
- package/dist/jsx-dev-runtime.d.ts +2 -2
- package/dist/jsx-dev-runtime.js +8 -8
- package/dist/jsx-dev-runtime.js.map +1 -1
- package/dist/jsx-runtime.d.ts +3 -3
- package/dist/jsx-runtime.js +10 -10
- package/dist/jsx-runtime.js.map +1 -1
- package/dist/markup-QqAGIoYP.js +1501 -0
- package/dist/markup-QqAGIoYP.js.map +1 -0
- package/dist/{modules/router.d.ts → router/index.d.ts} +53 -60
- package/dist/{routing.d.ts → router/router.utils.d.ts} +17 -3
- package/dist/router/router.utils.test.d.ts +1 -0
- package/dist/translate/index.d.ts +133 -0
- package/dist/typeChecking.d.ts +2 -98
- package/dist/typeChecking.test.d.ts +1 -0
- package/dist/types.d.ts +17 -7
- package/dist/utils.d.ts +18 -3
- package/docs/http.md +29 -0
- package/docs/i18n.md +38 -0
- package/docs/index.md +10 -0
- package/docs/router.md +80 -0
- package/docs/setup.md +31 -0
- package/docs/signals.md +166 -0
- package/docs/state.md +141 -0
- package/docs/stores.md +62 -0
- package/docs/views.md +208 -0
- package/examples/webcomponent/index.html +14 -0
- package/examples/webcomponent/main.js +165 -0
- package/index.d.ts +2 -2
- package/notes/TODO.md +6 -0
- package/notes/atomic.md +452 -0
- package/notes/context-routes.md +61 -0
- package/notes/custom-nodes.md +17 -0
- package/notes/elimination.md +33 -0
- package/notes/molecule.md +35 -0
- package/notes/readme-scratch.md +260 -0
- package/notes/route-middleware.md +42 -0
- package/notes/scratch.md +330 -7
- package/notes/splitting.md +5 -0
- package/notes/stores.md +53 -0
- package/package.json +13 -10
- package/vite.config.js +5 -10
- package/build.js +0 -34
- package/dist/markup.d.ts +0 -100
- package/dist/modules/language.d.ts +0 -41
- package/dist/modules/render.d.ts +0 -17
- package/dist/nodes/cond.d.ts +0 -26
- package/dist/nodes/html.d.ts +0 -31
- package/dist/nodes/observer.d.ts +0 -29
- package/dist/nodes/outlet.d.ts +0 -22
- package/dist/nodes/portal.d.ts +0 -19
- package/dist/nodes/repeat.d.ts +0 -34
- package/dist/nodes/text.d.ts +0 -19
- package/dist/passthrough-CtoBcpag.js +0 -1245
- package/dist/passthrough-CtoBcpag.js.map +0 -1
- package/dist/signals.d.ts +0 -101
- package/dist/view.d.ts +0 -50
- package/tests/signals.test.js +0 -135
- /package/dist/{routing.test.d.ts → core/signals-api.test.d.ts} +0 -0
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import type { Dolla } from "./dolla";
|
|
2
|
+
import type { View } from "./nodes/view";
|
|
3
|
+
import type { Source } from "./signals-api";
|
|
4
|
+
import type { Store, StoreFunction } from "./store";
|
|
5
|
+
export interface ElementContext {
|
|
6
|
+
/**
|
|
7
|
+
* The root Dolla instance this element belongs to.
|
|
8
|
+
*/
|
|
9
|
+
root: Dolla;
|
|
10
|
+
/**
|
|
11
|
+
* Stores attached to this context.
|
|
12
|
+
*/
|
|
13
|
+
stores: Map<StoreFunction<any, any>, Store<any, any>>;
|
|
14
|
+
/**
|
|
15
|
+
* The nearest view.
|
|
16
|
+
*/
|
|
17
|
+
view?: View<any>;
|
|
18
|
+
/**
|
|
19
|
+
* A reference to the parent context.
|
|
20
|
+
*/
|
|
21
|
+
parent?: ElementContext;
|
|
22
|
+
/**
|
|
23
|
+
* Whether to create DOM nodes in the SVG namespace. An `<svg>` element will set this to true and pass it down to children.
|
|
24
|
+
*/
|
|
25
|
+
isSVG?: boolean;
|
|
26
|
+
/**
|
|
27
|
+
* The name of the nearest parent view.
|
|
28
|
+
*/
|
|
29
|
+
/**
|
|
30
|
+
* The context of the nearest parent view.
|
|
31
|
+
*/
|
|
32
|
+
/**
|
|
33
|
+
* Current route layer of the nearest view.
|
|
34
|
+
*/
|
|
35
|
+
route?: Source<View<{}> | undefined>;
|
|
36
|
+
}
|
|
37
|
+
export interface ComponentContext {
|
|
38
|
+
/**
|
|
39
|
+
* A name for debugging purposes. Prepended to log messages.
|
|
40
|
+
*/
|
|
41
|
+
name: string;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* A context capable of providing stores.
|
|
45
|
+
*/
|
|
46
|
+
export interface StoreProviderContext {
|
|
47
|
+
/**
|
|
48
|
+
* Attaches a new store to this context and returns it.
|
|
49
|
+
*/
|
|
50
|
+
provide<Value>(store: StoreFunction<{}, Value>): Value;
|
|
51
|
+
/**
|
|
52
|
+
* Attaches a new store to this context and returns it.
|
|
53
|
+
*/
|
|
54
|
+
provide<Value>(store: StoreFunction<undefined, Value>): Value;
|
|
55
|
+
/**
|
|
56
|
+
* Attaches a new store to this context and returns it.
|
|
57
|
+
*/
|
|
58
|
+
provide<Options, Value>(store: StoreFunction<Options, Value>, options: Options): Value;
|
|
59
|
+
}
|
|
60
|
+
export interface StoreConsumerContext {
|
|
61
|
+
/**
|
|
62
|
+
* Gets the closest instance of a store. Throws an error if the store isn't provided higher in the tree.
|
|
63
|
+
*/
|
|
64
|
+
get<Value>(store: StoreFunction<any, Value>): Value;
|
|
65
|
+
}
|
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
1
|
+
import { HTTP } from "../http/index.js";
|
|
2
|
+
import { type Router } from "../router/index.js";
|
|
3
|
+
import { I18n } from "../translate/index.js";
|
|
4
|
+
import type { StoreConsumerContext, StoreProviderContext } from "./context.js";
|
|
5
|
+
import { type Markup, type MarkupElement } from "./markup.js";
|
|
6
|
+
import { type ViewElement, type ViewFunction } from "./nodes/view.js";
|
|
7
|
+
import { StoreFunction } from "./store.js";
|
|
8
|
+
import { type CrashViewProps } from "./views/default-crash-view.js";
|
|
9
9
|
export type Environment = "development" | "production";
|
|
10
10
|
/**
|
|
11
11
|
* Log type toggles. Each message category can be turned on or off or enabled only in a specific environment.
|
|
@@ -22,6 +22,7 @@ export interface Logger {
|
|
|
22
22
|
warn(...args: any[]): void;
|
|
23
23
|
error(...args: any[]): void;
|
|
24
24
|
crash(error: Error): void;
|
|
25
|
+
setName(name: string): Logger;
|
|
25
26
|
}
|
|
26
27
|
export interface LoggerErrorContext {
|
|
27
28
|
error: Error;
|
|
@@ -38,22 +39,11 @@ export type LoggerOptions = {
|
|
|
38
39
|
*/
|
|
39
40
|
uid?: string;
|
|
40
41
|
};
|
|
41
|
-
export declare class Dolla {
|
|
42
|
+
export declare class Dolla implements StoreProviderContext, StoreConsumerContext {
|
|
42
43
|
#private;
|
|
43
44
|
readonly http: HTTP;
|
|
44
|
-
readonly
|
|
45
|
-
readonly render: Render;
|
|
46
|
-
readonly router: Router;
|
|
45
|
+
readonly i18n: I18n;
|
|
47
46
|
constructor();
|
|
48
|
-
createSignal: typeof createSignal;
|
|
49
|
-
createSettableSignal: typeof createSettableSignal;
|
|
50
|
-
toSettableSignal: typeof toSettableSignal;
|
|
51
|
-
signalify: typeof signalify;
|
|
52
|
-
designalify: typeof designalify;
|
|
53
|
-
derive: typeof derive;
|
|
54
|
-
watch: typeof watch;
|
|
55
|
-
createRef: typeof createRef;
|
|
56
|
-
isRef: typeof isRef;
|
|
57
47
|
/**
|
|
58
48
|
* True when the app is connected to a DOM node and displayed to the user.
|
|
59
49
|
*/
|
|
@@ -73,8 +63,34 @@ export declare class Dolla {
|
|
|
73
63
|
* When a crash is reported the app will be unmounted and replaced with this crash page.
|
|
74
64
|
*/
|
|
75
65
|
setCrashView(view: ViewFunction<CrashViewProps>): void;
|
|
76
|
-
|
|
77
|
-
|
|
66
|
+
/**
|
|
67
|
+
* Returns the HTMLElement Dolla is mounted to. This will return undefined until Dolla.mount() is called.
|
|
68
|
+
*/
|
|
69
|
+
getRootElement(): Element | undefined;
|
|
70
|
+
/**
|
|
71
|
+
* Returns the top level view Dolla is rendering inside the root element. This will return undefined until Dolla.mount() is called.
|
|
72
|
+
*/
|
|
73
|
+
getRootView(): ViewElement | undefined;
|
|
74
|
+
/**
|
|
75
|
+
* Attaches a new store to this context.
|
|
76
|
+
*/
|
|
77
|
+
provide<Value>(store: StoreFunction<{}, Value>): Value;
|
|
78
|
+
/**
|
|
79
|
+
* Attaches a new store to this context.
|
|
80
|
+
*/
|
|
81
|
+
provide<Value>(store: StoreFunction<undefined, Value>): Value;
|
|
82
|
+
/**
|
|
83
|
+
* Attaches a new store to this context.
|
|
84
|
+
*/
|
|
85
|
+
provide<Options, Value>(store: StoreFunction<Options, Value>, options: Options): Value;
|
|
86
|
+
/**
|
|
87
|
+
* Gets the nearest instance of a store. Throws an error if the store isn't provided higher in the tree.
|
|
88
|
+
*/
|
|
89
|
+
get<Value>(store: StoreFunction<any, Value>): Value;
|
|
90
|
+
mount(selector: string, router: Router): Promise<void>;
|
|
91
|
+
mount(selector: string, view: ViewFunction<any>): Promise<void>;
|
|
92
|
+
mount(element: Element, router: Router): Promise<void>;
|
|
93
|
+
mount(element: Element, view: ViewFunction<any>): Promise<void>;
|
|
78
94
|
unmount(): Promise<void>;
|
|
79
95
|
/**
|
|
80
96
|
* Registers a `callback` to run after `Dolla.mount` is called, before the app is mounted. If `callback` returns a Promise,
|
|
@@ -99,13 +115,14 @@ export declare class Dolla {
|
|
|
99
115
|
*/
|
|
100
116
|
setLoggles(options: Partial<Loggles>): void;
|
|
101
117
|
setLogFilter(filter: string | RegExp): void;
|
|
102
|
-
createLogger(name: string
|
|
118
|
+
createLogger(name: string, options?: LoggerOptions): Logger;
|
|
103
119
|
/**
|
|
104
120
|
*
|
|
105
121
|
*/
|
|
106
|
-
constructView<P>(view: ViewFunction<P>, props: P, children?: Markup[]):
|
|
122
|
+
constructView<P>(view: ViewFunction<P>, props: P, children?: Markup[]): ViewElement;
|
|
107
123
|
/**
|
|
108
124
|
*
|
|
109
125
|
*/
|
|
110
|
-
constructMarkup(markup: Markup | Markup[]):
|
|
126
|
+
constructMarkup(markup: Markup | Markup[]): MarkupElement;
|
|
111
127
|
}
|
|
128
|
+
export declare function getDefaultConsole(): Console | undefined;
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import type { Renderable } from "../types.js";
|
|
2
|
+
import type { ElementContext } from "./context.js";
|
|
3
|
+
import { View, type ViewContext, type ViewFunction, type ViewResult } from "./nodes/view.js";
|
|
4
|
+
import { type MaybeSignal, type Signal } from "./signals-api.js";
|
|
5
|
+
/**
|
|
6
|
+
* Markup is a set of element metadata that hasn't been constructed into a MarkupElement yet.
|
|
7
|
+
*/
|
|
8
|
+
export interface Markup {
|
|
9
|
+
/**
|
|
10
|
+
* In the case of a view, type will be the View function itself. It can also hold an identifier for special nodes like "$cond", "$repeat", etc.
|
|
11
|
+
* DOM nodes can be created by name, such as HTML elements like "div", "ul" or "span", SVG elements like ""
|
|
12
|
+
*/
|
|
13
|
+
type: string | ViewFunction<any>;
|
|
14
|
+
/**
|
|
15
|
+
* Data that will be passed to a new MarkupElement instance when it is constructed.
|
|
16
|
+
*/
|
|
17
|
+
props?: Record<string, any>;
|
|
18
|
+
/**
|
|
19
|
+
*
|
|
20
|
+
*/
|
|
21
|
+
children?: any[];
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* A DOM node that has been constructed from a Markup object.
|
|
25
|
+
*/
|
|
26
|
+
export interface MarkupElement {
|
|
27
|
+
readonly domNode?: Node;
|
|
28
|
+
readonly isMounted: boolean;
|
|
29
|
+
mount(parent: Node, after?: Node): void;
|
|
30
|
+
/**
|
|
31
|
+
* Disconnect from the DOM and clean up. If parentIsUnmounting, DOM operations are skipped.
|
|
32
|
+
* parentIsUnmounting is set for all children by HTML nodes when they unmount.
|
|
33
|
+
*/
|
|
34
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
35
|
+
}
|
|
36
|
+
export declare function isMarkup(value: any): value is Markup;
|
|
37
|
+
export declare function isMarkupElement(value: any): value is MarkupElement;
|
|
38
|
+
export declare function toMarkup(renderables: Renderable | Renderable[]): Markup[];
|
|
39
|
+
export declare enum MarkupType {
|
|
40
|
+
Text = "$text",
|
|
41
|
+
Repeat = "$repeat",
|
|
42
|
+
Dynamic = "$dynamic",
|
|
43
|
+
Outlet = "$outlet",
|
|
44
|
+
Fragment = "$fragment",
|
|
45
|
+
Node = "$node",
|
|
46
|
+
Portal = "$portal"
|
|
47
|
+
}
|
|
48
|
+
export interface MarkupAttributes {
|
|
49
|
+
[MarkupType.Text]: {
|
|
50
|
+
value: any;
|
|
51
|
+
};
|
|
52
|
+
[MarkupType.Repeat]: {
|
|
53
|
+
items: Signal<any[]>;
|
|
54
|
+
keyFn: (value: any, index: number) => string | number | symbol;
|
|
55
|
+
renderFn: (item: Signal<any>, index: Signal<number>, ctx: ViewContext) => ViewResult;
|
|
56
|
+
};
|
|
57
|
+
[MarkupType.Dynamic]: {
|
|
58
|
+
source: Signal<Renderable>;
|
|
59
|
+
};
|
|
60
|
+
[MarkupType.Outlet]: {
|
|
61
|
+
view: Signal<View<{}> | undefined>;
|
|
62
|
+
};
|
|
63
|
+
[MarkupType.Fragment]: {
|
|
64
|
+
children: MaybeSignal<MarkupElement[]>;
|
|
65
|
+
};
|
|
66
|
+
[MarkupType.Node]: {
|
|
67
|
+
value: Node;
|
|
68
|
+
};
|
|
69
|
+
[MarkupType.Portal]: {
|
|
70
|
+
content: Renderable;
|
|
71
|
+
parent: Node;
|
|
72
|
+
};
|
|
73
|
+
[tag: string]: Record<string, any>;
|
|
74
|
+
}
|
|
75
|
+
export declare function markup<T extends keyof MarkupAttributes>(type: T, attributes: MarkupAttributes[T], ...children: Renderable[]): Markup;
|
|
76
|
+
export declare function markup<I>(type: ViewFunction<I>, attributes?: I, ...children: any[]): Markup;
|
|
77
|
+
/**
|
|
78
|
+
* Displays `thenContent` when `condition` is truthy and `elseContent` when falsy.
|
|
79
|
+
*/
|
|
80
|
+
export declare function when(condition: MaybeSignal<any>, thenContent?: Renderable, elseContent?: Renderable): Markup;
|
|
81
|
+
/**
|
|
82
|
+
* Inverted `when`. Displays `thenContent` when `condition` is falsy and `elseContent` when truthy.
|
|
83
|
+
*/
|
|
84
|
+
export declare function unless(condition: MaybeSignal<any>, thenContent?: Renderable, elseContent?: Renderable): Markup;
|
|
85
|
+
/**
|
|
86
|
+
* Calls `renderFn` for each item in `items`. Dynamically adds and removes views as items change.
|
|
87
|
+
* The result of `keyFn` is used to compare items and decide if item was added, removed or updated.
|
|
88
|
+
*/
|
|
89
|
+
export declare function repeat<T>(items: MaybeSignal<T[]>, keyFn: (value: T, index: number) => string | number | symbol, renderFn: (item: Signal<T>, index: Signal<number>, ctx: ViewContext) => ViewResult): Markup;
|
|
90
|
+
/**
|
|
91
|
+
* Renders `content` into a `parent` node anywhere in the page, rather than its usual position in the view.
|
|
92
|
+
*/
|
|
93
|
+
export declare function portal(parent: Node, content: Renderable): Markup;
|
|
94
|
+
/**
|
|
95
|
+
* Construct Markup metadata into a set of MarkupElements.
|
|
96
|
+
*/
|
|
97
|
+
export declare function constructMarkup(elementContext: ElementContext, markup: Markup | Markup[]): MarkupElement[];
|
|
98
|
+
/**
|
|
99
|
+
* Combines one or more MarkupElements into a single MarkupElement.
|
|
100
|
+
*/
|
|
101
|
+
export declare function groupElements(elements: MarkupElement[]): MarkupElement;
|
|
102
|
+
export declare function isRenderable(value: unknown): value is Renderable;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { MarkupElement } from "../markup";
|
|
2
|
+
import { IS_MARKUP_ELEMENT } from "../symbols";
|
|
3
|
+
/**
|
|
4
|
+
* Wraps any plain DOM node in a MarkupElement interface.
|
|
5
|
+
*/
|
|
6
|
+
export declare class DOMNode implements MarkupElement {
|
|
7
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
8
|
+
domNode: Node;
|
|
9
|
+
get isMounted(): boolean;
|
|
10
|
+
constructor(node: Node);
|
|
11
|
+
mount(parent: Node, after?: Node): void;
|
|
12
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
13
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import type { Renderable } from "../../types.js";
|
|
2
|
+
import type { ElementContext } from "../context.js";
|
|
3
|
+
import { type MarkupElement } from "../markup.js";
|
|
4
|
+
import { Signal } from "../signals-api.js";
|
|
5
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
6
|
+
interface DynamicOptions {
|
|
7
|
+
source: Signal<Renderable>;
|
|
8
|
+
elementContext: ElementContext;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Displays dynamic children without a parent element.
|
|
12
|
+
* Renders a Reactive value via a render function.
|
|
13
|
+
*
|
|
14
|
+
* This is probably the most used element type aside from HTML.
|
|
15
|
+
*/
|
|
16
|
+
export declare class Dynamic implements MarkupElement {
|
|
17
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
18
|
+
domNode: Text;
|
|
19
|
+
private children;
|
|
20
|
+
private elementContext;
|
|
21
|
+
private source;
|
|
22
|
+
private unsubscribe?;
|
|
23
|
+
get isMounted(): boolean;
|
|
24
|
+
constructor(options: DynamicOptions);
|
|
25
|
+
mount(parent: Node, after?: Node): void;
|
|
26
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
27
|
+
cleanup(parentIsUnmounting: boolean): void;
|
|
28
|
+
update(children: Renderable[]): void;
|
|
29
|
+
}
|
|
30
|
+
export {};
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { type MarkupElement } from "../markup.js";
|
|
2
|
+
import { type MaybeSignal } from "../signals-api.js";
|
|
3
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
4
|
+
/**
|
|
5
|
+
* Manages several MarkupElements as one.
|
|
6
|
+
*/
|
|
7
|
+
export declare class Fragment implements MarkupElement {
|
|
8
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
9
|
+
domNode: Text;
|
|
10
|
+
isMounted: boolean;
|
|
11
|
+
private source;
|
|
12
|
+
private elements;
|
|
13
|
+
private unsubscribe?;
|
|
14
|
+
constructor(source: MaybeSignal<MarkupElement[]>);
|
|
15
|
+
mount(parent: Node, after?: Node | undefined): void;
|
|
16
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
17
|
+
private cleanup;
|
|
18
|
+
private update;
|
|
19
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { type ElementContext } from "../context.js";
|
|
2
|
+
import { type MarkupElement } from "../markup.js";
|
|
3
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
4
|
+
type HTMLOptions = {
|
|
5
|
+
elementContext: ElementContext;
|
|
6
|
+
tag: string;
|
|
7
|
+
props: Record<string, any>;
|
|
8
|
+
children?: any[];
|
|
9
|
+
};
|
|
10
|
+
export declare class HTML implements MarkupElement {
|
|
11
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
12
|
+
domNode: HTMLElement | SVGElement;
|
|
13
|
+
private props;
|
|
14
|
+
private childMarkup;
|
|
15
|
+
private children;
|
|
16
|
+
private unsubscribers;
|
|
17
|
+
private elementContext;
|
|
18
|
+
private logger;
|
|
19
|
+
private ref?;
|
|
20
|
+
private canClickAway;
|
|
21
|
+
get isMounted(): boolean;
|
|
22
|
+
constructor({ tag, props, children, elementContext }: HTMLOptions);
|
|
23
|
+
mount(parent: Node, after?: Node): void;
|
|
24
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
25
|
+
private attachProp;
|
|
26
|
+
private applyProps;
|
|
27
|
+
private applyStyles;
|
|
28
|
+
private applyClasses;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Converts a camelCase string to kebab-case.
|
|
32
|
+
*/
|
|
33
|
+
export declare function camelToKebab(value: string): string;
|
|
34
|
+
export {};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { type MarkupElement } from "../markup.js";
|
|
2
|
+
import { type Signal } from "../signals-api.js";
|
|
3
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
4
|
+
import { View } from "./view.js";
|
|
5
|
+
/**
|
|
6
|
+
* Renders the subroute of the nearest view.
|
|
7
|
+
*/
|
|
8
|
+
export declare class Outlet implements MarkupElement {
|
|
9
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
10
|
+
domNode: Text;
|
|
11
|
+
isMounted: boolean;
|
|
12
|
+
private view;
|
|
13
|
+
private mountedView?;
|
|
14
|
+
private unsubscribe?;
|
|
15
|
+
constructor(view: Signal<View<{}> | undefined>);
|
|
16
|
+
mount(parent: Node, after?: Node | undefined): void;
|
|
17
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
18
|
+
private cleanup;
|
|
19
|
+
private update;
|
|
20
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { Renderable } from "../../types.js";
|
|
2
|
+
import type { ElementContext } from "../context.js";
|
|
3
|
+
import { type MarkupElement } from "../markup.js";
|
|
4
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
5
|
+
interface PortalConfig {
|
|
6
|
+
content: Renderable;
|
|
7
|
+
parent: Node;
|
|
8
|
+
elementContext: ElementContext;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Renders content into a specified parent node.
|
|
12
|
+
*/
|
|
13
|
+
export declare class Portal implements MarkupElement {
|
|
14
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
15
|
+
private config;
|
|
16
|
+
private element?;
|
|
17
|
+
get isMounted(): boolean;
|
|
18
|
+
constructor(config: PortalConfig);
|
|
19
|
+
mount(_parent: Node, _after?: Node): void;
|
|
20
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
21
|
+
}
|
|
22
|
+
export {};
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { type ElementContext } from "../context.js";
|
|
2
|
+
import { type MarkupElement } from "../markup.js";
|
|
3
|
+
import { type Signal } from "../signals-api.js";
|
|
4
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
5
|
+
import { type ViewContext, type ViewResult } from "./view.js";
|
|
6
|
+
interface RepeatOptions<T> {
|
|
7
|
+
elementContext: ElementContext;
|
|
8
|
+
items: Signal<T[]>;
|
|
9
|
+
keyFn: (item: T, index: number) => string | number | symbol;
|
|
10
|
+
renderFn: (item: Signal<T>, index: Signal<number>, ctx: ViewContext) => ViewResult;
|
|
11
|
+
}
|
|
12
|
+
export declare class Repeat<T> implements MarkupElement {
|
|
13
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
14
|
+
domNode: Text;
|
|
15
|
+
private items;
|
|
16
|
+
private unsubscribe;
|
|
17
|
+
private connectedItems;
|
|
18
|
+
private elementContext;
|
|
19
|
+
private renderFn;
|
|
20
|
+
private keyFn;
|
|
21
|
+
get isMounted(): boolean;
|
|
22
|
+
constructor({ elementContext, items, renderFn, keyFn }: RepeatOptions<T>);
|
|
23
|
+
mount(parent: Node, after?: Node): void;
|
|
24
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
25
|
+
private _cleanup;
|
|
26
|
+
private _update;
|
|
27
|
+
}
|
|
28
|
+
export {};
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
import type { ComponentContext, ElementContext, StoreConsumerContext, StoreProviderContext } from "../context.js";
|
|
2
|
+
import type { Logger } from "../dolla.js";
|
|
3
|
+
import { type Markup, type MarkupElement } from "../markup.js";
|
|
4
|
+
import { type Signal, type EffectCallback, type UnsubscribeFunction } from "../signals-api.js";
|
|
5
|
+
import { StoreFunction } from "../store.js";
|
|
6
|
+
import { IS_MARKUP_ELEMENT } from "../symbols.js";
|
|
7
|
+
/**
|
|
8
|
+
* Any valid value that a View can return.
|
|
9
|
+
*/
|
|
10
|
+
export type ViewResult = Node | Signal<any> | Markup | Markup[] | null;
|
|
11
|
+
export type ViewFunction<P> = (this: ViewContext, props: P, context: ViewContext) => ViewResult;
|
|
12
|
+
/**
|
|
13
|
+
* A view that has been constructed into DOM nodes.
|
|
14
|
+
*/
|
|
15
|
+
export interface ViewElement extends MarkupElement {
|
|
16
|
+
setRouteView(view: ViewFunction<{}>): ViewElement;
|
|
17
|
+
}
|
|
18
|
+
export interface ViewContext extends Omit<Logger, "setName">, ComponentContext, StoreProviderContext, StoreConsumerContext {
|
|
19
|
+
/**
|
|
20
|
+
* An ID unique to this view.
|
|
21
|
+
*/
|
|
22
|
+
readonly uid: string;
|
|
23
|
+
/**
|
|
24
|
+
* True while this view is connected to the DOM.
|
|
25
|
+
*/
|
|
26
|
+
readonly isMounted: boolean;
|
|
27
|
+
/**
|
|
28
|
+
* Registers a callback to run just before this view is mounted. DOM nodes are not yet attached to the page.
|
|
29
|
+
*/
|
|
30
|
+
beforeMount(callback: () => void): void;
|
|
31
|
+
/**
|
|
32
|
+
* Registers a callback to run just after this view is mounted.
|
|
33
|
+
*/
|
|
34
|
+
onMount(callback: () => void): void;
|
|
35
|
+
/**
|
|
36
|
+
* Registers a callback to run just before this view is unmounted. DOM nodes are still attached to the page.
|
|
37
|
+
*/
|
|
38
|
+
beforeUnmount(callback: () => void): void;
|
|
39
|
+
/**
|
|
40
|
+
* Registers a callback to run just after this view is unmounted.
|
|
41
|
+
*/
|
|
42
|
+
onUnmount(callback: () => void): void;
|
|
43
|
+
/**
|
|
44
|
+
* Passes a getter function to `callback` that will track reactive states and return their current values.
|
|
45
|
+
* Callback will be run each time a tracked state gets a new value.
|
|
46
|
+
*/
|
|
47
|
+
effect(callback: EffectCallback): UnsubscribeFunction;
|
|
48
|
+
/**
|
|
49
|
+
* Displays this view's subroutes if mounted as a router view.
|
|
50
|
+
*/
|
|
51
|
+
outlet(): Markup;
|
|
52
|
+
}
|
|
53
|
+
interface Context extends Omit<Logger, "setName"> {
|
|
54
|
+
}
|
|
55
|
+
declare class Context implements ViewContext {
|
|
56
|
+
private view;
|
|
57
|
+
constructor(view: View<any>);
|
|
58
|
+
get uid(): string;
|
|
59
|
+
get isMounted(): boolean;
|
|
60
|
+
get name(): string;
|
|
61
|
+
set name(value: string);
|
|
62
|
+
provide<Value>(store: StoreFunction<any, Value>, options?: any): Value;
|
|
63
|
+
get<Value>(store: StoreFunction<any, Value>): Value;
|
|
64
|
+
beforeMount(callback: () => void): void;
|
|
65
|
+
onMount(callback: () => void): void;
|
|
66
|
+
beforeUnmount(callback: () => void): void;
|
|
67
|
+
onUnmount(callback: () => void): void;
|
|
68
|
+
effect(callback: EffectCallback): UnsubscribeFunction;
|
|
69
|
+
outlet(): Markup;
|
|
70
|
+
}
|
|
71
|
+
export declare class View<P> implements ViewElement {
|
|
72
|
+
[IS_MARKUP_ELEMENT]: boolean;
|
|
73
|
+
uniqueId: string;
|
|
74
|
+
elementContext: ElementContext;
|
|
75
|
+
logger: Logger;
|
|
76
|
+
props: P & {
|
|
77
|
+
children: Markup[] | undefined;
|
|
78
|
+
};
|
|
79
|
+
fn: ViewFunction<P>;
|
|
80
|
+
element?: MarkupElement;
|
|
81
|
+
name: string;
|
|
82
|
+
context: Context;
|
|
83
|
+
lifecycleListeners: {
|
|
84
|
+
beforeMount: (() => any)[];
|
|
85
|
+
mount: (() => any)[];
|
|
86
|
+
beforeUnmount: (() => any)[];
|
|
87
|
+
unmount: (() => any)[];
|
|
88
|
+
};
|
|
89
|
+
constructor(elementContext: ElementContext, fn: ViewFunction<P>, props: P, children?: Markup[]);
|
|
90
|
+
get domNode(): Node;
|
|
91
|
+
isMounted: boolean;
|
|
92
|
+
mount(parent: Node, after?: Node): void;
|
|
93
|
+
unmount(parentIsUnmounting?: boolean): void;
|
|
94
|
+
setRouteView(fn: ViewFunction<{}>): View<{}>;
|
|
95
|
+
private _initialize;
|
|
96
|
+
}
|
|
97
|
+
export {};
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A getter that returns the current value held within the signal.
|
|
3
|
+
* If called inside a trackable scope this signal will be tracked as a dependency.
|
|
4
|
+
*/
|
|
5
|
+
export interface Signal<T> {
|
|
6
|
+
(): T;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Extends Signal with the ability to pass a value or an updater function to change the Signal's value.
|
|
10
|
+
*/
|
|
11
|
+
export interface Source<T> extends Signal<T> {
|
|
12
|
+
(value: T): void;
|
|
13
|
+
(updater: (value: T) => T): void;
|
|
14
|
+
}
|
|
15
|
+
export type MaybeSignal<T> = Signal<T> | T;
|
|
16
|
+
export type EqualityFunction<T> = (current: T, next: T) => boolean;
|
|
17
|
+
export interface SignalOptions<T> {
|
|
18
|
+
/**
|
|
19
|
+
* A function to compare the current and next values. Returning `true` means the value has changed.
|
|
20
|
+
*/
|
|
21
|
+
equals?: EqualityFunction<T>;
|
|
22
|
+
}
|
|
23
|
+
export declare function isSource<T>(value: MaybeSignal<T>): value is Source<T>;
|
|
24
|
+
export declare function peek<T>(value: MaybeSignal<T>): T;
|
|
25
|
+
export declare function get<T>(value: MaybeSignal<T>): T;
|
|
26
|
+
/**
|
|
27
|
+
* Function to be invoked for the effect. Can return an optional cleanup function to be called between invocations.
|
|
28
|
+
*/
|
|
29
|
+
export type EffectCallback = () => void | (() => void);
|
|
30
|
+
export type UnsubscribeFunction = () => void;
|
|
31
|
+
/**
|
|
32
|
+
* Creates a tracked scope that re-runs whenever the values of any tracked reactives changes.
|
|
33
|
+
* Reactives are tracked by accessing their `value` within the body of the function.
|
|
34
|
+
*
|
|
35
|
+
* NOTE: You must call the unsubscribe function to stop watching for changes.
|
|
36
|
+
* If you are using an effect inside a View or Store, use `ctx.effect` instead, which cleans up automatically when the component unmounts.
|
|
37
|
+
*/
|
|
38
|
+
export declare function effect(fn: EffectCallback): UnsubscribeFunction;
|
|
39
|
+
export declare function $<T>(compute: () => MaybeSignal<T>, options?: SignalOptions<T>): Signal<T>;
|
|
40
|
+
export declare function $<T>(value: T, options?: SignalOptions<T>): Source<T>;
|
|
41
|
+
export declare function $<T>(value: undefined, options?: SignalOptions<T>): Source<T | undefined>;
|
|
42
|
+
export declare function $<T>(): Source<T | undefined>;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { type Dependency, type Subscriber, SubscriberFlags } from "alien-signals";
|
|
2
|
+
import type { EqualityFunction } from "./signals-api";
|
|
3
|
+
export interface Effect extends Subscriber, Dependency {
|
|
4
|
+
/**
|
|
5
|
+
* Effect function. Can return an optional cleanup callback to be invoked before the next fn() call.
|
|
6
|
+
*/
|
|
7
|
+
fn(): (() => void) | void;
|
|
8
|
+
cleanup?: () => void;
|
|
9
|
+
}
|
|
10
|
+
export interface Computed<T = any> extends Value<T | undefined>, Subscriber {
|
|
11
|
+
getter: (cachedValue?: T) => T;
|
|
12
|
+
equals: EqualityFunction<T>;
|
|
13
|
+
}
|
|
14
|
+
export interface Value<T = any> extends Dependency {
|
|
15
|
+
current: T;
|
|
16
|
+
}
|
|
17
|
+
export declare const link: (dep: Dependency, sub: Subscriber) => import("alien-signals").Link | undefined, propagate: (link: import("alien-signals").Link) => void, updateDirtyFlag: (sub: Subscriber, flags: SubscriberFlags) => boolean, startTracking: (sub: Subscriber) => void, endTracking: (sub: Subscriber) => void, processEffectNotifications: () => void, processComputedUpdate: (computed: Dependency & Subscriber, flags: SubscriberFlags) => void, processPendingInnerEffects: (sub: Subscriber, flags: SubscriberFlags) => void;
|
|
18
|
+
export declare let activeSub: Subscriber | undefined;
|
|
19
|
+
export declare function queueEffect(e: Effect): void;
|
|
20
|
+
export declare function stopEffect(this: Effect): void;
|
|
21
|
+
export declare function pauseTracking(): void;
|
|
22
|
+
export declare function resumeTracking(): void;
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import type { ComponentContext, ElementContext, StoreConsumerContext } from "./context.js";
|
|
2
|
+
import type { Logger } from "./dolla.js";
|
|
3
|
+
import { type EffectCallback, type UnsubscribeFunction } from "./signals-api.js";
|
|
4
|
+
export type StoreFunction<Options, Value> = (this: StoreContext, options: Options, context: StoreContext) => Value;
|
|
5
|
+
export type StoreFactory<Options, Value> = Options extends undefined ? () => Store<Options, Value> : (options: Options) => Store<Options, Value>;
|
|
6
|
+
export interface StoreContext extends Omit<Logger, "setName">, ComponentContext, StoreConsumerContext {
|
|
7
|
+
/**
|
|
8
|
+
* True while this store is attached to a context that is currently mounted in the view tree.
|
|
9
|
+
*/
|
|
10
|
+
readonly isMounted: boolean;
|
|
11
|
+
/**
|
|
12
|
+
* Registers a callback to run just after this store is mounted.
|
|
13
|
+
*/
|
|
14
|
+
onMount(callback: () => void): void;
|
|
15
|
+
/**
|
|
16
|
+
* Registers a callback to run just after this store is unmounted.
|
|
17
|
+
*/
|
|
18
|
+
onUnmount(callback: () => void): void;
|
|
19
|
+
/**
|
|
20
|
+
* Passes a getter function to `callback` that will track reactive states and return their current values.
|
|
21
|
+
* Callback will be run each time a tracked state gets a new value.
|
|
22
|
+
*/
|
|
23
|
+
effect(callback: EffectCallback): UnsubscribeFunction;
|
|
24
|
+
}
|
|
25
|
+
export declare class Store<Options, Value> {
|
|
26
|
+
readonly fn: StoreFunction<Options, Value>;
|
|
27
|
+
private _options;
|
|
28
|
+
/**
|
|
29
|
+
* Value is guaranteed to be set after `attach` is called.
|
|
30
|
+
*/
|
|
31
|
+
value: Value;
|
|
32
|
+
isMounted: boolean;
|
|
33
|
+
elementContext: ElementContext;
|
|
34
|
+
lifecycleListeners: {
|
|
35
|
+
mount: (() => any)[];
|
|
36
|
+
unmount: (() => any)[];
|
|
37
|
+
};
|
|
38
|
+
logger: Logger;
|
|
39
|
+
id: string;
|
|
40
|
+
name: string;
|
|
41
|
+
constructor(fn: StoreFunction<Options, Value>, options: Options);
|
|
42
|
+
/**
|
|
43
|
+
* Attaches this Store to the elementContext.
|
|
44
|
+
* Returns false if there was already an instance attached, and true otherwise.
|
|
45
|
+
*/
|
|
46
|
+
attach(elementContext: ElementContext): boolean;
|
|
47
|
+
handleMount(): void;
|
|
48
|
+
handleUnmount(): void;
|
|
49
|
+
}
|
|
50
|
+
export declare function isStore<Options, Value>(value: any): value is Store<Options, Value>;
|
|
51
|
+
export declare class StoreError extends Error {
|
|
52
|
+
}
|