diff --git a/modules/benchmarks/src/largetable/render3/table.ts b/modules/benchmarks/src/largetable/render3/table.ts index f7efd084370f3..5e62f6dca179c 100644 --- a/modules/benchmarks/src/largetable/render3/table.ts +++ b/modules/benchmarks/src/largetable/render3/table.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {ɵC as C, ɵE as E, ɵT as T, ɵV as V, ɵb as b, ɵc as c, ɵcR as cR, ɵcr as cr, ɵdefineComponent as defineComponent, ɵdetectChanges as detectChanges, ɵe as e, ɵs as s, ɵt as t, ɵv as v} from '@angular/core'; +import {ɵC as C, ɵE as E, ɵT as T, ɵV as V, ɵb as b, ɵcR as cR, ɵcr as cr, ɵdefineComponent as defineComponent, ɵdetectChanges as detectChanges, ɵe as e, ɵs as s, ɵt as t, ɵv as v} from '@angular/core'; import {ComponentDef} from '@angular/core/src/render3/interfaces/definition'; import {TableCell, buildTable, emptyTable} from '../util'; @@ -16,17 +16,13 @@ export class LargeTableComponent { /** @nocollapse */ static ngComponentDef: ComponentDef = defineComponent({ - type: LargeTableComponent, tag: 'largetable', template: function(ctx: LargeTableComponent, cm: boolean) { if (cm) { E(0, 'table'); { E(1, 'tbody'); - { - C(2); - c(); - } + { C(2); } e(); } e(); @@ -39,7 +35,6 @@ export class LargeTableComponent { if (cm1) { E(0, 'tr'); C(1); - c(); e(); } cR(1); diff --git a/modules/benchmarks/src/tree/render3/tree.ts b/modules/benchmarks/src/tree/render3/tree.ts index 71cead278a3e5..78d4611190b86 100644 --- a/modules/benchmarks/src/tree/render3/tree.ts +++ b/modules/benchmarks/src/tree/render3/tree.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {ɵC as C, ɵD as D, ɵE as E, ɵT as T, ɵV as V, ɵb as b, ɵb1 as b1, ɵc as c, ɵcR as cR, ɵcr as cr, ɵdefineComponent as defineComponent, ɵdetectChanges as _detectChanges, ɵe as e, ɵp as p, ɵs as s, ɵt as t, ɵv as v} from '@angular/core'; +import {ɵC as C, ɵD as D, ɵE as E, ɵT as T, ɵV as V, ɵb as b, ɵb1 as b1, ɵcR as cR, ɵcr as cr, ɵdefineComponent as defineComponent, ɵdetectChanges as _detectChanges, ɵe as e, ɵp as p, ɵs as s, ɵt as t, ɵv as v} from '@angular/core'; import {ComponentDef} from '@angular/core/src/render3/interfaces/definition'; import {TreeNode, buildTree, emptyTree} from '../util'; @@ -36,7 +36,6 @@ export class TreeComponent { /** @nocollapse */ static ngComponentDef: ComponentDef = defineComponent({ - type: TreeComponent, tag: 'tree', template: function(ctx: TreeComponent, cm: boolean) { if (cm) { @@ -44,9 +43,7 @@ export class TreeComponent { { T(1); } e(); C(2); - c(); C(3); - c(); } s(0, 'background-color', b(ctx.data.depth % 2 ? '' : 'grey')); t(1, b1(' ', ctx.data.value, ' ')); @@ -56,8 +53,7 @@ export class TreeComponent { let cm0 = V(0); { if (cm0) { - E(0, TreeComponent.ngComponentDef); - { D(1, TreeComponent.ngComponentDef.n(), TreeComponent.ngComponentDef); } + E(0, TreeComponent); e(); } p(0, 'data', b(ctx.data.left)); @@ -74,8 +70,7 @@ export class TreeComponent { let cm0 = V(0); { if (cm0) { - E(0, TreeComponent.ngComponentDef); - { D(1, TreeComponent.ngComponentDef.n(), TreeComponent.ngComponentDef); } + E(0, TreeComponent); e(); } p(0, 'data', b(ctx.data.right)); @@ -97,7 +92,6 @@ export class TreeFunction extends TreeComponent { /** @nocollapse */ static ngComponentDef: ComponentDef = defineComponent({ - type: TreeFunction, tag: 'tree', template: function(ctx: TreeFunction, cm: boolean) { // bit of a hack @@ -114,9 +108,7 @@ export function TreeTpl(ctx: TreeNode, cm: boolean) { { T(1); } e(); C(2); - c(); C(3); - c(); } s(0, 'background-color', b(ctx.depth % 2 ? '' : 'grey')); t(1, b1(' ', ctx.value, ' ')); diff --git a/packages/core/src/core_render3_private_export.ts b/packages/core/src/core_render3_private_export.ts index 42daa7c96ccb9..a8b619c516626 100644 --- a/packages/core/src/core_render3_private_export.ts +++ b/packages/core/src/core_render3_private_export.ts @@ -18,7 +18,6 @@ export { V as ɵV, b as ɵb, b1 as ɵb1, - c as ɵc, cR as ɵcR, cr as ɵcr, e as ɵe, diff --git a/packages/core/src/render3/assert.ts b/packages/core/src/render3/assert.ts index 0c30b7cec952a..b90245f85ad11 100644 --- a/packages/core/src/render3/assert.ts +++ b/packages/core/src/render3/assert.ts @@ -21,7 +21,10 @@ * @returns The stringified value */ function stringifyValueForError(value: any): string { - return typeof value === 'string' ? `"${value}"` : '' + value; + if (value && value.native && value.native.outerHTML) { + return value.native.outerHTML; + } + return typeof value === 'string' ? `"${value}"` : value; } export function assertNumber(actual: any, name: string) { @@ -57,6 +60,8 @@ export function assertNotEqual(actual: T, expected: T, name: string) { export function assertThrow( actual: T, expected: T, name: string, operator: string, serializer: ((v: T) => string) = stringifyValueForError): never { - throw new Error( - `ASSERT: expected ${name} ${operator} ${serializer(expected)} but was ${serializer(actual)}!`); + const error = + `ASSERT: expected ${name} ${operator} ${serializer(expected)} but was ${serializer(actual)}!`; + debugger; // leave `debugger` here to aid in debugging. + throw new Error(error); } diff --git a/packages/core/src/render3/component.ts b/packages/core/src/render3/component.ts index e9a1b85a9a6be..f9e18c739e935 100644 --- a/packages/core/src/render3/component.ts +++ b/packages/core/src/render3/component.ts @@ -13,10 +13,10 @@ import {ComponentRef as viewEngine_ComponentRef} from '../linker/component_facto import {EmbeddedViewRef as viewEngine_EmbeddedViewRef} from '../linker/view_ref'; import {assertNotNull} from './assert'; -import {NG_HOST_SYMBOL, createError, createLView, directive, enterView, hostElement, leaveView, locateHostElement, renderComponentOrTemplate} from './instructions'; -import {ComponentDef, ComponentType} from './interfaces/definition'; +import {NG_HOST_SYMBOL, createError, createLView, directive, directiveCreate, enterView, hostElement, leaveView, locateHostElement, renderComponentOrTemplate} from './instructions'; +import {ComponentDef, ComponentType, TypedComponentDef} from './interfaces/definition'; import {LElementNode} from './interfaces/node'; -import {RElement, RendererFactory3, domRendererFactory3} from './interfaces/renderer'; +import {RElement, Renderer3, RendererFactory3, domRendererFactory3} from './interfaces/renderer'; import {notImplemented, stringify} from './util'; @@ -166,7 +166,8 @@ export const NULL_INJECTOR: Injector = { export function renderComponent( componentType: ComponentType, opts: CreateComponentOptions = {}): T { const rendererFactory = opts.rendererFactory || domRendererFactory3; - const componentDef = componentType.ngComponentDef; + const componentDef = componentType.ngComponentDef as TypedComponentDef; + if (componentDef.type != componentType) componentDef.type = componentType; let component: T; const hostNode = locateHostElement(rendererFactory, opts.host || componentDef.tag); const oldView = enterView( @@ -176,7 +177,7 @@ export function renderComponent( // Create element node at index 0 in data array hostElement(hostNode, componentDef); // Create directive instance with n() and store at index 1 in data array (el is 0) - component = directive(1, componentDef.n(), componentDef); + component = directiveCreate(1, componentDef.n(), componentDef); } finally { leaveView(oldView); } diff --git a/packages/core/src/render3/definition.ts b/packages/core/src/render3/definition.ts index 74563c93da068..13ea394cfd88a 100644 --- a/packages/core/src/render3/definition.ts +++ b/packages/core/src/render3/definition.ts @@ -32,7 +32,6 @@ import {ComponentDef, ComponentDefArgs, DirectiveDef, DirectiveDefArgs} from './ */ export function defineComponent(componentDefinition: ComponentDefArgs): ComponentDef { const def = >{ - type: componentDefinition.type, diPublic: null, n: componentDefinition.factory, tag: (componentDefinition as ComponentDefArgs).tag || null !, @@ -44,6 +43,7 @@ export function defineComponent(componentDefinition: ComponentDefArgs): Co outputs: invertObject(componentDefinition.outputs), methods: invertObject(componentDefinition.methods), rendererType: resolveRendererType2(componentDefinition.rendererType) || null, + exportAs: componentDefinition.exportAs, }; const feature = componentDefinition.features; feature && feature.forEach((fn) => fn(def)); diff --git a/packages/core/src/render3/di.ts b/packages/core/src/render3/di.ts index d233c10231ade..759dbef3d2f18 100644 --- a/packages/core/src/render3/di.ts +++ b/packages/core/src/render3/di.ts @@ -17,7 +17,7 @@ import {ViewContainerRef as viewEngine_ViewContainerRef} from '../linker/view_co import {EmbeddedViewRef as viewEngine_EmbeddedViewRef, ViewRef as viewEngine_ViewRef} from '../linker/view_ref'; import {Type} from '../type'; -import {ComponentTemplate, DirectiveDef} from './interfaces/definition'; +import {ComponentTemplate, DirectiveDef, TypedDirectiveDef} from './interfaces/definition'; import {LInjector} from './interfaces/injector'; import {LContainerNode, LElementNode, LNodeFlags} from './interfaces/node'; import {assertNodeType} from './node_assert'; @@ -147,7 +147,7 @@ function createInjectionError(text: string, token: any) { * @param di The node injector in which a directive will be added * @param def The definition of the directive to be made public */ -export function diPublicInInjector(di: LInjector, def: DirectiveDef): void { +export function diPublicInInjector(di: LInjector, def: TypedDirectiveDef): void { bloomAdd(di, def.type); } @@ -211,7 +211,7 @@ export function getOrCreateInjectable(di: LInjector, token: Type, flags?: for (let i = start, ii = start + size; i < ii; i++) { // Get the definition for the directive at this index and, if it is injectable (diPublic), // and matches the given token, return the directive instance. - const directiveDef = ngStaticData[i] as DirectiveDef; + const directiveDef = ngStaticData[i] as TypedDirectiveDef; if (directiveDef.diPublic && directiveDef.type == token) { return node.view.data[i]; } diff --git a/packages/core/src/render3/index.ts b/packages/core/src/render3/index.ts index bec2d6bef0d9c..3317d3d2a5649 100644 --- a/packages/core/src/render3/index.ts +++ b/packages/core/src/render3/index.ts @@ -39,8 +39,7 @@ export { componentRefresh as r, - containerStart as C, - containerEnd as c, + container as C, containerRefreshStart as cR, containerRefreshEnd as cr, @@ -84,3 +83,4 @@ export { defineDirective, }; export {createComponentRef, detectChanges, getHostElement, markDirty, renderComponent}; +export {InjectFlags} from './di'; \ No newline at end of file diff --git a/packages/core/src/render3/instructions.ts b/packages/core/src/render3/instructions.ts index f425d00d27112..925976ba02bd4 100644 --- a/packages/core/src/render3/instructions.ts +++ b/packages/core/src/render3/instructions.ts @@ -24,7 +24,7 @@ import {LContainerNode, LElementNode, LNode, LNodeFlags, LProjectionNode, LTextN import {assertNodeType} from './node_assert'; import {appendChild, insertChild, insertView, processProjectedNode, removeView} from './node_manipulation'; import {isNodeMatchingSelector} from './node_selector_matcher'; -import {ComponentDef, ComponentTemplate, ComponentType, DirectiveDef} from './interfaces/definition'; +import {ComponentDef, ComponentTemplate, ComponentType, DirectiveDef, DirectiveType, TypedDirectiveDef, TypedComponentDef} from './interfaces/definition'; import {InjectFlags, diPublicInInjector, getOrCreateNodeInjectorForNode, getOrCreateElementRef, getOrCreateTemplateRef, getOrCreateContainerRef, getOrCreateInjectable} from './di'; import {QueryList, LQuery_} from './query'; import {RComment, RElement, RText, Renderer3, RendererFactory3, ProceduralRenderer3, ObjectOrientedRenderer3, RendererStyleFlags3} from './interfaces/renderer'; @@ -343,7 +343,7 @@ export function getOrCreateNodeInjector(): LInjector { * * @param def The definition of the directive to be made public */ -export function diPublic(def: DirectiveDef): void { +export function diPublic(def: TypedDirectiveDef): void { diPublicInInjector(getOrCreateNodeInjector(), def); } @@ -411,29 +411,37 @@ export function injectViewContainerRef(): ViewContainerRef { * Create DOM element. The instruction must later be followed by `elementEnd()` call. * * @param index Index of the element in the data array - * @param nameOrComponentDef Name of the DOM Node or `ComponentDef`. + * @param nameOrComponentType Name of the DOM Node or `ComponentType` to create. * @param attrs Statically bound set of attributes to be written into the DOM element on creation. - * @param localName A name under which a given element is exported. + * @param directiveTypes A set of directives declared on this element. + * @param localRefs A set of local reference bindings on the element. * - * Attributes are passed as an array of strings where elements with an even index hold an attribute - * name and elements with an odd index hold an attribute value, ex.: + * Attributes and localRefs are passed as an array of strings where elements with an even index + * hold an attribute name and elements with an odd index hold an attribute value, ex.: * ['id', 'warning5', 'class', 'alert'] */ export function elementStart( - index: number, nameOrComponentDef?: string | ComponentDef, attrs?: string[] | null, - localName?: string): RElement { + index: number, nameOrComponentType?: string | ComponentType, attrs?: string[] | null, + directiveTypes?: DirectiveType[] | null, localRefs?: string[] | null): RElement { let node: LElementNode; let native: RElement; - if (nameOrComponentDef == null) { + if (nameOrComponentType == null) { // native node retrieval - used for exporting elements as tpl local variables (
) const node = data[index] !; native = node && (node as LElementNode).native; } else { ngDevMode && assertEqual(currentView.bindingStartIndex, null, 'bindingStartIndex'); - const isHostElement = typeof nameOrComponentDef !== 'string'; - const name = isHostElement ? (nameOrComponentDef as ComponentDef).tag : - nameOrComponentDef as string; + const isHostElement = typeof nameOrComponentType !== 'string'; + // MEGAMORPHIC: `ngComponentDef` is a megamorphic property access here. + // This is OK, since we will refactor this code and store the result in `TView.data` + // which means that we will be reading this value only once. We are trading clean/simple + // template + // code for slight startup(first run) performance. (No impact on subsequent runs) + // TODO(misko): refactor this to store the `ComponentDef` in `TView.data`. + const hostComponentDef = + isHostElement ? (nameOrComponentType as ComponentType).ngComponentDef : null; + const name = isHostElement ? hostComponentDef !.tag : nameOrComponentType as string; if (name === null) { // TODO: future support for nameless components. throw 'for now name is required'; @@ -442,10 +450,9 @@ export function elementStart( let componentView: LView|null = null; if (isHostElement) { - const ngStaticData = getTemplateStatic((nameOrComponentDef as ComponentDef).template); + const ngStaticData = getTemplateStatic(hostComponentDef !.template); componentView = addToViewTree(createLView( - -1, rendererFactory.createRenderer( - native, (nameOrComponentDef as ComponentDef).rendererType), + -1, rendererFactory.createRenderer(native, hostComponentDef !.rendererType), ngStaticData)); } @@ -453,19 +460,77 @@ export function elementStart( // accessed through their containers because they may be removed / re-added later. node = createLNode(index, LNodeFlags.Element, native, componentView); + // TODO(misko): implement code which caches the local reference resolution + const queryName: string|null = hack_findQueryName(hostComponentDef, localRefs, ''); + if (node.tNode == null) { ngDevMode && assertDataInRange(index - 1); node.tNode = ngStaticData[index] = - createTNode(name, attrs || null, null, localName || null); + createTNode(name, attrs || null, null, hostComponentDef ? null : queryName); } if (attrs) setUpAttributes(native, attrs); appendChild(node.parent !, native, currentView); + + if (hostComponentDef) { + // TODO(mhevery): This assumes that the directives come in correct order, which + // is not guaranteed. Must be refactored to take it into account. + (hostComponentDef as TypedComponentDef).type = + nameOrComponentType as ComponentType; + directiveCreate(++index, hostComponentDef.n(), hostComponentDef, queryName); + } + hack_declareDirectives(index, directiveTypes, localRefs); } } return native; } +/** + * This function instantiates a directive with a correct queryName. It is a hack since we should + * compute the query value only once and store it with the template (rather than on each invocation) + */ +function hack_declareDirectives( + index: number, directiveTypes: DirectiveType[] | null | undefined, + localRefs: string[] | null | undefined, ) { + if (directiveTypes) { + // TODO(mhevery): This assumes that the directives come in correct order, which + // is not guaranteed. Must be refactored to take it into account. + for (let i = 0; i < directiveTypes.length; i++) { + // MEGAMORPHIC: `ngDirectiveDef` is a megamorphic property access here. + // This is OK, since we will refactor this code and store the result in `TView.data` + // which means that we will be reading this value only once. We are trading clean/simple + // template + // code for slight startup(first run) performance. (No impact on subsequent runs) + // TODO(misko): refactor this to store the `DirectiveDef` in `TView.data`. + const directiveType = directiveTypes[i]; + const directiveDef = directiveType.ngDirectiveDef; + (directiveDef as TypedDirectiveDef).type = directiveType; + directiveCreate( + ++index, directiveDef.n(), directiveDef, hack_findQueryName(directiveDef, localRefs)); + } + } +} + +/** + * This function returns the queryName for a directive. It is a hack since we should + * compute the query value only once and store it with the template (rather than on each invocation) + */ +function hack_findQueryName( + directiveDef: DirectiveDef| null, localRefs: string[] | null | undefined, + defaultExport?: string, ): string|null { + const exportAs = directiveDef && directiveDef.exportAs || defaultExport; + if (exportAs != null && localRefs) { + for (let i = 0; i < localRefs.length; i = i + 2) { + const local = localRefs[i]; + const toExportAs = localRefs[i | 1]; + if (toExportAs === exportAs || toExportAs === defaultExport) { + return local; + } + } + } + return null; +} + /** * Gets static data from a template function or creates a new static * data array if it doesn't already exist. @@ -836,7 +901,21 @@ export function textBinding(index: number, value: T | NO_CHANGE): void { ////////////////////////// /** - * Create or retrieve the directive. + * Retrieve a directive. + * + * NOTE: directives can be created in order other than the index order. They can also + * be retrieved before they are created in which case the value will be null. + * + * @param index Each directive in a `View` will have a unique index. Directives can + * be created or retrieved out of order. + */ +export function directive(index: number): T { + ngDevMode && assertDataInRange(index); + return data[index]; +} + +/** + * Create a directive. * * NOTE: directives can be created in order other than the index order. They can also * be retrieved before they are created in which case the value will be null. @@ -845,56 +924,46 @@ export function textBinding(index: number, value: T | NO_CHANGE): void { * be created or retrieved out of order. * @param directive The directive instance. * @param directiveDef DirectiveDef object which contains information about the template. + * @param queryName Name under which the query can retrieve the directive instance. */ -export function directive(index: number): T; -export function directive( - index: number, directive: T, directiveDef: DirectiveDef, localName?: string): T; -export function directive( - index: number, directive?: T, directiveDef?: DirectiveDef, localName?: string): T { +export function directiveCreate( + index: number, directive: T, directiveDef: DirectiveDef, queryName?: string | null): T { let instance; - if (directive == null) { - // return existing - ngDevMode && assertDataInRange(index); - instance = data[index]; + ngDevMode && assertEqual(currentView.bindingStartIndex, null, 'bindingStartIndex'); + ngDevMode && assertPreviousIsParent(); + let flags = previousOrParentNode !.flags; + let size = flags & LNodeFlags.SIZE_MASK; + if (size === 0) { + flags = (index << LNodeFlags.INDX_SHIFT) | LNodeFlags.SIZE_SKIP | flags & LNodeFlags.TYPE_MASK; } else { - ngDevMode && assertEqual(currentView.bindingStartIndex, null, 'bindingStartIndex'); - ngDevMode && assertPreviousIsParent(); - let flags = previousOrParentNode !.flags; - let size = flags & LNodeFlags.SIZE_MASK; - if (size === 0) { - flags = - (index << LNodeFlags.INDX_SHIFT) | LNodeFlags.SIZE_SKIP | flags & LNodeFlags.TYPE_MASK; - } else { - flags += LNodeFlags.SIZE_SKIP; - } - previousOrParentNode !.flags = flags; - - ngDevMode && assertDataInRange(index - 1); - Object.defineProperty( - directive, NG_HOST_SYMBOL, {enumerable: false, value: previousOrParentNode}); + flags += LNodeFlags.SIZE_SKIP; + } + previousOrParentNode !.flags = flags; - data[index] = instance = directive; + ngDevMode && assertDataInRange(index - 1); + Object.defineProperty( + directive, NG_HOST_SYMBOL, {enumerable: false, value: previousOrParentNode}); - if (index >= ngStaticData.length) { - ngStaticData[index] = directiveDef !; - if (localName) { - ngDevMode && assertNotNull(previousOrParentNode.tNode, 'previousOrParentNode.staticData'); - const tNode = previousOrParentNode !.tNode !; - (tNode.localNames || (tNode.localNames = [])).push(localName, index); - } - } + data[index] = instance = directive; - const diPublic = directiveDef !.diPublic; - if (diPublic) { - diPublic(directiveDef !); + if (index >= ngStaticData.length) { + ngStaticData[index] = directiveDef !; + if (queryName) { + ngDevMode && assertNotNull(previousOrParentNode.tNode, 'previousOrParentNode.staticData'); + const nodeStaticData = previousOrParentNode !.tNode !; + (nodeStaticData.localNames || (nodeStaticData.localNames = [])).push(queryName, index); } + } - const tNode: TNode|null = previousOrParentNode.tNode !; - if (tNode && tNode.attrs) { - setInputsFromAttrs(instance, directiveDef !.inputs, tNode); - } + const diPublic = directiveDef !.diPublic; + if (diPublic) { + diPublic(directiveDef !); } + const staticData: TNode|null = previousOrParentNode.tNode !; + if (staticData && staticData.attrs) { + setInputsFromAttrs(instance, directiveDef !.inputs, staticData); + } return instance; } @@ -1039,10 +1108,11 @@ export function executeViewHooks(): void { * @param template Optional inline template * @param tagName The name of the container element, if applicable * @param attrs The attrs attached to the container, if applicable + * @param localRefs A set of local reference bindings on the element. */ -export function containerStart( - index: number, template?: ComponentTemplate, tagName?: string, attrs?: string[], - localName?: string): void { +export function container( + index: number, directiveTypes?: DirectiveType[], template?: ComponentTemplate, + tagName?: string, attrs?: string[], localRefs?: string[] | null): void { ngDevMode && assertEqual(currentView.bindingStartIndex, null, 'bindingStartIndex'); // If the direct parent of the container is a view, its views (including its comment) @@ -1068,22 +1138,18 @@ export function containerStart( }); if (node.tNode == null) { + // TODO(misko): implement queryName caching + const queryName: string|null = hack_findQueryName(null, localRefs, ''); node.tNode = ngStaticData[index] = - createTNode(tagName || null, attrs || null, [], localName || null); + createTNode(tagName || null, attrs || null, [], queryName || null); } // Containers are added to the current view tree instead of their embedded views // because views can be removed and re-inserted. addToViewTree(node.data); -} + hack_declareDirectives(index, directiveTypes, localRefs); -export function containerEnd() { - if (isParent) { - isParent = false; - } else { - ngDevMode && assertHasParent(); - previousOrParentNode = previousOrParentNode.parent !; - } + isParent = false; ngDevMode && assertNodeType(previousOrParentNode, LNodeFlags.Container); const query = previousOrParentNode.query; query && query.addNode(previousOrParentNode); diff --git a/packages/core/src/render3/interfaces/definition.ts b/packages/core/src/render3/interfaces/definition.ts index 296d444a5c5cd..cd5cff3805606 100644 --- a/packages/core/src/render3/interfaces/definition.ts +++ b/packages/core/src/render3/interfaces/definition.ts @@ -28,11 +28,6 @@ export const enum DirectiveDefFlags {ContentQuery = 0b10} * `DirectiveDef` is a compiled version of the Directive used by the renderer instructions. */ export interface DirectiveDef { - /** - * Token representing the directive. Used by DI. - */ - type: Type; - /** Function that makes a directive public to the DI system. */ diPublic: ((def: DirectiveDef) => void)|null; @@ -41,21 +36,26 @@ export interface DirectiveDef { * * The key is minified property name whereas the value is the original unminified name. */ - inputs: {[P in keyof T]: P}; + readonly inputs: {[P in keyof T]: P}; /** * List of outputs which are part of the components public API. * * The key is minified property name whereas the value is the original unminified name.= */ - outputs: {[P in keyof T]: P}; + readonly outputs: {[P in keyof T]: P}; /** * List of methods which are part of the components public API. * * The key is minified property name whereas the value is the original unminified name. */ - methods: {[P in keyof T]: P}; + readonly methods: {[P in keyof T]: P}; + + /** + * Name under which the directive is exported (for use with local references in template) + */ + readonly exportAs: string|null; /** * factory function used to create a new directive instance. @@ -106,31 +106,41 @@ export interface ComponentDef extends DirectiveDef { * * NOTE: only used with component directives. */ - tag: string; + readonly tag: string; /** * The View template of the component. * * NOTE: only used with component directives. */ - template: ComponentTemplate; + readonly template: ComponentTemplate; /** * Renderer type data of the component. * * NOTE: only used with component directives. */ - rendererType: RendererType2|null; + readonly rendererType: RendererType2|null; } +/** + * Private: do not export + */ +export interface TypedDirectiveDef extends DirectiveDef { type: DirectiveType; } + +/** + * Private: do not export + */ +export interface TypedComponentDef extends ComponentDef { type: ComponentType; } + export interface DirectiveDefArgs { - type: Type; factory: () => T; refresh?: (directiveIndex: number, elementIndex: number) => void; inputs?: {[P in keyof T]?: string}; outputs?: {[P in keyof T]?: string}; methods?: {[P in keyof T]?: string}; features?: DirectiveDefFeature[]; + exportAs?: string; } export interface ComponentDefArgs extends DirectiveDefArgs { diff --git a/packages/core/src/render3/query.ts b/packages/core/src/render3/query.ts index 2afc949dd6c9f..b605850be88d0 100644 --- a/packages/core/src/render3/query.ts +++ b/packages/core/src/render3/query.ts @@ -17,13 +17,14 @@ import {Type} from '../type'; import {assertNotNull} from './assert'; import {getOrCreateContainerRef, getOrCreateElementRef, getOrCreateNodeInjectorForNode, getOrCreateTemplateRef} from './di'; -import {DirectiveDef} from './interfaces/definition'; +import {DirectiveDef, TypedDirectiveDef} from './interfaces/definition'; import {LInjector} from './interfaces/injector'; import {LContainerNode, LElementNode, LNode, LNodeFlags, LViewNode, TNode} from './interfaces/node'; import {LQuery, QueryReadType} from './interfaces/query'; import {assertNodeOfPossibleTypes} from './node_assert'; + /** * A predicate which determines if a given element/directive should be included in the query */ @@ -142,7 +143,7 @@ function geIdxOfMatchingDirective(node: LNode, type: Type): number|null { for (let i = flags >> LNodeFlags.INDX_SHIFT, ii = i + ((flags & LNodeFlags.SIZE_MASK) >> LNodeFlags.SIZE_SHIFT); i < ii; i++) { - const def = ngStaticData[i] as DirectiveDef; + const def = ngStaticData[i] as TypedDirectiveDef; if (def.diPublic && def.type === type) { return i; } diff --git a/packages/core/test/render3/basic_perf.ts b/packages/core/test/render3/basic_perf.ts index 43af27250a73e..89a6d2ca35cb5 100644 --- a/packages/core/test/render3/basic_perf.ts +++ b/packages/core/test/render3/basic_perf.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, E, T, V, c, cR, cr, defineComponent, e, v} from '../../src/render3/index'; +import {C, E, T, V, cR, cr, defineComponent, e, v} from '../../src/render3/index'; import {document, renderComponent} from './render_util'; @@ -32,12 +32,10 @@ describe('iv perf test', () => { it(`${iteration}. create ${count} divs in Render3`, () => { class Component { static ngComponentDef = defineComponent({ - type: Component, tag: 'div', template: function Template(ctx: any, cm: any) { if (cm) { C(0); - c(); } cR(0); { diff --git a/packages/core/test/render3/compiler_canonical_spec.ts b/packages/core/test/render3/compiler_canonical_spec.ts new file mode 100644 index 0000000000000..3e589dde3479a --- /dev/null +++ b/packages/core/test/render3/compiler_canonical_spec.ts @@ -0,0 +1,262 @@ +/** + * @license + * Copyright Google Inc. All Rights Reserved. + * + * Use of this source code is governed by an MIT-style license that can be + * found in the LICENSE file at https://angular.io/license + */ + +import {Component, Directive, Injectable, NgModule, Optional, TemplateRef, Type} from '../../src/core'; +import * as r3 from '../../src/render3/index'; + +import {containerEl, renderComponent, requestAnimationFrame, toHtml} from './render_util'; + +/** + * NORMATIVE => /NORMATIVE: Designates what the compiler is expected to generate. + * + * All local variable names are considered non-normative (informative). + */ + +describe('compiler specification', () => { + describe('elements', () => { + it('should translate DOM structure', () => { + @Component({ + selector: 'my-component', + template: `
Hello World!
` + }) + class MyComponent { + // NORMATIVE + static ngComponentDef = r3.defineComponent({ + tag: 'my-component', + factory: () => new MyComponent(), + template: function(ctx: MyComponent, cm: boolean) { + if (cm) { + r3.E(0, 'div', e0_attrs); + r3.T(1, 'Hello '); + r3.E(2, 'b'); + r3.T(3, 'World'); + r3.e(); + r3.T(4, '!'); + r3.e(); + } + } + }); + // /NORMATIVE + } + // Important: keep arrays outside of function to not create new instances. + const e0_attrs = ['class', 'my-app', 'title', 'Hello']; + + expect(renderComp(MyComponent)) + .toEqual('
Hello World!
'); + }); + }); + + describe('components & directives', () => { + it('should instantiate directives', () => { + const log: string[] = []; + @Component({selector: 'child', template: 'child-view'}) + class ChildComponent { + constructor() { log.push('ChildComponent'); } + // NORMATIVE + static ngComponentDef = r3.defineComponent({ + tag: `child`, + factory: () => new ChildComponent(), + template: function(ctx: ChildComponent, cm: boolean) { + if (cm) { + r3.T(0, 'child-view'); + } + } + }); + // /NORMATIVE + } + + @Directive({ + selector: 'some-directive', + }) + class SomeDirective { + constructor() { log.push('SomeDirective'); } + // NORMATIVE + static ngDirectiveDef = r3.defineDirective({ + factory: () => new SomeDirective(), + }); + // /NORMATIVE + } + + @Component({selector: 'my-component', template: `!`}) + class MyComponent { + // NORMATIVE + static ngComponentDef = r3.defineComponent({ + tag: 'my-component', + factory: () => new MyComponent(), + template: function(ctx: MyComponent, cm: boolean) { + if (cm) { + r3.E(0, ChildComponent, e0_attrs, e0_dirs); + r3.e(); + r3.T(3, '!'); + } + ChildComponent.ngComponentDef.r(1, 0); + } + }); + // /NORMATIVE + } + // Important: keep arrays outside of function to not create new instances. + // NORMATIVE + const e0_attrs = ['some-directive', '']; + const e0_dirs = [SomeDirective]; + // /NORMATIVE + + expect(renderComp(MyComponent)).toEqual('child-view!'); + expect(log).toEqual(['ChildComponent', 'SomeDirective']); + }); + + xit('should support structural directives', () => { + const log: string[] = []; + @Directive({ + selector: 'if', + }) + class IfDirective { + constructor(template: TemplateRef) { log.push('ifDirective'); } + // NORMATIVE + static ngDirectiveDef = r3.defineDirective({ + factory: () => new IfDirective(r3.injectTemplateRef()), + }); + // /NORMATIVE + } + + @Component( + {selector: 'my-component', template: `
  • {{salutation}} {{foo}}
`}) + class MyComponent { + salutation = 'Hello'; + // NORMATIVE + static ngComponentDef = r3.defineComponent({ + tag: 'my-component', + factory: () => new MyComponent(), + template: function(ctx: MyComponent, cm: boolean) { + if (cm) { + r3.E(0, 'ul', null, null, e0_locals); + r3.C(2, c1_dirs, C1); + r3.e(); + } + let foo = r3.m(1); + r3.cR(2); + IfDirective.ngDirectiveDef.r(3, 2); + r3.cr(); + + function C1(ctx1: any, cm: boolean) { + if (cm) { + r3.E(0, 'li'); + r3.T(1); + r3.e(); + } + r3.t(1, r3.b2('', ctx.salutation, ' ', foo, '')); + } + } + }); + // /NORMATIVE + } + // Important: keep arrays outside of function to not create new instances. + // NORMATIVE + const e0_locals = ['foo', '']; + const c1_dirs = [IfDirective]; + // /NORMATIVE + + expect(renderComp(MyComponent)).toEqual('child-view!'); + expect(log).toEqual(['ChildComponent', 'SomeDirective']); + }); + }); + + describe('local references', () => { + // TODO(misko): currently disabled until local refs are working + xit('should translate DOM structure', () => { + @Component({selector: 'my-component', template: `Hello {{user.value}}!`}) + class MyComponent { + // NORMATIVE + static ngComponentDef = r3.defineComponent({ + tag: 'my-component', + factory: () => new MyComponent, + template: function(ctx: MyComponent, cm: boolean) { + if (cm) { + r3.E(0, 'input', null, null, ['user', '']); + r3.e(); + r3.T(2); + } + r3.t(2, r3.b1('Hello ', r3.m(1).value, '!')); + } + }); + // NORMATIVE + } + + expect(renderComp(MyComponent)) + .toEqual('
Hello World!
'); + }); + }); + +}); + +xdescribe('NgModule', () => { + interface Injectable { + scope?: /*InjectorDefType*/ any; + factory: Function; + } + + function defineInjectable(opts: Injectable): Injectable { + // This class should be imported from https://github.com/angular/angular/pull/20850 + return opts; + } + function defineInjector(opts: any): any { + // This class should be imported from https://github.com/angular/angular/pull/20850 + return opts; + } + it('should convert module', () => { + @Injectable() + class Toast { + constructor(name: String) {} + // NORMATIVE + static ngInjectableDef = defineInjectable({ + factory: () => new Toast(inject(String)), + }); + // /NORMATIVE + } + + class CommonModule { + // NORMATIVE + static ngInjectorDef = defineInjector({}); + // /NORMATIVE + } + + @NgModule({ + providers: [Toast, {provide: String, useValue: 'Hello'}], + imports: [CommonModule], + }) + class MyModule { + constructor(toast: Toast) {} + // NORMATIVE + static ngInjectorDef = defineInjector({ + factory: () => new MyModule(inject(Toast)), + provider: [ + {provide: Toast, deps: [String]}, // If Toast has matadata generate this line + Toast, // If toast has not metadata generate this line. + {provide: String, useValue: 'Hello'} + ], + imports: [CommonModule] + }); + // /NORMATIVE + } + + @Injectable(/*{MyModule}*/) + class BurntToast { + constructor(@Optional() toast: Toast|null, name: String) {} + // NORMATIVE + static ngInjectableDef = defineInjectable({ + scope: MyModule, + factory: () => new BurntToast(inject(Toast, r3.InjectFlags.Optional), inject(String)), + }); + // /NORMATIVE + } + + }); +}); + +function renderComp(type: r3.ComponentType): string { + return toHtml(renderComponent(type)); +} diff --git a/packages/core/test/render3/component_spec.ts b/packages/core/test/render3/component_spec.ts index 07039a2e969c5..b955864bc3cc9 100644 --- a/packages/core/test/render3/component_spec.ts +++ b/packages/core/test/render3/component_spec.ts @@ -20,7 +20,6 @@ describe('component', () => { increment() { this.count++; } static ngComponentDef = defineComponent({ - type: CounterComponent, tag: 'counter', template: function(ctx: CounterComponent, cm: boolean) { if (cm) { @@ -64,12 +63,10 @@ describe('component', () => { describe('encapsulation', () => { class WrapperComponent { static ngComponentDef = defineComponent({ - type: WrapperComponent, tag: 'wrapper', template: function(ctx: WrapperComponent, cm: boolean) { if (cm) { - E(0, EncapsulatedComponent.ngComponentDef); - { D(1, EncapsulatedComponent.ngComponentDef.n(), EncapsulatedComponent.ngComponentDef); } + E(0, EncapsulatedComponent); e(); } EncapsulatedComponent.ngComponentDef.h(1, 0); @@ -81,13 +78,11 @@ describe('encapsulation', () => { class EncapsulatedComponent { static ngComponentDef = defineComponent({ - type: EncapsulatedComponent, tag: 'encapsulated', template: function(ctx: EncapsulatedComponent, cm: boolean) { if (cm) { T(0, 'foo'); - E(1, LeafComponent.ngComponentDef); - { D(2, LeafComponent.ngComponentDef.n(), LeafComponent.ngComponentDef); } + E(1, LeafComponent); e(); } LeafComponent.ngComponentDef.h(2, 1); @@ -101,7 +96,6 @@ describe('encapsulation', () => { class LeafComponent { static ngComponentDef = defineComponent({ - type: LeafComponent, tag: 'leaf', template: function(ctx: LeafComponent, cm: boolean) { if (cm) { @@ -131,12 +125,10 @@ describe('encapsulation', () => { it('should encapsulate host and children with different attributes', () => { class WrapperComponentWith { static ngComponentDef = defineComponent({ - type: WrapperComponent, tag: 'wrapper', template: function(ctx: WrapperComponentWith, cm: boolean) { if (cm) { - E(0, LeafComponentwith.ngComponentDef); - { D(1, LeafComponentwith.ngComponentDef.n(), LeafComponentwith.ngComponentDef); } + E(0, LeafComponentwith); e(); } LeafComponentwith.ngComponentDef.h(1, 0); @@ -150,7 +142,6 @@ describe('encapsulation', () => { class LeafComponentwith { static ngComponentDef = defineComponent({ - type: LeafComponentwith, tag: 'leaf', template: function(ctx: LeafComponentwith, cm: boolean) { if (cm) { diff --git a/packages/core/test/render3/content_spec.ts b/packages/core/test/render3/content_spec.ts index b7af571faf899..c41b2f498061b 100644 --- a/packages/core/test/render3/content_spec.ts +++ b/packages/core/test/render3/content_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, D, E, P, T, V, c, cR, cr, detectChanges, e, m, pD, v} from '../../src/render3/index'; +import {C, D, E, P, T, V, cR, cr, detectChanges, e, m, pD, v} from '../../src/render3/index'; import {createComponent, renderComponent, toHtml} from './render_util'; @@ -30,11 +30,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); - { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); - T(2, 'content'); - } + E(0, Child); + { T(2, 'content'); } e(); } Child.ngComponentDef.h(1, 0); @@ -53,11 +50,8 @@ describe('content projection', () => { }); const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); - { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); - T(2, 'content'); - } + E(0, Child); + { T(2, 'content'); } e(); } Child.ngComponentDef.h(1, 0); @@ -79,11 +73,8 @@ describe('content projection', () => { const Child = createComponent('child', function(ctx: any, cm: boolean) { if (cm) { m(0, pD()); - E(1, GrandChild.ngComponentDef); - { - D(2, GrandChild.ngComponentDef.n(), GrandChild.ngComponentDef); - P(3, 0); - } + E(1, GrandChild); + { P(3, 0); } e(); GrandChild.ngComponentDef.h(2, 1); GrandChild.ngComponentDef.r(2, 1); @@ -91,9 +82,8 @@ describe('content projection', () => { }); const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'b'); T(3, 'Hello'); e(); @@ -120,12 +110,10 @@ describe('content projection', () => { }); const Parent = createComponent('parent', function(ctx: {value: any}, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); T(2, '('); C(3); - c(); T(4, ')'); } e(); @@ -162,12 +150,8 @@ describe('content projection', () => { }); const Parent = createComponent('parent', function(ctx: {value: any}, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); - { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); - C(2); - c(); - } + E(0, Child); + { C(2); } e(); } cR(2); @@ -206,12 +190,10 @@ describe('content projection', () => { }); const Parent = createComponent('parent', function(ctx: {value: any}, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); T(2, '('); C(3); - c(); T(4, ')'); } e(); @@ -260,10 +242,7 @@ describe('content projection', () => { if (cm) { m(0, pD()); E(1, 'div'); - { - C(2); - c(); - } + { C(2); } e(); } cR(2); @@ -285,9 +264,9 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, childCmptInstance = Child.ngComponentDef.n(), Child.ngComponentDef); + childCmptInstance = D(1); T(2, 'content'); } e(); @@ -318,10 +297,7 @@ describe('content projection', () => { if (cm) { m(0, pD()); E(1, 'div'); - { - C(2); - c(); - } + { C(2); } e(); } cR(2); @@ -341,9 +317,9 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, childCmptInstance = Child.ngComponentDef.n(), Child.ngComponentDef); + childCmptInstance = D(1); T(2, 'content'); } e(); @@ -381,11 +357,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); - { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); - T(2, 'content'); - } + E(0, Child); + { T(2, 'content'); } e(); } Child.ngComponentDef.h(1, 0); @@ -419,10 +392,7 @@ describe('content projection', () => { m(0, pD()); P(1, 0); E(2, 'div'); - { - C(3); - c(); - } + { C(3); } e(); } cR(3); @@ -442,9 +412,9 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, childCmptInstance = Child.ngComponentDef.n(), Child.ngComponentDef); + childCmptInstance = D(1); T(2, 'content'); } e(); @@ -488,9 +458,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span', ['title', 'toFirst']); { T(3, '1'); } e(); @@ -536,9 +505,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span', ['class', 'toFirst']); { T(3, '1'); } e(); @@ -584,9 +552,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span', ['class', 'other toFirst']); { T(3, '1'); } e(); @@ -631,9 +598,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span', ['class', 'toFirst']); { T(3, '1'); } e(); @@ -678,9 +644,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span', ['class', 'toFirst']); { T(3, '1'); } e(); @@ -727,9 +692,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span'); { T(3, '1'); } e(); @@ -780,9 +744,8 @@ describe('content projection', () => { const Child = createComponent('child', function(ctx: any, cm: boolean) { if (cm) { m(0, pD()); - E(1, GrandChild.ngComponentDef); + E(1, GrandChild); { - D(2, GrandChild.ngComponentDef.n(), GrandChild.ngComponentDef); P(3, 0); E(4, 'span'); { T(5, 'in child template'); } @@ -803,9 +766,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); + E(0, Child); { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); E(2, 'span'); { T(3, 'parent content'); } e(); @@ -845,12 +807,8 @@ describe('content projection', () => { */ const Parent = createComponent('parent', function(ctx: {value: any}, cm: boolean) { if (cm) { - E(0, Child.ngComponentDef); - { - D(1, Child.ngComponentDef.n(), Child.ngComponentDef); - C(2, undefined, 'div'); - c(); - } + E(0, Child); + { C(2, undefined, undefined, 'div'); } e(); } cR(2); diff --git a/packages/core/test/render3/control_flow_spec.ts b/packages/core/test/render3/control_flow_spec.ts index 465e7d67dd54a..0a5532cacbaae 100644 --- a/packages/core/test/render3/control_flow_spec.ts +++ b/packages/core/test/render3/control_flow_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, E, T, V, b, c, cR, cr, e, t, v} from '../../src/render3/index'; +import {C, E, T, V, b, cR, cr, e, t, v} from '../../src/render3/index'; import {renderToHtml} from './render_util'; @@ -17,10 +17,7 @@ describe('JS control flow', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'div'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -68,10 +65,7 @@ describe('JS control flow', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'div'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -81,10 +75,7 @@ describe('JS control flow', () => { { if (cm1) { E(0, 'span'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -141,7 +132,6 @@ describe('JS control flow', () => { { T(1, 'hello'); } e(); C(2); - c(); } cR(2); { @@ -150,7 +140,6 @@ describe('JS control flow', () => { { if (cm0) { C(0); - c(); } cR(0); { @@ -185,10 +174,7 @@ describe('JS control flow', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'ul'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -234,10 +220,7 @@ describe('JS control flow', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'ul'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -247,10 +230,7 @@ describe('JS control flow', () => { { if (cm1) { E(0, 'li'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -298,7 +278,6 @@ describe('JS control flow', () => { { T(1, 'Before'); C(2); - c(); T(3, 'After'); } e(); @@ -313,7 +292,6 @@ describe('JS control flow', () => { { T(1); } e(); C(2); - c(); T(3, '-'); } t(1, b(ctx.cafes[i].name)); @@ -380,7 +358,6 @@ describe('JS control flow', () => { { T(1, 'Before'); C(2); - c(); T(3, 'After'); } e(); @@ -395,7 +372,6 @@ describe('JS control flow', () => { { T(1); } e(); C(2); - c(); T(3, '-'); } t(1, b(ctx.cafes[i].name)); @@ -409,7 +385,6 @@ describe('JS control flow', () => { { T(1); } e(); C(2); - c(); } t(1, b(ctx.cafes[i].entrees[j].name)); cR(2); @@ -470,10 +445,7 @@ describe('JS control flow', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'div'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -521,10 +493,7 @@ describe('JS for loop', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'div'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); @@ -580,9 +549,7 @@ describe('function calls', () => { { T(1, 'Before'); C(2); - c(); C(3); - c(); T(4, 'After'); } e(); diff --git a/packages/core/test/render3/di_spec.ts b/packages/core/test/render3/di_spec.ts index 22e41bc35604e..f9fc6005e7293 100644 --- a/packages/core/test/render3/di_spec.ts +++ b/packages/core/test/render3/di_spec.ts @@ -9,7 +9,7 @@ import {ElementRef, TemplateRef, ViewContainerRef} from '@angular/core'; import {bloomAdd, bloomFindPossibleInjector} from '../../src/render3/di'; -import {C, D, E, PublicFeature, T, V, b, b2, c, cR, cr, defineDirective, e, inject, injectElementRef, injectTemplateRef, injectViewContainerRef, t, v} from '../../src/render3/index'; +import {C, D, E, PublicFeature, T, V, b, b2, cR, cr, defineDirective, e, inject, injectElementRef, injectTemplateRef, injectViewContainerRef, t, v} from '../../src/render3/index'; import {createLNode, createLView, enterView, getOrCreateNodeInjector, leaveView} from '../../src/render3/instructions'; import {LInjector} from '../../src/render3/interfaces/injector'; import {LNodeFlags} from '../../src/render3/interfaces/node'; @@ -21,16 +21,13 @@ describe('di', () => { it('should create directive with no deps', () => { class Directive { value: string = 'Created'; + static ngDirectiveDef = defineDirective({factory: () => new Directive}); } - const DirectiveDef = defineDirective({type: Directive, factory: () => new Directive}); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - { - D(1, DirectiveDef.n(), DirectiveDef); - T(2); - } + E(0, 'div', null, [Directive]); + { T(2); } e(); } t(2, b(D(1).value)); @@ -44,36 +41,29 @@ describe('di', () => { it('should create directive with inter view dependencies', () => { class DirectiveA { value: string = 'A'; + static ngDirectiveDef = + defineDirective({factory: () => new DirectiveA, features: [PublicFeature]}); } - const DirectiveADef = defineDirective( - {type: DirectiveA, factory: () => new DirectiveA, features: [PublicFeature]}); class DirectiveB { value: string = 'B'; + static ngDirectiveDef = + defineDirective({factory: () => new DirectiveB, features: [PublicFeature]}); } - const DirectiveBDef = defineDirective( - {type: DirectiveB, factory: () => new DirectiveB, features: [PublicFeature]}); class DirectiveC { value: string; constructor(a: DirectiveA, b: DirectiveB) { this.value = a.value + b.value; } + static ngDirectiveDef = defineDirective( + {factory: () => new DirectiveC(inject(DirectiveA), inject(DirectiveB))}); } - const DirectiveCDef = defineDirective({ - type: DirectiveC, - factory: () => new DirectiveC(inject(DirectiveA), inject(DirectiveB)) - }); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); + E(0, 'div', null, [DirectiveA]); { - D(1, DirectiveADef.n(), DirectiveADef); - E(2, 'span'); - { - D(3, DirectiveBDef.n(), DirectiveBDef); - D(4, DirectiveCDef.n(), DirectiveCDef); - T(5); - } + E(2, 'span', null, [DirectiveB, DirectiveC]); + { T(5); } e(); } e(); @@ -92,32 +82,23 @@ describe('di', () => { constructor(public elementRef: ElementRef) { this.value = (elementRef.constructor as any).name; } + static ngDirectiveDef = defineDirective( + {factory: () => new Directive(injectElementRef()), features: [PublicFeature]}); } - const DirectiveDef = defineDirective({ - type: Directive, - factory: () => new Directive(injectElementRef()), - features: [PublicFeature] - }); class DirectiveSameInstance { value: boolean; constructor(elementRef: ElementRef, directive: Directive) { this.value = elementRef === directive.elementRef; } + static ngDirectiveDef = defineDirective( + {factory: () => new DirectiveSameInstance(injectElementRef(), inject(Directive))}); } - const DirectiveSameInstanceDef = defineDirective({ - type: DirectiveSameInstance, - factory: () => new DirectiveSameInstance(injectElementRef(), inject(Directive)) - }); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - { - D(1, DirectiveDef.n(), DirectiveDef); - D(2, DirectiveSameInstanceDef.n(), DirectiveSameInstanceDef); - T(3); - } + E(0, 'div', null, [Directive, DirectiveSameInstance]); + { T(3); } e(); } t(3, b2('', D(1).value, '-', D(2).value, '')); @@ -134,33 +115,23 @@ describe('di', () => { constructor(public templateRef: TemplateRef) { this.value = (templateRef.constructor as any).name; } + static ngDirectiveDef = defineDirective( + {factory: () => new Directive(injectTemplateRef()), features: [PublicFeature]}); } - const DirectiveDef = defineDirective({ - type: Directive, - factory: () => new Directive(injectTemplateRef()), - features: [PublicFeature] - }); class DirectiveSameInstance { value: boolean; constructor(templateRef: TemplateRef, directive: Directive) { this.value = templateRef === directive.templateRef; } + static ngDirectiveDef = defineDirective( + {factory: () => new DirectiveSameInstance(injectTemplateRef(), inject(Directive))}); } - const DirectiveSameInstanceDef = defineDirective({ - type: DirectiveSameInstance, - factory: () => new DirectiveSameInstance(injectTemplateRef(), inject(Directive)) - }); function Template(ctx: any, cm: any) { if (cm) { - C(0, function() {}); - { - D(1, DirectiveDef.n(), DirectiveDef); - D(2, DirectiveSameInstanceDef.n(), DirectiveSameInstanceDef); - } - c(); + C(0, [Directive, DirectiveSameInstance], function() {}); T(3); } t(3, b2('', D(1).value, '-', D(2).value, '')); @@ -177,32 +148,24 @@ describe('di', () => { constructor(public viewContainerRef: ViewContainerRef) { this.value = (viewContainerRef.constructor as any).name; } + static ngDirectiveDef = defineDirective( + {factory: () => new Directive(injectViewContainerRef()), features: [PublicFeature]}); } - const DirectiveDef = defineDirective({ - type: Directive, - factory: () => new Directive(injectViewContainerRef()), - features: [PublicFeature] - }); class DirectiveSameInstance { value: boolean; constructor(viewContainerRef: ViewContainerRef, directive: Directive) { this.value = viewContainerRef === directive.viewContainerRef; } + static ngDirectiveDef = defineDirective({ + factory: () => new DirectiveSameInstance(injectViewContainerRef(), inject(Directive)) + }); } - const DirectiveSameInstanceDef = defineDirective({ - type: DirectiveSameInstance, - factory: () => new DirectiveSameInstance(injectViewContainerRef(), inject(Directive)) - }); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - { - D(1, DirectiveDef.n(), DirectiveDef); - D(2, DirectiveSameInstanceDef.n(), DirectiveSameInstanceDef); - T(3); - } + E(0, 'div', null, [Directive, DirectiveSameInstance]); + { T(3); } e(); } t(3, b2('', D(1).value, '-', D(2).value, '')); @@ -255,52 +218,42 @@ describe('di', () => { }); it('should inject from parent view', () => { - class ParentDirective {} - const ParentDirectiveDef = defineDirective( - {type: ParentDirective, factory: () => new ParentDirective(), features: [PublicFeature]}); + class ParentDirective { + static ngDirectiveDef = + defineDirective({factory: () => new ParentDirective(), features: [PublicFeature]}); + } class ChildDirective { value: string; constructor(public parent: ParentDirective) { this.value = (parent.constructor as any).name; } + static ngDirectiveDef = defineDirective({ + factory: () => new ChildDirective(inject(ParentDirective)), + features: [PublicFeature] + }); } - const ChildDirectiveDef = defineDirective({ - type: ChildDirective, - factory: () => new ChildDirective(inject(ParentDirective)), - features: [PublicFeature] - }); class Child2Directive { value: boolean; constructor(parent: ParentDirective, child: ChildDirective) { this.value = parent === child.parent; } + static ngDirectiveDef = defineDirective( + {factory: () => new Child2Directive(inject(ParentDirective), inject(ChildDirective))}); } - const Child2DirectiveDef = defineDirective({ - type: Child2Directive, - factory: () => new Child2Directive(inject(ParentDirective), inject(ChildDirective)) - }); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - { - D(1, ParentDirectiveDef.n(), ParentDirectiveDef); - C(2); - c(); - } + E(0, 'div', null, [ParentDirective]); + { C(2); } e(); } cR(2); { if (V(0)) { - E(0, 'span'); - { - D(1, ChildDirectiveDef.n(), ChildDirectiveDef); - D(2, Child2DirectiveDef.n(), Child2DirectiveDef); - T(3); - } + E(0, 'span', null, [ChildDirective, Child2Directive]); + { T(3); } e(); } t(3, b2('', D(1).value, '-', D(2).value, '')); diff --git a/packages/core/test/render3/directive_spec.ts b/packages/core/test/render3/directive_spec.ts index 13e298b8b2948..25782ad3345e4 100644 --- a/packages/core/test/render3/directive_spec.ts +++ b/packages/core/test/render3/directive_spec.ts @@ -19,22 +19,20 @@ describe('directive', () => { class Directive { klass = 'foo'; + static ngDirectiveDef = defineDirective({ + factory: () => directiveInstance = new Directive, + refresh: (directiveIndex: number, elementIndex: number) => { + p(elementIndex, 'className', b(D(directiveIndex).klass)); + } + }); } - const DirectiveDef = defineDirective({ - type: Directive, - factory: () => directiveInstance = new Directive, - refresh: (directiveIndex: number, elementIndex: number) => { - p(elementIndex, 'className', b(D(directiveIndex).klass)); - } - }); function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'span'); - { D(1, DirectiveDef.n(), DirectiveDef); } + E(0, 'span', null, [Directive]); e(); } - DirectiveDef.r(1, 0); + Directive.ngDirectiveDef.r(1, 0); } expect(renderToHtml(Template, {})).toEqual(''); diff --git a/packages/core/test/render3/exports_spec.ts b/packages/core/test/render3/exports_spec.ts index 6f474a69188f3..3ce2d4164e66c 100644 --- a/packages/core/test/render3/exports_spec.ts +++ b/packages/core/test/render3/exports_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, D, E, T, V, a, b, c, cR, cr, defineComponent, defineDirective, e, k, p, t, v} from '../../src/render3/index'; +import {C, D, E, T, V, a, b, cR, cr, defineComponent, defineDirective, e, k, p, t, v} from '../../src/render3/index'; import {renderToHtml} from './render_util'; @@ -32,8 +32,7 @@ describe('exports', () => { /** {{ myComp.name }} */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, MyComponent.ngComponentDef); - { D(1, MyComponent.ngComponentDef.n(), MyComponent.ngComponentDef); } + E(0, MyComponent); e(); T(2); } @@ -43,12 +42,8 @@ describe('exports', () => { class MyComponent { name = 'Nancy'; - static ngComponentDef = defineComponent({ - type: MyComponent, - tag: 'comp', - template: function() {}, - factory: () => new MyComponent - }); + static ngComponentDef = + defineComponent({tag: 'comp', template: function() {}, factory: () => new MyComponent}); } expect(renderToHtml(Template, {})).toEqual('Nancy'); @@ -60,29 +55,22 @@ describe('exports', () => { let myDir: MyDir; class MyComponent { constructor() { myComponent = this; } - static ngComponentDef = defineComponent({ - type: MyComponent, - tag: 'comp', - template: function() {}, - factory: () => new MyComponent - }); + static ngComponentDef = + defineComponent({tag: 'comp', template: function() {}, factory: () => new MyComponent}); } class MyDir { myDir: MyComponent; constructor() { myDir = this; } - static ngDirectiveDef = - defineDirective({type: MyDir, factory: () => new MyDir, inputs: {myDir: 'myDir'}}); + static ngDirectiveDef = defineDirective({factory: () => new MyDir, inputs: {myDir: 'myDir'}}); } /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, MyComponent.ngComponentDef); - { D(1, MyComponent.ngComponentDef.n(), MyComponent.ngComponentDef); } + E(0, MyComponent); e(); - E(2, 'div'); - { D(3, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(2, 'div', null, [MyDir]); e(); } p(2, 'myDir', b(D(1))); @@ -97,8 +85,7 @@ describe('exports', () => { /**
{{ myDir.name }} */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - D(1, SomeDirDef.n(), SomeDirDef); + E(0, 'div', null, [SomeDir]); e(); T(2); } @@ -107,8 +94,8 @@ describe('exports', () => { class SomeDir { name = 'Drew'; + static ngDirectiveDef = defineDirective({factory: () => new SomeDir}); } - const SomeDirDef = defineDirective({type: SomeDir, factory: () => new SomeDir}); expect(renderToHtml(Template, {})).toEqual('
Drew'); }); @@ -188,7 +175,6 @@ describe('exports', () => { constructor() { myComponent = this; } static ngComponentDef = defineComponent({ - type: MyComponent, tag: 'comp', template: function(ctx: MyComponent, cm: boolean) {}, factory: () => new MyComponent @@ -201,17 +187,15 @@ describe('exports', () => { constructor() { myDir = this; } static ngDirectiveDef = - defineDirective({type: MyDir, factory: () => new MyDir, inputs: {myDir: 'myDir'}}); + defineDirective({factory: () => new MyDir, inputs: {myDir: 'myDir'}}); } /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div'); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', null, [MyDir]); e(); - E(2, MyComponent.ngComponentDef); - { D(3, MyComponent.ngComponentDef.n(), MyComponent.ngComponentDef); } + E(2, MyComponent); e(); } p(0, 'myDir', b(D(3))); @@ -228,8 +212,7 @@ describe('exports', () => { if (cm) { T(0); T(1); - E(2, 'comp'); - { D(3, MyComponent.ngComponentDef.n(), MyComponent.ngComponentDef); } + E(2, MyComponent); e(); E(4, 'input', ['value', 'one']); e(); @@ -247,12 +230,8 @@ describe('exports', () => { constructor() { myComponent = this; } - static ngComponentDef = defineComponent({ - type: MyComponent, - tag: 'comp', - template: function() {}, - factory: () => new MyComponent - }); + static ngComponentDef = + defineComponent({tag: 'comp', template: function() {}, factory: () => new MyComponent}); } expect(renderToHtml(Template, {})).toEqual('oneNancy'); }); @@ -261,10 +240,7 @@ describe('exports', () => { function Template(ctx: any, cm: boolean) { if (cm) { E(0, 'div'); - { - C(1); - c(); - } + { C(1); } e(); } cR(1); diff --git a/packages/core/test/render3/integration_spec.ts b/packages/core/test/render3/integration_spec.ts index 3a50e0b939e67..922d28781f73c 100644 --- a/packages/core/test/render3/integration_spec.ts +++ b/packages/core/test/render3/integration_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, D, E, NC, T, V, a, b, b1, b2, b3, b4, b5, b6, b7, b8, bV, c, cR, cr, defineComponent, e, k, p, r, s, t, v} from '../../src/render3/index'; +import {C, D, E, NC, T, V, a, b, b1, b2, b3, b4, b5, b6, b7, b8, bV, cR, cr, defineComponent, e, k, p, r, s, t, v} from '../../src/render3/index'; import {NO_CHANGE} from '../../src/render3/instructions'; import {containerEl, renderToHtml} from './render_util'; @@ -210,7 +210,6 @@ describe('render3 integration test', () => { value = ' one'; static ngComponentDef = defineComponent({ - type: TodoComponent, tag: 'todo', template: function TodoTemplate(ctx: any, cm: boolean) { if (cm) { @@ -230,8 +229,7 @@ describe('render3 integration test', () => { it('should support a basic component template', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, TodoComponent.ngComponentDef); - { D(1, TodoComponent.ngComponentDef.n(), TodoComponent.ngComponentDef); } + E(0, TodoComponent); e(); } TodoComponent.ngComponentDef.h(1, 0); @@ -244,8 +242,7 @@ describe('render3 integration test', () => { it('should support a component template with sibling', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, TodoComponent.ngComponentDef); - { D(1, TodoComponent.ngComponentDef.n(), TodoComponent.ngComponentDef); } + E(0, TodoComponent); e(); T(2, 'two'); } @@ -262,11 +259,9 @@ describe('render3 integration test', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, TodoComponent.ngComponentDef); - { D(1, TodoComponent.ngComponentDef.n(), TodoComponent.ngComponentDef); } + E(0, TodoComponent); e(); - E(2, TodoComponent.ngComponentDef); - { D(3, TodoComponent.ngComponentDef.n(), TodoComponent.ngComponentDef); } + E(2, TodoComponent); e(); } TodoComponent.ngComponentDef.h(1, 0); @@ -284,7 +279,6 @@ describe('render3 integration test', () => { class TodoComponentHostBinding { title = 'one'; static ngComponentDef = defineComponent({ - type: TodoComponentHostBinding, tag: 'todo', template: function TodoComponentHostBindingTemplate( ctx: TodoComponentHostBinding, cm: boolean) { @@ -303,11 +297,7 @@ describe('render3 integration test', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, TodoComponentHostBinding.ngComponentDef); - { - D(1, TodoComponentHostBinding.ngComponentDef.n(), - TodoComponentHostBinding.ngComponentDef); - } + E(0, TodoComponentHostBinding); e(); } TodoComponentHostBinding.ngComponentDef.h(1, 0); @@ -324,7 +314,6 @@ describe('render3 integration test', () => { class MyComp { name = 'Bess'; static ngComponentDef = defineComponent({ - type: MyComp, tag: 'comp', template: function MyCompTemplate(ctx: any, cm: boolean) { if (cm) { @@ -340,8 +329,7 @@ describe('render3 integration test', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, MyComp.ngComponentDef); - { D(1, MyComp.ngComponentDef.n(), MyComp.ngComponentDef); } + E(0, MyComp); e(); } MyComp.ngComponentDef.h(1, 0); @@ -360,12 +348,10 @@ describe('render3 integration test', () => { class MyComp { condition: boolean; static ngComponentDef = defineComponent({ - type: MyComp, tag: 'comp', template: function MyCompTemplate(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { @@ -388,8 +374,7 @@ describe('render3 integration test', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, MyComp.ngComponentDef); - { D(1, MyComp.ngComponentDef.n(), MyComp.ngComponentDef); } + E(0, MyComp); e(); } p(0, 'condition', b(ctx.condition)); @@ -488,7 +473,6 @@ describe('render3 integration test', () => { if (cm) { E(0, 'span'); C(1); - c(); e(); } a(0, 'title', b(ctx.title)); @@ -605,7 +589,6 @@ describe('render3 integration test', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { diff --git a/packages/core/test/render3/lifecycle_spec.ts b/packages/core/test/render3/lifecycle_spec.ts index 820d44753a55b..57766836d2559 100644 --- a/packages/core/test/render3/lifecycle_spec.ts +++ b/packages/core/test/render3/lifecycle_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, ComponentDef, ComponentTemplate, D, E, L, LifecycleHook, T, V, b, c, cR, cr, defineComponent, e, l, p, r, v} from '../../src/render3/index'; +import {C, ComponentDef, ComponentTemplate, D, E, L, LifecycleHook, T, V, b, cR, cr, defineComponent, e, l, p, r, v} from '../../src/render3/index'; import {containerEl, renderToHtml} from './render_util'; @@ -15,8 +15,7 @@ describe('lifecycles', () => { function getParentTemplate(type: any) { return (ctx: any, cm: boolean) => { if (cm) { - E(0, type.ngComponentDef); - { D(1, type.ngComponentDef.n(), type.ngComponentDef); } + E(0, type); e(); } p(0, 'val', b(ctx.val)); @@ -39,7 +38,6 @@ describe('lifecycles', () => { ngOnInit() { events.push(`${name}${this.val}`); } static ngComponentDef = defineComponent({ - type: Component, tag: name, factory: () => new Component(), hostBindings: function(directiveIndex: number, elementIndex: number): @@ -54,8 +52,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', b(ctx.val)); @@ -78,8 +75,7 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } Parent.ngComponentDef.h(1, 0); @@ -100,11 +96,9 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); - E(2, Parent.ngComponentDef); - { D(3, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(2, Parent); e(); } p(0, 'val', 1); @@ -130,14 +124,12 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -169,13 +161,10 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); C(2); - c(); - E(3, Comp.ngComponentDef); - { D(4, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(3, Comp); e(); } p(0, 'val', 1); @@ -186,8 +175,7 @@ describe('lifecycles', () => { { for (let j = 2; j < 5; j++) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', j); @@ -219,13 +207,10 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); C(2); - c(); - E(3, Parent.ngComponentDef); - { D(4, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(3, Parent); e(); } p(0, 'val', 1); @@ -236,8 +221,7 @@ describe('lifecycles', () => { { for (let j = 2; j < 5; j++) { if (V(0)) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } p(0, 'val', j); @@ -286,7 +270,6 @@ describe('lifecycles', () => { ngOnInit() { allEvents.push('ngOnInit ' + name); } static ngComponentDef = defineComponent({ - type: Component, tag: name, factory: () => new Component(), hostBindings: function( @@ -303,8 +286,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -326,8 +308,7 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } Parent.ngComponentDef.h(1, 0); @@ -342,8 +323,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -381,7 +361,6 @@ describe('lifecycles', () => { ngAfterViewChecked() { allEvents.push(`${name}${this.val} check`); } static ngComponentDef = defineComponent({ - type: Component, tag: name, factory: () => new Component(), refresh: (directiveIndex: number, elementIndex: number) => { @@ -400,8 +379,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -424,14 +402,12 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -461,8 +437,7 @@ describe('lifecycles', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } Parent.ngComponentDef.h(1, 0); @@ -483,11 +458,9 @@ describe('lifecycles', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); - E(2, Parent.ngComponentDef); - { D(3, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(2, Parent); e(); } p(0, 'val', 1); @@ -512,13 +485,10 @@ describe('lifecycles', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); C(2); - c(); - E(3, Comp.ngComponentDef); - { D(4, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(3, Comp); e(); } p(0, 'val', 1); @@ -529,8 +499,7 @@ describe('lifecycles', () => { { for (let i = 2; i < 4; i++) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', i); @@ -559,13 +528,10 @@ describe('lifecycles', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); C(2); - c(); - E(3, Parent.ngComponentDef); - { D(4, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(3, Parent); e(); } p(0, 'val', 1); @@ -576,8 +542,7 @@ describe('lifecycles', () => { { for (let i = 2; i < 4; i++) { if (V(0)) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } p(0, 'val', i); @@ -604,8 +569,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -623,8 +587,7 @@ describe('lifecycles', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', b(ctx.myVal)); @@ -649,13 +612,10 @@ describe('lifecycles', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); C(2); - c(); - E(3, Parent.ngComponentDef); - { D(4, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(3, Parent); e(); } p(0, 'val', 1); @@ -666,8 +626,7 @@ describe('lifecycles', () => { { for (let i = 2; i < 4; i++) { if (V(0)) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } p(0, 'val', i); @@ -708,7 +667,6 @@ describe('lifecycles', () => { ngOnDestroy() { events.push(`${name}${this.val}`); } static ngComponentDef = defineComponent({ - type: Component, tag: name, factory: () => { const comp = new Component(); @@ -731,14 +689,12 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); @@ -765,17 +721,14 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); - E(2, Comp.ngComponentDef); - { D(3, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(2, Comp); e(); } p(0, 'val', b('1')); @@ -807,14 +760,12 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } Parent.ngComponentDef.h(1, 0); @@ -842,8 +793,7 @@ describe('lifecycles', () => { let Grandparent = createOnDestroyComponent('grandparent', function(ctx: any, cm: boolean) { if (cm) { - E(0, Parent.ngComponentDef); - { D(1, Parent.ngComponentDef.n(), Parent.ngComponentDef); } + E(0, Parent); e(); } Parent.ngComponentDef.h(1, 0); @@ -853,14 +803,12 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Grandparent.ngComponentDef); - { D(1, Grandparent.ngComponentDef.n(), Grandparent.ngComponentDef); } + E(0, Grandparent); e(); } Grandparent.ngComponentDef.h(1, 0); @@ -891,19 +839,15 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); C(2); - c(); - E(3, Comp.ngComponentDef); - { D(4, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(3, Comp); e(); } p(0, 'val', b('1')); @@ -914,8 +858,7 @@ describe('lifecycles', () => { { if (ctx.condition2) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', b('2')); @@ -972,19 +915,15 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); C(2); - c(); - E(3, Comp.ngComponentDef); - { D(4, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(3, Comp); e(); } p(0, 'val', b('1')); @@ -995,8 +934,7 @@ describe('lifecycles', () => { { for (let j = 2; j < ctx.len; j++) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'val', b(j)); @@ -1055,7 +993,6 @@ describe('lifecycles', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { @@ -1067,8 +1004,7 @@ describe('lifecycles', () => { T(1, 'Click me'); } e(); - E(2, Comp.ngComponentDef); - { D(3, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(2, Comp); e(); E(4, 'button'); { diff --git a/packages/core/test/render3/listeners_spec.ts b/packages/core/test/render3/listeners_spec.ts index 6b3d2bef38200..096e9d1863fc9 100644 --- a/packages/core/test/render3/listeners_spec.ts +++ b/packages/core/test/render3/listeners_spec.ts @@ -6,7 +6,7 @@ * found in the LICENSE file at https://angular.io/license */ -import {C, D, E, L, T, V, c, cR, cr, defineComponent, e, v} from '../../src/render3/index'; +import {C, D, E, L, T, V, cR, cr, defineComponent, e, v} from '../../src/render3/index'; import {containerEl, renderComponent, renderToHtml} from './render_util'; @@ -21,7 +21,6 @@ describe('event listeners', () => { onClick() { this.counter++; } static ngComponentDef = defineComponent({ - type: MyComp, tag: 'comp', /** */ template: function CompTemplate(ctx: any, cm: boolean) { @@ -137,7 +136,6 @@ describe('event listeners', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { @@ -145,7 +143,6 @@ describe('event listeners', () => { if (V(0)) { T(0, 'Hello'); C(1); - c(); } cR(1); { @@ -197,18 +194,15 @@ describe('event listeners', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.showing) { if (V(0)) { T(0, 'Hello'); - E(1, MyComp.ngComponentDef); - { D(2, MyComp.ngComponentDef.n(), MyComp.ngComponentDef); } + E(1, MyComp); e(); - E(3, MyComp.ngComponentDef); - { D(4, MyComp.ngComponentDef.n(), MyComp.ngComponentDef); } + E(3, MyComp); e(); } MyComp.ngComponentDef.h(2, 1); @@ -256,7 +250,6 @@ describe('event listeners', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { @@ -264,9 +257,7 @@ describe('event listeners', () => { if (V(0)) { T(0, 'Hello'); C(1); - c(); C(2); - c(); } cR(1); { diff --git a/packages/core/test/render3/outputs_spec.ts b/packages/core/test/render3/outputs_spec.ts index f478008690ce0..103e8829704a3 100644 --- a/packages/core/test/render3/outputs_spec.ts +++ b/packages/core/test/render3/outputs_spec.ts @@ -8,7 +8,7 @@ import {EventEmitter} from '@angular/core'; -import {C, D, E, L, LifecycleHook, T, V, b, c, cR, cr, defineComponent, defineDirective, e, l, p, v} from '../../src/render3/index'; +import {C, D, E, L, LifecycleHook, T, V, b, cR, cr, defineComponent, defineDirective, e, l, p, v} from '../../src/render3/index'; import {containerEl, renderToHtml} from './render_util'; @@ -21,7 +21,6 @@ describe('outputs', () => { static ngComponentDef = defineComponent({ tag: 'button-toggle', - type: ButtonToggle, template: function(ctx: any, cm: boolean) {}, factory: () => buttonToggle = new ButtonToggle(), outputs: {change: 'change', resetStream: 'reset'} @@ -33,22 +32,16 @@ describe('outputs', () => { class OtherDir { changeStream = new EventEmitter(); - static ngDirectiveDef = defineDirective({ - type: OtherDir, - factory: () => otherDir = new OtherDir, - outputs: {changeStream: 'change'} - }); + static ngDirectiveDef = defineDirective( + {factory: () => otherDir = new OtherDir, outputs: {changeStream: 'change'}}); } it('should call component output function when event is emitted', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle); + { L('change', ctx.onChange.bind(ctx)); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -70,9 +63,8 @@ describe('outputs', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, ButtonToggle.ngComponentDef); + E(0, ButtonToggle); { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); L('change', ctx.onChange.bind(ctx)); L('reset', ctx.onReset.bind(ctx)); } @@ -98,11 +90,8 @@ describe('outputs', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', () => ctx.counter++); - } + E(0, ButtonToggle); + { L('change', () => ctx.counter++); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -130,17 +119,13 @@ describe('outputs', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle); + { L('change', ctx.onChange.bind(ctx)); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -178,24 +163,19 @@ describe('outputs', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { if (ctx.condition) { if (V(0)) { C(0); - c(); } cR(0); { if (ctx.condition2) { if (V(0)) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle); + { L('change', ctx.onChange.bind(ctx)); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -233,7 +213,6 @@ describe('outputs', () => { static ngComponentDef = defineComponent({ tag: 'destroy-comp', - type: DestroyComp, template: function(ctx: any, cm: boolean) {}, factory: () => { destroyComp = new DestroyComp(); @@ -253,7 +232,6 @@ describe('outputs', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { @@ -265,14 +243,10 @@ describe('outputs', () => { T(1, 'Click me'); } e(); - E(2, ButtonToggle.ngComponentDef); - { - D(3, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', ctx.onChange.bind(ctx)); - } + E(2, ButtonToggle); + { L('change', ctx.onChange.bind(ctx)); } e(); - E(4, DestroyComp.ngComponentDef); - { D(5, DestroyComp.ngComponentDef.n(), DestroyComp.ngComponentDef); } + E(4, DestroyComp); e(); } ButtonToggle.ngComponentDef.h(3, 2); @@ -317,17 +291,14 @@ describe('outputs', () => { class MyButton { click = new EventEmitter(); - static ngDirectiveDef = defineDirective( - {type: MyButton, factory: () => buttonDir = new MyButton, outputs: {click: 'click'}}); + static ngDirectiveDef = + defineDirective({factory: () => buttonDir = new MyButton, outputs: {click: 'click'}}); } function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); - { - D(1, MyButton.ngDirectiveDef.n(), MyButton.ngDirectiveDef); - L('click', ctx.onClick.bind(ctx)); - } + E(0, 'button', null, [MyButton]); + { L('click', ctx.onClick.bind(ctx)); } e(); } } @@ -349,12 +320,8 @@ describe('outputs', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - D(2, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle, null, [OtherDir]); + { L('change', ctx.onChange.bind(ctx)); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -377,19 +344,15 @@ describe('outputs', () => { class OtherDir { change: boolean; - static ngDirectiveDef = defineDirective( - {type: OtherDir, factory: () => otherDir = new OtherDir, inputs: {change: 'change'}}); + static ngDirectiveDef = + defineDirective({factory: () => otherDir = new OtherDir, inputs: {change: 'change'}}); } /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - D(2, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle, null, [OtherDir]); + { L('change', ctx.onChange.bind(ctx)); } e(); } p(0, 'change', b(ctx.change)); @@ -427,17 +390,13 @@ describe('outputs', () => { } e(); C(2); - c(); } cR(2); { if (ctx.condition) { if (V(0)) { - E(0, ButtonToggle.ngComponentDef); - { - D(1, ButtonToggle.ngComponentDef.n(), ButtonToggle.ngComponentDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, ButtonToggle); + { L('change', ctx.onChange.bind(ctx)); } e(); } ButtonToggle.ngComponentDef.h(1, 0); @@ -445,11 +404,8 @@ describe('outputs', () => { v(); } else { if (V(1)) { - E(0, 'div'); - { - D(1, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, 'div', null, [OtherDir]); + { L('change', ctx.onChange.bind(ctx)); } e(); } v(); diff --git a/packages/core/test/render3/properties_spec.ts b/packages/core/test/render3/properties_spec.ts index d5be8b17eb20a..2aa72d1676983 100644 --- a/packages/core/test/render3/properties_spec.ts +++ b/packages/core/test/render3/properties_spec.ts @@ -8,7 +8,7 @@ import {EventEmitter} from '@angular/core'; -import {C, D, E, L, T, V, b, b1, c, cR, cr, defineComponent, defineDirective, e, p, t, v} from '../../src/render3/index'; +import {C, D, E, L, T, V, b, b1, cR, cr, defineComponent, defineDirective, e, p, t, v} from '../../src/render3/index'; import {NO_CHANGE} from '../../src/render3/instructions'; import {renderToHtml} from './render_util'; @@ -69,8 +69,8 @@ describe('elementProperty', () => { class MyButton { disabled: boolean; - static ngDirectiveDef = defineDirective( - {type: MyButton, factory: () => button = new MyButton(), inputs: {disabled: 'disabled'}}); + static ngDirectiveDef = + defineDirective({factory: () => button = new MyButton(), inputs: {disabled: 'disabled'}}); } class OtherDir { @@ -78,7 +78,6 @@ describe('elementProperty', () => { clickStream = new EventEmitter(); static ngDirectiveDef = defineDirective({ - type: OtherDir, factory: () => otherDir = new OtherDir(), inputs: {id: 'id'}, outputs: {clickStream: 'click'} @@ -90,12 +89,8 @@ describe('elementProperty', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); - { - D(1, MyButton.ngDirectiveDef.n(), MyButton.ngDirectiveDef); - D(2, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); - T(3, 'Click me'); - } + E(0, 'button', null, [MyButton, OtherDir]); + { T(3, 'Click me'); } e(); } @@ -120,11 +115,8 @@ describe('elementProperty', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); - { - D(1, MyButton.ngDirectiveDef.n(), MyButton.ngDirectiveDef); - T(2, 'Click me'); - } + E(0, 'button', null, [MyButton]); + { T(2, 'Click me'); } e(); } @@ -149,7 +141,6 @@ describe('elementProperty', () => { static ngComponentDef = defineComponent({ tag: 'comp', - type: Comp, template: function(ctx: any, cm: boolean) {}, factory: () => comp = new Comp(), inputs: {id: 'id'} @@ -159,8 +150,7 @@ describe('elementProperty', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } p(0, 'id', b(ctx.id)); @@ -182,7 +172,6 @@ describe('elementProperty', () => { disabled: boolean; static ngDirectiveDef = defineDirective({ - type: OtherDisabledDir, factory: () => otherDisabledDir = new OtherDisabledDir(), inputs: {disabled: 'disabled'} }); @@ -191,12 +180,8 @@ describe('elementProperty', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); - { - D(1, MyButton.ngDirectiveDef.n(), MyButton.ngDirectiveDef); - D(2, OtherDisabledDir.ngDirectiveDef.n(), OtherDisabledDir.ngDirectiveDef); - T(3, 'Click me'); - } + E(0, 'button', null, [MyButton, OtherDisabledDir]); + { T(3, 'Click me'); } e(); } p(0, 'disabled', b(ctx.isDisabled)); @@ -217,9 +202,8 @@ describe('elementProperty', () => { /** */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); + E(0, 'button', null, [OtherDir]); { - D(1, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); L('click', ctx.onClick.bind(ctx)); T(2, 'Click me'); } @@ -247,8 +231,8 @@ describe('elementProperty', () => { class IdDir { idNumber: number; - static ngDirectiveDef = defineDirective( - {type: IdDir, factory: () => idDir = new IdDir(), inputs: {idNumber: 'id'}}); + static ngDirectiveDef = + defineDirective({factory: () => idDir = new IdDir(), inputs: {idNumber: 'id'}}); } /** @@ -261,14 +245,10 @@ describe('elementProperty', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'button'); - { - D(1, IdDir.ngDirectiveDef.n(), IdDir.ngDirectiveDef); - T(2, 'Click me'); - } + E(0, 'button', null, [IdDir]); + { T(2, 'Click me'); } e(); C(3); - c(); } p(0, 'id', b(ctx.id1)); cR(3); @@ -283,11 +263,8 @@ describe('elementProperty', () => { v(); } else { if (V(1)) { - E(0, 'button'); - { - D(1, OtherDir.ngDirectiveDef.n(), OtherDir.ngDirectiveDef); - T(2, 'Click me too'); - } + E(0, 'button', null, [OtherDir]); + { T(2, 'Click me too'); } e(); } p(0, 'id', b(ctx.id3)); @@ -317,7 +294,6 @@ describe('elementProperty', () => { changeStream = new EventEmitter(); static ngDirectiveDef = defineDirective({ - type: MyDir, factory: () => myDir = new MyDir(), inputs: {role: 'role', direction: 'dir'}, outputs: {changeStream: 'change'} @@ -328,8 +304,8 @@ describe('elementProperty', () => { class MyDirB { roleB: string; - static ngDirectiveDef = defineDirective( - {type: MyDirB, factory: () => dirB = new MyDirB(), inputs: {roleB: 'role'}}); + static ngDirectiveDef = + defineDirective({factory: () => dirB = new MyDirB(), inputs: {roleB: 'role'}}); } it('should set input property based on attribute if existing', () => { @@ -337,8 +313,7 @@ describe('elementProperty', () => { /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'button'], [MyDir]); e(); } } @@ -352,8 +327,7 @@ describe('elementProperty', () => { /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'button'], [MyDir]); e(); } p(0, 'role', b(ctx.role)); @@ -371,11 +345,7 @@ describe('elementProperty', () => { /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button']); - { - D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); - D(2, MyDirB.ngDirectiveDef.n(), MyDirB.ngDirectiveDef); - } + E(0, 'div', ['role', 'button'], [MyDir, MyDirB]); e(); } } @@ -390,8 +360,7 @@ describe('elementProperty', () => { /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button', 'dir', 'rtl']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'button', 'dir', 'rtl'], [MyDir]); e(); } } @@ -406,11 +375,8 @@ describe('elementProperty', () => { /**
*/ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button']); - { - D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); - L('change', ctx.onChange.bind(ctx)); - } + E(0, 'div', ['role', 'button'], [MyDir]); + { L('change', ctx.onChange.bind(ctx)); } e(); } } @@ -434,11 +400,9 @@ describe('elementProperty', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button', 'dir', 'rtl']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'button', 'dir', 'rtl'], [MyDir]); e(); - E(2, 'div', ['role', 'listbox']); - { D(3, MyDirB.ngDirectiveDef.n(), MyDirB.ngDirectiveDef); } + E(2, 'div', ['role', 'listbox'], [MyDirB]); e(); } } @@ -462,18 +426,15 @@ describe('elementProperty', () => { */ function Template(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'listbox']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'listbox'], [MyDir]); e(); C(2); - c(); } cR(2); { if (ctx.condition) { if (V(0)) { - E(0, 'div', ['role', 'button']); - { D(1, MyDirB.ngDirectiveDef.n(), MyDirB.ngDirectiveDef); } + E(0, 'div', ['role', 'button'], [MyDirB]); e(); } v(); @@ -507,11 +468,9 @@ describe('elementProperty', () => { class Comp { static ngComponentDef = defineComponent({ tag: 'comp', - type: Comp, template: function(ctx: any, cm: boolean) { if (cm) { - E(0, 'div', ['role', 'button']); - { D(1, MyDir.ngDirectiveDef.n(), MyDir.ngDirectiveDef); } + E(0, 'div', ['role', 'button'], [MyDir]); e(); T(2); } @@ -529,14 +488,12 @@ describe('elementProperty', () => { function Template(ctx: any, cm: boolean) { if (cm) { C(0); - c(); } cR(0); { for (let i = 0; i < 2; i++) { if (V(0)) { - E(0, Comp.ngComponentDef); - { D(1, Comp.ngComponentDef.n(), Comp.ngComponentDef); } + E(0, Comp); e(); } Comp.ngComponentDef.h(1, 0); diff --git a/packages/core/test/render3/query_spec.ts b/packages/core/test/render3/query_spec.ts index 8f3f601133d07..f80ba97f49d03 100644 --- a/packages/core/test/render3/query_spec.ts +++ b/packages/core/test/render3/query_spec.ts @@ -5,7 +5,7 @@ * Use of this source code is governed by an MIT-style license that can be * found in the LICENSE file at https://angular.io/license */ -import {C, D, E, Q, QueryList, c, e, m, qR} from '../../src/render3/index'; +import {C, D, E, Q, QueryList, e, m, qR} from '../../src/render3/index'; import {QueryReadType} from '../../src/render3/interfaces/query'; import {createComponent, createDirective, renderComponent} from './render_util'; @@ -59,11 +59,11 @@ describe('query', () => { if (cm) { m(0, Q(Child, false)); m(1, Q(Child, true)); - E(2, Child.ngComponentDef); + E(2, Child); { - child1 = D(3, Child.ngComponentDef.n(), Child.ngComponentDef); - E(4, Child.ngComponentDef); - { child2 = D(5, Child.ngComponentDef.n(), Child.ngComponentDef); } + child1 = D(3); + E(4, Child); + { child2 = D(5); } e(); } e(); @@ -92,8 +92,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(Child, false, QueryReadType.ElementRef)); - elToQuery = E(1, 'div'); - { D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef); } + elToQuery = E(1, 'div', null, [Child]); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -121,11 +120,8 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(Child, false, OtherChild)); - E(1, 'div'); - { - D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef); - D(3, otherChildInstance = OtherChild.ngDirectiveDef.n(), OtherChild.ngDirectiveDef); - } + E(1, 'div', null, [Child, OtherChild]); + { otherChildInstance = D(3); } e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -150,8 +146,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(Child, false, OtherChild)); - E(1, 'div'); - { D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef); } + E(1, 'div', null, [Child]); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -179,7 +174,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'])); - elToQuery = E(1, 'div', [], 'foo'); + elToQuery = E(1, 'div', null, null, ['foo', '']); e(); E(2, 'div'); e(); @@ -209,11 +204,11 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo', 'bar'])); - el1ToQuery = E(1, 'div', null, 'foo'); + el1ToQuery = E(1, 'div', null, null, ['foo', '']); e(); E(2, 'div'); e(); - el2ToQuery = E(3, 'div', null, 'bar'); + el2ToQuery = E(3, 'div', null, null, ['bar', '']); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -240,7 +235,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, QueryReadType.ElementRef)); - elToQuery = E(1, 'div', [], 'foo'); + elToQuery = E(1, 'div', null, null, ['foo', '']); e(); E(2, 'div'); e(); @@ -266,7 +261,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, QueryReadType.ViewContainerRef)); - E(1, 'div', [], 'foo'); + E(1, 'div', null, null, ['foo', '']); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -289,8 +284,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, QueryReadType.ViewContainerRef)); - C(1, undefined, undefined, undefined, 'foo'); - c(); + C(1, undefined, undefined, undefined, undefined, ['foo', '']); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); }); @@ -313,8 +307,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, QueryReadType.ElementRef)); - C(1, undefined, undefined, undefined, 'foo'); - c(); + C(1, undefined, undefined, undefined, undefined, ['foo', '']); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); }); @@ -338,8 +331,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'])); - C(1, undefined, undefined, undefined, 'foo'); - c(); + C(1, undefined, undefined, undefined, undefined, ['foo', '']); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); }); @@ -362,8 +354,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, QueryReadType.TemplateRef)); - C(1, undefined, undefined, undefined, 'foo'); - c(); + C(1, undefined, undefined, undefined, undefined, ['foo', '']); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); }); @@ -388,8 +379,8 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'])); - E(1, Child.ngComponentDef, []); - { childInstance = D(2, Child.ngComponentDef.n(), Child.ngComponentDef, 'foo'); } + E(1, Child, null, null, ['foo', '']); + { childInstance = D(2); } e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -403,7 +394,7 @@ describe('query', () => { it('should read directive instance if element queried for has an exported directive with a matching name', () => { - const Child = createDirective(); + const Child = createDirective({exportAs: 'child'}); let childInstance; /** @@ -416,8 +407,8 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'])); - E(1, 'div'); - { childInstance = D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef, 'foo'); } + E(1, 'div', null, [Child], ['foo', 'child']); + childInstance = D(2); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -430,8 +421,8 @@ describe('query', () => { }); it('should read all matching directive instances from a given element', () => { - const Child1 = createDirective(); - const Child2 = createDirective(); + const Child1 = createDirective({exportAs: 'child1'}); + const Child2 = createDirective({exportAs: 'child2'}); let child1Instance, child2Instance; /** @@ -444,10 +435,10 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo', 'bar'])); - E(1, 'div'); + E(1, 'div', null, [Child1, Child2], ['foo', 'child1', 'bar', 'child2']); { - child1Instance = D(2, Child1.ngDirectiveDef.n(), Child1.ngDirectiveDef, 'foo'); - child2Instance = D(3, Child2.ngDirectiveDef.n(), Child2.ngDirectiveDef, 'bar'); + child1Instance = D(2); + child2Instance = D(3); } e(); } @@ -462,7 +453,7 @@ describe('query', () => { }); it('should match match on exported directive name and read a requested token', () => { - const Child = createDirective(); + const Child = createDirective({exportAs: 'child'}); let div; /** @@ -475,8 +466,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], undefined, QueryReadType.ElementRef)); - div = E(1, 'div'); - { D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef, 'foo'); } + div = E(1, 'div', null, [Child], ['foo', 'child']); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -489,7 +479,7 @@ describe('query', () => { }); it('should support reading a mix of ElementRef and directive instances', () => { - const Child = createDirective(); + const Child = createDirective({exportAs: 'child'}); let childInstance, div; /** @@ -502,8 +492,8 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo', 'bar'])); - div = E(1, 'div', [], 'foo'); - { childInstance = D(2, Child.ngDirectiveDef.n(), Child.ngDirectiveDef, 'bar'); } + div = E(1, 'div', null, [Child], ['foo', '', 'bar', 'child']); + { childInstance = D(2); } e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); @@ -530,7 +520,7 @@ describe('query', () => { let tmp: any; if (cm) { m(0, Q(['foo'], false, Child)); - div = E(1, 'div', [], 'foo'); + div = E(1, 'div', null, null, ['foo', '']); e(); } qR(tmp = m>(0)) && (ctx.query = tmp as QueryList); diff --git a/packages/core/test/render3/render_util.ts b/packages/core/test/render3/render_util.ts index 9e93cbc02daf1..6b64bfb4db6f4 100644 --- a/packages/core/test/render3/render_util.ts +++ b/packages/core/test/render3/render_util.ts @@ -7,10 +7,13 @@ */ import {stringifyElement} from '@angular/platform-browser/testing/src/browser_util'; + import {ComponentTemplate, ComponentType, DirectiveType, PublicFeature, defineComponent, defineDirective, renderComponent as _renderComponent} from '../../src/render3/index'; import {NG_HOST_SYMBOL, createLNode, createLView, renderTemplate} from '../../src/render3/instructions'; +import {DirectiveDefArgs} from '../../src/render3/interfaces/definition'; import {LElementNode, LNodeFlags} from '../../src/render3/interfaces/node'; import {RElement, RText, Renderer3, RendererFactory3, domRendererFactory3} from '../../src/render3/interfaces/renderer'; + import {getRendererFactory2} from './imported_renderer2'; export const document = ((global || window) as any).document; @@ -79,22 +82,17 @@ export function createComponent( name: string, template: ComponentTemplate): ComponentType { return class Component { value: any; - static ngComponentDef = defineComponent({ - type: Component, - tag: name, - factory: () => new Component, - template: template, - features: [PublicFeature] - }); + static ngComponentDef = defineComponent( + {tag: name, factory: () => new Component, template: template, features: [PublicFeature]}); }; } -export function createDirective(): DirectiveType { +export function createDirective({exportAs}: {exportAs?: string} = {}): DirectiveType { return class Directive { static ngDirectiveDef = defineDirective({ - type: Directive, factory: () => new Directive(), features: [PublicFeature], + exportAs: exportAs, }); }; } diff --git a/packages/core/test/render3/renderer_factory_spec.ts b/packages/core/test/render3/renderer_factory_spec.ts index 3f885f42b5d63..14d75f8025c6e 100644 --- a/packages/core/test/render3/renderer_factory_spec.ts +++ b/packages/core/test/render3/renderer_factory_spec.ts @@ -29,7 +29,6 @@ describe('renderer factory lifecycle', () => { class SomeComponent { static ngComponentDef = defineComponent({ - type: SomeComponent, tag: 'some-component', template: function(ctx: SomeComponent, cm: boolean) { logs.push('component'); @@ -43,7 +42,6 @@ describe('renderer factory lifecycle', () => { class SomeComponentWhichThrows { static ngComponentDef = defineComponent({ - type: SomeComponentWhichThrows, tag: 'some-component-with-Error', template: function(ctx: SomeComponentWhichThrows, cm: boolean) { throw(new Error('SomeComponentWhichThrows threw')); @@ -63,8 +61,7 @@ describe('renderer factory lifecycle', () => { logs.push('function_with_component'); if (cm) { T(0, 'bar'); - E(1, SomeComponent.ngComponentDef); - { D(2, SomeComponent.ngComponentDef.n(), SomeComponent.ngComponentDef); } + E(1, SomeComponent); e(); } SomeComponent.ngComponentDef.h(2, 1); @@ -123,7 +120,6 @@ describe('animation renderer factory', () => { class SomeComponent { static ngComponentDef = defineComponent({ - type: SomeComponent, tag: 'some-component', template: function(ctx: SomeComponent, cm: boolean) { if (cm) { @@ -140,7 +136,6 @@ describe('animation renderer factory', () => { eventLogs.push(`${event.fromState ? event.fromState : event.toState} - ${event.phaseName}`); } static ngComponentDef = defineComponent({ - type: SomeComponentWithAnimation, tag: 'some-component', template: function(ctx: SomeComponentWithAnimation, cm: boolean) { if (cm) {