diff --git a/modules/angular2/src/compiler/view_compiler/view_binder.ts b/modules/angular2/src/compiler/view_compiler/view_binder.ts index 806ba523ed..1cd1136727 100644 --- a/modules/angular2/src/compiler/view_compiler/view_binder.ts +++ b/modules/angular2/src/compiler/view_compiler/view_binder.ts @@ -103,6 +103,7 @@ class ViewBinderVisitor implements TemplateAstVisitor { bindDirectiveDestroyLifecycleCallbacks(directiveAst.directive, directiveInstance, compileElement); }); + bindView(compileElement.embeddedView, ast.children); return null; } diff --git a/modules/angular2/src/compiler/view_compiler/view_builder.ts b/modules/angular2/src/compiler/view_compiler/view_builder.ts index c6abdb06e2..7fc3d3aeee 100644 --- a/modules/angular2/src/compiler/view_compiler/view_builder.ts +++ b/modules/angular2/src/compiler/view_compiler/view_builder.ts @@ -50,8 +50,6 @@ import { CompileTokenMetadata } from '../compile_metadata'; -import {bindView} from './view_binder'; - const IMPLICIT_TEMPLATE_VAR = '\$implicit'; const CLASS_ATTR = 'class'; const STYLE_ATTR = 'style'; @@ -65,28 +63,28 @@ export class ViewCompileDependency { } export function buildView(view: CompileView, template: TemplateAst[], - targetDependencies: ViewCompileDependency[], - targetStatements: o.Statement[]): number { - var builderVisitor = new ViewBuilderVisitor(view, targetDependencies, targetStatements); + targetDependencies: ViewCompileDependency[]): number { + var builderVisitor = new ViewBuilderVisitor(view, targetDependencies); templateVisitAll(builderVisitor, template, view.declarationElement.isNull() ? view.declarationElement : view.declarationElement.parent); - // Need to separate binding from creation to be able to refer to - // variables that have been declared after usage. - bindView(view, template); - view.afterNodes(); - - createViewTopLevelStmts(view, targetStatements); - return builderVisitor.nestedViewCount; } +export function finishView(view: CompileView, targetStatements: o.Statement[]) { + view.afterNodes(); + createViewTopLevelStmts(view, targetStatements); + view.nodes.forEach((node) => { + if (node instanceof CompileElement && node.hasEmbeddedView) { + finishView(node.embeddedView, targetStatements); + } + }); +} class ViewBuilderVisitor implements TemplateAstVisitor { nestedViewCount: number = 0; - constructor(public view: CompileView, public targetDependencies: ViewCompileDependency[], - public targetStatements: o.Statement[]) {} + constructor(public view: CompileView, public targetDependencies: ViewCompileDependency[]) {} private _isRootNode(parent: CompileElement): boolean { return parent.view !== this.view; } @@ -284,8 +282,7 @@ class ViewBuilderVisitor implements TemplateAstVisitor { var embeddedView = new CompileView( this.view.component, this.view.genConfig, this.view.pipeMetas, o.NULL_EXPR, this.view.viewIndex + this.nestedViewCount, compileElement, templateVariableBindings); - this.nestedViewCount += - buildView(embeddedView, ast.children, this.targetDependencies, this.targetStatements); + this.nestedViewCount += buildView(embeddedView, ast.children, this.targetDependencies); compileElement.beforeChildren(); this._addRootNodeAndProject(compileElement, ast.ngContentIndex, parent); diff --git a/modules/angular2/src/compiler/view_compiler/view_compiler.ts b/modules/angular2/src/compiler/view_compiler/view_compiler.ts index 39cc3e7169..ae64c4a953 100644 --- a/modules/angular2/src/compiler/view_compiler/view_compiler.ts +++ b/modules/angular2/src/compiler/view_compiler/view_compiler.ts @@ -3,7 +3,8 @@ import {Injectable} from 'angular2/src/core/di'; import * as o from '../output/output_ast'; import {CompileElement} from './compile_element'; import {CompileView} from './compile_view'; -import {buildView, ViewCompileDependency} from './view_builder'; +import {buildView, finishView, ViewCompileDependency} from './view_builder'; +import {bindView} from './view_binder'; import {CompileDirectiveMetadata, CompilePipeMetadata} from '../compile_metadata'; @@ -25,7 +26,12 @@ export class ViewCompiler { var dependencies = []; var view = new CompileView(component, this._genConfig, pipes, styles, 0, CompileElement.createNull(), []); - buildView(view, template, dependencies, statements); + buildView(view, template, dependencies); + // Need to separate binding from creation to be able to refer to + // variables that have been declared after usage. + bindView(view, template); + finishView(view, statements); + return new ViewCompileResult(statements, view.viewFactory.name, dependencies); } } diff --git a/modules/angular2/test/core/linker/integration_spec.ts b/modules/angular2/test/core/linker/integration_spec.ts index 0635c369d6..560ca2715f 100644 --- a/modules/angular2/test/core/linker/integration_spec.ts +++ b/modules/angular2/test/core/linker/integration_spec.ts @@ -587,18 +587,16 @@ function declareTests(isJit: boolean) { (tcb: TestComponentBuilder, async) => { tcb.overrideView( MyComp, new ViewMetadata({ - template: '

{{alice.ctxProp}}

', - directives: [ChildComp] + template: + '|{{alice.ctxProp}}|', + directives: [ChildComp, NgIf] })) .createAsync(MyComp) .then((fixture) => { fixture.detectChanges(); - expect(fixture.debugElement.nativeElement) - .toHaveText('hellohello'); // this first one is the - // component, the second one is - // the text binding + expect(fixture.debugElement.nativeElement).toHaveText('hello|hello|hello'); async.done(); })}));