Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[experiment]: Demo app for glimmer-next renderer #20711

Draft
wants to merge 23 commits into
base: main
Choose a base branch
from
Draft
36 changes: 19 additions & 17 deletions babel.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -6,32 +6,34 @@
test suite.
*/

import { resolve, dirname } from 'node:path';
import { fileURLToPath } from 'node:url';
// import { resolve, dirname } from 'node:path';
// import { fileURLToPath } from 'node:url';

export default {
plugins: [
[
'@babel/plugin-transform-typescript',
{
allowDeclareFields: true,
},
],
// [
// '@babel/plugin-transform-typescript',
// {
// allowDeclareFields: true,
// allExtensions: true,
// onlyRemoveTypeImports: true,
// },
// ],
[
'module:decorator-transforms',
{
runEarly: true,
runtime: { import: 'decorator-transforms/runtime' },
},
],
[
'babel-plugin-ember-template-compilation',
{
compilerPath: resolve(
dirname(fileURLToPath(import.meta.url)),
'./broccoli/glimmer-template-compiler'
),
},
],
// [
// 'babel-plugin-ember-template-compilation',
// {
// compilerPath: resolve(
// dirname(fileURLToPath(import.meta.url)),
// './broccoli/glimmer-template-compiler'
// ),
// },
// ],
],
};
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@
"unlink:all": "node bin/unlink-all.mjs"
},
"dependencies": {
"@lifeart/gxt": "0.0.53",
"@babel/core": "^7.24.4",
"@ember/edition-utils": "^1.2.0",
"@glimmer/compiler": "0.92.0",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
import type { Reference } from '@glimmer/reference';
import { childRefFor, createComputeRef, createPrimitiveRef, valueForRef } from '@glimmer/reference';
import { reifyPositional } from '@glimmer/runtime';
import { EMPTY_ARRAY, unwrapTemplate } from '@glimmer/util';
import { unwrapTemplate } from '@glimmer/utils';

Check failure on line 31 in packages/@ember/-internals/glimmer/lib/component-managers/curly.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Cannot find module '@glimmer/utils' or its corresponding type declarations.

Check failure on line 31 in packages/@ember/-internals/glimmer/lib/component-managers/curly.ts

View workflow job for this annotation

GitHub Actions / Linting

Unable to resolve path to module '@glimmer/utils'
import {
beginTrackFrame,
beginUntrackFrame,
Expand All @@ -54,6 +54,7 @@

export const ARGS = enumerableSymbol('ARGS');
export const HAS_BLOCK = enumerableSymbol('HAS_BLOCK');
const EMPTY_ARRAY = [];

Check failure on line 57 in packages/@ember/-internals/glimmer/lib/component-managers/curly.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Variable 'EMPTY_ARRAY' implicitly has type 'any[]' in some locations where its type cannot be determined.

Check failure on line 57 in packages/@ember/-internals/glimmer/lib/component-managers/curly.ts

View workflow job for this annotation

GitHub Actions / Linting

Delete `·`

export const DIRTY_TAG = Symbol('DIRTY_TAG');
export const IS_DISPATCHING_ATTRS = Symbol('IS_DISPATCHING_ATTRS');
Expand Down Expand Up @@ -232,7 +233,7 @@
return null;
}

return { positional: EMPTY_ARRAY as readonly Reference[], named };

Check failure on line 236 in packages/@ember/-internals/glimmer/lib/component-managers/curly.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Variable 'EMPTY_ARRAY' implicitly has an 'any[]' type.
}

/*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
import { capabilityFlagsFrom } from '@glimmer/manager';
import type { Reference } from '@glimmer/reference';
import { createConstRef, valueForRef } from '@glimmer/reference';
import { unwrapTemplate } from '@glimmer/util';
import { unwrapTemplate } from '@glimmer/utils';

Check failure on line 24 in packages/@ember/-internals/glimmer/lib/component-managers/mount.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Cannot find module '@glimmer/utils' or its corresponding type declarations.

Check failure on line 24 in packages/@ember/-internals/glimmer/lib/component-managers/mount.ts

View workflow job for this annotation

GitHub Actions / Linting

Unable to resolve path to module '@glimmer/utils'
import type RuntimeResolver from '../resolver';

interface EngineState {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
import type { Reference } from '@glimmer/reference';
import { createConstRef, valueForRef } from '@glimmer/reference';
import { EMPTY_ARGS } from '@glimmer/runtime';
import { unwrapTemplate } from '@glimmer/util';
import { unwrapTemplate } from '@glimmer/utils';

Check failure on line 24 in packages/@ember/-internals/glimmer/lib/component-managers/outlet.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Cannot find module '@glimmer/utils' or its corresponding type declarations.

Check failure on line 24 in packages/@ember/-internals/glimmer/lib/component-managers/outlet.ts

View workflow job for this annotation

GitHub Actions / Linting

Unable to resolve path to module '@glimmer/utils'

import type { DynamicScope } from '../renderer';
import type { OutletState } from '../utils/outlet';
Expand Down
13 changes: 12 additions & 1 deletion packages/@ember/-internals/glimmer/lib/components/internal.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,20 @@
} from '@glimmer/interfaces';
import { setComponentTemplate, setInternalComponentManager } from '@glimmer/manager';
import type { Reference } from '@glimmer/reference';
import { createConstRef, isConstRef, valueForRef } from '@glimmer/reference';
import { reference } from '@lifeart/gxt/glimmer-compatibility';

Check failure on line 18 in packages/@ember/-internals/glimmer/lib/components/internal.ts

View workflow job for this annotation

GitHub Actions / Type Checking (current version)

Cannot find module '@lifeart/gxt/glimmer-compatibility' or its corresponding type declarations.

Check failure on line 18 in packages/@ember/-internals/glimmer/lib/components/internal.ts

View workflow job for this annotation

GitHub Actions / Linting

Unable to resolve path to module '@lifeart/gxt/glimmer-compatibility'
// import { createConstRef, isConstRef, valueForRef } from '@glimmer/reference';
import { untrack } from '@glimmer/validator';

const { createConstRef } = reference;
function isConstRef() {
return true;
}
function valueForRef(ref) {
if (!ref) {
debugger;

Check failure on line 28 in packages/@ember/-internals/glimmer/lib/components/internal.ts

View workflow job for this annotation

GitHub Actions / Linting

Unexpected 'debugger' statement
}
return ref.value;
}
function NOOP(): void {}

export type EventListener = (event: Event) => void;
Expand Down
61 changes: 39 additions & 22 deletions packages/@ember/-internals/glimmer/lib/renderer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import { getOwner } from '@ember/-internals/owner';
import { guidFor } from '@ember/-internals/utils';
import { getViewElement, getViewId } from '@ember/-internals/views';
import { destroyElementSync, renderComponent } from '@lifeart/gxt';
import { assert } from '@ember/debug';
import { _backburner, _getCurrentRunLoop } from '@ember/runloop';
import { destroy } from '@glimmer/destroyable';
Expand Down Expand Up @@ -31,14 +32,14 @@
import type { CurriedValue } from '@glimmer/runtime';
import {
clientBuilder,
curry,
// curry,
DOMChanges,
DOMTreeConstruction,
inTransaction,
renderMain,

Check failure on line 39 in packages/@ember/-internals/glimmer/lib/renderer.ts

View workflow job for this annotation

GitHub Actions / Linting

'renderMain' is defined but never used. Allowed unused vars must match /^_/u
runtimeContext,
} from '@glimmer/runtime';
import { unwrapTemplate } from '@glimmer/util';
import { unwrapTemplate } from '@glimmer/utils';

Check failure on line 42 in packages/@ember/-internals/glimmer/lib/renderer.ts

View workflow job for this annotation

GitHub Actions / Linting

Unable to resolve path to module '@glimmer/utils'
import { CURRENT_TAG, validateTag, valueForTag } from '@glimmer/validator';
import type { SimpleDocument, SimpleElement, SimpleNode } from '@simple-dom/interface';
import RSVP from 'rsvp';
Expand All @@ -64,6 +65,23 @@
[BOUNDS]: Bounds | null;
}

function curry(
type: T,
spec: object | string | any,
owner: any,
args: any | null,
resolved = false
) {
console.log('curry');

Check failure on line 75 in packages/@ember/-internals/glimmer/lib/renderer.ts

View workflow job for this annotation

GitHub Actions / Linting

Unexpected console statement
return {
type,
spec,
owner,
args,
resolved,
};
}

export class DynamicScope implements GlimmerDynamicScope {
constructor(public view: View | null, public outletState: Reference<OutletState | undefined>) {}

Expand Down Expand Up @@ -129,13 +147,13 @@
constructor(
public root: Component | OutletView,
public runtime: RuntimeContext,
context: CompileTimeCompilationContext,
_context: CompileTimeCompilationContext,
owner: InternalOwner,
template: Template,
self: Reference<unknown>,
parentElement: SimpleElement,
dynamicScope: DynamicScope,
builder: IBuilder
_dynamicScope: DynamicScope,
_builder: IBuilder
) {
assert(
`You cannot render \`${valueForRef(self)}\` without a template.`,
Expand All @@ -146,23 +164,16 @@
this.result = undefined;
this.destroyed = false;

this.render = errorLoopTransaction(() => {
let layout = unwrapTemplate(template).asLayout();

let iterator = renderMain(
runtime,
context,
owner,
self,
builder(runtime.env, { element: parentElement, nextSibling: null }),
layout,
dynamicScope
);

let result = (this.result = iterator.sync());
// console.log(layout);

// override .render function after initial render
this.render = errorLoopTransaction(() => result.rerender({ alwaysRevalidate: false }));
this.render = errorLoopTransaction(() => {
let layout = unwrapTemplate(template).asLayout().compile();
const layoutInstance = new layout(this);
// @ts-expect-error fine
this.result = renderComponent(layoutInstance, parentElement, owner);
this.render = errorLoopTransaction(() => {
// fine
});
});
}

Expand Down Expand Up @@ -195,7 +206,12 @@

*/

inTransaction(env, () => destroy(result!));
inTransaction(env, () => {
// @ts-expect-error foo-bar
destroyElementSync(result);
// runDestructors(result.ctx);
destroy(result!);
});
}
}
}
Expand Down Expand Up @@ -370,6 +386,7 @@
// renderer HOOKS

appendOutletView(view: OutletView, target: SimpleElement): void {
console.log('appendOutletView', view, target);

Check failure on line 389 in packages/@ember/-internals/glimmer/lib/renderer.ts

View workflow job for this annotation

GitHub Actions / Linting

Unexpected console statement
let definition = createRootOutlet(view);
this._appendDefinition(
view,
Expand Down
9 changes: 4 additions & 5 deletions packages/@ember/-internals/glimmer/lib/templates/empty.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import { precompileTemplate } from '@ember/template-compilation';
export default precompileTemplate('', {
moduleName: 'packages/@ember/-internals/glimmer/lib/templates/empty.hbs',
strictMode: true,
});
import { hbs } from '@lifeart/gxt';
export default function emptyTemplate() {
return hbs``;
};
18 changes: 5 additions & 13 deletions packages/@ember/-internals/glimmer/lib/templates/input.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import { precompileTemplate } from '@ember/template-compilation';
import { on } from '@ember/modifier';
export default precompileTemplate(
`<input
import { hbs } from '@lifeart/gxt';
export default function InputTemplate() {
return hbs`<input
{{!-- for compatibility --}}
id={{this.id}}
class={{this.class}}
Expand All @@ -17,12 +16,5 @@ export default precompileTemplate(
{{on "keyup" this.keyUp}}
{{on "paste" this.valueDidChange}}
{{on "cut" this.valueDidChange}}
/>`,
{
moduleName: 'packages/@ember/-internals/glimmer/lib/templates/input.hbs',
strictMode: true,
scope() {
return { on };
},
}
);
/>`;
}
41 changes: 16 additions & 25 deletions packages/@ember/-internals/glimmer/lib/templates/link-to.ts
Original file line number Diff line number Diff line change
@@ -1,30 +1,21 @@
import { precompileTemplate } from '@ember/template-compilation';
import { on } from '@ember/modifier';
import { hbs } from '@lifeart/gxt';

export default precompileTemplate(
`<a
{{!-- for compatibility --}}
id={{this.id}}
class={{this.class}}
export default function LinkToTemplate() {
return hbs`<a
{{!-- for compatibility --}}
id={{this.id}}
class={{this.class}}

{{!-- deprecated attribute bindings --}}
role={{this.role}}
title={{this.title}}
rel={{this.rel}}
tabindex={{this.tabindex}}
target={{this.target}}
{{!-- deprecated attribute bindings --}}
role={{this.role}}
title={{this.title}}
rel={{this.rel}}
tabindex={{this.tabindex}}
target={{this.target}}

...attributes
...attributes

href={{this.href}}
href={{this.href}}

{{on 'click' this.click}}
>{{yield}}</a>`,
{
moduleName: 'packages/@ember/-internals/glimmer/lib/templates/link-to.hbs',
strictMode: true,
scope() {
return { on };
},
}
);
{{on 'click' this.click}} >{{yield}}</a>`;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import { Component, cell } from '@lifeart/gxt';

interface State {
outlets: {
main: State | undefined,
},
render: {
template(): () => unknown,
controller: unknown,
name: string,
}
}

export default class OutletHelper extends Component {
get state() {
let state = this.args.state();
if (typeof state === 'function') {
state = state();
}
return state.outlets.main || state;
}
get nextState() {
return () => {
return this.hasNext;
}
}
get hasNext() {
return this.state.outlets.main;
}
get canRender() {
return !!this?.state?.render;
}
get MyComponent() {

const state = this.state;
const render = state.render;
const tpl = render.template();
if (tpl.instance) {
tpl.renderCell.update(render.model);
return tpl.instance.template;
}
const renderCell = cell(render.model);
// console.log('render.model', render.model);
const args = {
get model() {
return renderCell.value;
}
}

render.controller['args'] = args;
// render.controller.model = render.model;
const tplComponentInstance = new tpl(args);
tplComponentInstance.template = tplComponentInstance.template.bind(render.controller);
// we need to provide stable refs here to avoid re-renders
tpl.instance = tplComponentInstance;
tpl.renderCell = renderCell;
return tplComponentInstance.template;
}
get model() {
const state = this.state;
const render = state.render;
console.log('getModel', render.model);
return render.model;
}
<template>
{{#if this.canRender}}
<this.MyComponent @model={{this.model}}>
{{#if this.hasNext}}
<OutletHelper @state={{this.nextState}} @root={{false}} />
{{/if}}
</this.MyComponent>

{{/if}}
</template>
}
Loading
Loading