Skip to content
This repository has been archived by the owner on Jan 30, 2025. It is now read-only.

feat: context dom #114

Merged
merged 2 commits into from
Dec 10, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
64 changes: 32 additions & 32 deletions .sizes.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,81 +7,81 @@
{
"name": "*",
"total": {
"min": 11419,
"gzip": 4891,
"brotli": 4454
"min": 12006,
"gzip": 5073,
"brotli": 4630
}
},
{
"name": "counter",
"user": {
"min": 370,
"gzip": 275,
"gzip": 277,
"brotli": 245
},
"runtime": {
"min": 3140,
"gzip": 1455,
"brotli": 1307
"min": 3141,
"gzip": 1458,
"brotli": 1308
},
"total": {
"min": 3510,
"gzip": 1730,
"brotli": 1552
"min": 3511,
"gzip": 1735,
"brotli": 1553
}
},
{
"name": "counter 💧",
"user": {
"min": 229,
"gzip": 195,
"brotli": 170
"gzip": 193,
"brotli": 178
},
"runtime": {
"min": 2502,
"gzip": 1282,
"brotli": 1138
"brotli": 1150
},
"total": {
"min": 2731,
"gzip": 1477,
"brotli": 1308
"gzip": 1475,
"brotli": 1328
}
},
{
"name": "comments",
"user": {
"min": 1142,
"gzip": 700,
"brotli": 634
"gzip": 702,
"brotli": 636
},
"runtime": {
"min": 6841,
"gzip": 3123,
"brotli": 2837
"min": 6931,
"gzip": 3151,
"brotli": 2874
},
"total": {
"min": 7983,
"gzip": 3823,
"brotli": 3471
"min": 8073,
"gzip": 3853,
"brotli": 3510
}
},
{
"name": "comments 💧",
"user": {
"min": 315,
"gzip": 243,
"brotli": 230
"min": 310,
"gzip": 241,
"brotli": 225
},
"runtime": {
"min": 7685,
"gzip": 3513,
"brotli": 3189
"min": 7776,
"gzip": 3539,
"brotli": 3222
},
"total": {
"min": 8000,
"gzip": 3756,
"brotli": 3419
"min": 8086,
"gzip": 3780,
"brotli": 3447
}
}
]
Expand Down
3 changes: 3 additions & 0 deletions packages/runtime/src/common/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ export type HydrateInstance = [
number // offset
];

export type ScopeContext = Record<string, [Scope, number | string]>;

export type Scope<
T extends { [x: string | number]: unknown } = {
[x: string | number]: unknown;
Expand All @@ -23,6 +25,7 @@ export type Scope<
___client: boolean;
___boundSignals: Map<Signal, Signal> | undefined;
___renderer: ClientRenderer | undefined;
___context: ScopeContext | undefined;
_: Scope | undefined;
[x: string | number]: any;
} & T;
Expand Down
9 changes: 5 additions & 4 deletions packages/runtime/src/dom/control-flow.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import type { Scope } from "../common/types";
import type { Context } from "../common/context";
import { reconcile } from "./reconcile";
import { Renderer, createScopeWithRenderer } from "./renderer";
import { getEmptyScope, destroyScope } from "./scope";
Expand Down Expand Up @@ -88,7 +87,8 @@ export function setConditionalRenderer<ChildScope extends Scope>(
newScope = scope[conditionalIndex + ConditionalIndex.SCOPE] =
createScopeWithRenderer(
newRenderer,
scope[conditionalIndex + ConditionalIndex.CONTEXT] as typeof Context,
(scope[conditionalIndex + ConditionalIndex.CONTEXT] ||=
scope.___context),
scope
) as ChildScope;
prevScope =
Expand Down Expand Up @@ -127,7 +127,8 @@ export function setConditionalRendererOnlyChild(
const newScope = (scope[conditionalIndex + ConditionalIndex.SCOPE] =
createScopeWithRenderer(
newRenderer,
scope[conditionalIndex + ConditionalIndex.CONTEXT] as typeof Context,
(scope[conditionalIndex + ConditionalIndex.CONTEXT] ||=
scope.___context),
scope
));
fragment.___insertBefore(newScope, referenceNode, null);
Expand Down Expand Up @@ -240,7 +241,7 @@ export function setLoopOf<T, ChildScope extends Scope>(
if (!childScope) {
childScope = createScopeWithRenderer(
renderer,
scope[loopIndex + LoopIndex.CONTEXT] as typeof Context,
(scope[loopIndex + LoopIndex.CONTEXT] ||= scope.___context),
scope
) as ChildScope;
// TODO: once we can track moves
Expand Down
8 changes: 7 additions & 1 deletion packages/runtime/src/dom/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,11 @@ export { write, bind, bindRenderer } from "./scope";

export type { Scope } from "../common/types";

export { createRenderer, createRenderFn } from "./renderer";
export {
createRenderer,
createRenderFn,
initContextProvider,
} from "./renderer";

export {
setSource,
Expand All @@ -48,4 +52,6 @@ export {
closure,
dynamicClosure,
dynamicSubscribers,
contextClosure,
inChildMany,
} from "./signals";
45 changes: 36 additions & 9 deletions packages/runtime/src/dom/renderer.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import type { Scope } from "../common/types";
import type { Scope, ScopeContext } from "../common/types";
import type { Signal } from "./signals";
import { createScope } from "./scope";
import { Context, setContext } from "../common/context";
import { setContext } from "../common/context";
import { WalkCodes, walk, trimWalkString } from "./walker";
import { queueHydrate, runHydrate } from "./queue";
import { DOMFragment, singleNodeFragment } from "./fragment";

const enum NodeType {
Element = 1,
Expand Down Expand Up @@ -35,20 +36,46 @@ type RenderResult<I extends Input> = {

export function createScopeWithRenderer<S extends Scope = Scope>(
renderer: Renderer<S>,
context: typeof Context,
context: ScopeContext,
ownerScope?: Scope
) {
setContext(context);
const newScope = createScope(renderer.___owner || ownerScope) as S;
const newScope = createScope(context as ScopeContext) as S;
newScope._ = renderer.___owner || ownerScope;
newScope.___renderer = renderer as Renderer;
initRenderer<S>(renderer, newScope);
for (const signal of renderer.___closureSignals) {
signal.___subscribe?.(newScope);
}
newScope.___renderer = renderer as Renderer;
initRenderer<S>(renderer, newScope);
setContext(null);
return newScope;
}

export function initContextProvider(
scope: Scope,
scopeAccessor: number,
valueAccessor: number,
contextKey: string,
renderer: Renderer,
fragment: DOMFragment = singleNodeFragment
) {
const node: Node = scope[scopeAccessor];
const newScope = createScopeWithRenderer(
renderer,
{
...scope.___context,
[contextKey]: [scope, valueAccessor],
},
scope
);

fragment.___insertBefore(newScope, node.parentNode!, node.nextSibling);

for (const signal of renderer.___closureSignals) {
signal.___notify(newScope, true);
}
}

export function initRenderer<S extends Scope = Scope>(
renderer: Renderer<S>,
scope: S
Expand Down Expand Up @@ -86,16 +113,16 @@ export function createRenderFn<I extends Input, S extends Scope>(
walks: string,
setup?: SetupFn<S>,
attrs?: Signal,
hasUserEffects?: 0 | 1,
closureSignals?: Signal[],
dynamicStartNodeOffset?: number,
dynamicEndNodeOffset?: number
) {
const renderer = createRenderer<S>(
template,
walks,
setup,
[],
hasUserEffects,
closureSignals,
0,
dynamicStartNodeOffset,
dynamicEndNodeOffset
);
Expand Down
6 changes: 3 additions & 3 deletions packages/runtime/src/dom/scope.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import { queueHydrate } from "./queue";
import type { Scope } from "../common/types";
import type { Scope, ScopeContext } from "../common/types";
import type { Renderer } from "./renderer";
import { Signal, wrapSignal } from "./signals";

export function createScope(owner?: Scope): Scope {
export function createScope(context?: ScopeContext): Scope {
const scope = {} as Scope;
scope.___client = true;
scope._ = owner;
scope.___context = context;
return scope;
}

Expand Down
Loading