问题描述本文涉及的代码位置:https://github.com/wangzixi-d...我有一个Angular可以接受contentprojection的Component:具体投影内容,由ng-container和命令ngTemplateOutlet指定。ngTemplateOutlet的来源是content,是Component通过如下内容查询得到的结果:@ContentChild(ZippyContentDirective)content!:ZippyContentDirective;从语义上讲,在消费app-example-zippy的Component的HTML模板中,只有ng-template元素设置了自定义指令ZippyContentDirective对应的属性选择器,那么ng-template中的内容就会自动投射到应用程序示例zippy。但是在运行时,我们无法观察到上图中高亮显示的第四行的内容,而是在控制台看到如下错误信息:ERRORTypeError:Cannotreadpropertiesofundefined(reading'templateRef')atZippyComponent_div_1_Template(template.html:3:19)atexecuteTemplate(core.js:7511:9)atrefreshView(core.js:7380:13)atrefreshEmbeddedViews(core.js:8481:17)atrefreshView(core.js:7404:9))atrefreshComponent(core.js:8527:13)atrefreshChildComponents(core.js:7186:9)atrefreshView(core.js:7430:13)atrefreshComponent(core.js:8527:13)atrefreshChildComponents(core.js:7186:9)问题分析content的内容未定义,说明内容查询执行失败:app-example-zippy里面的ng-template,使用的属性Directive与ZippyContentDirective定义的selector不一致,如下图:修改后问题消失。总结在渲染时,Ivy需要跟踪三种数据:Template、LogicalTree和RenderTree。在我们的许多数据结构中,为简洁起见,这三个概念缩写为T、L和R前缀。模板是源代码的解析版本。它包含以Ivy指令和有关组件/指令的元数据的形式呈现模板的指令。如果你能在源代码中找到它,模板数据结构中的相应字段也会存在。模板信息的存在与其中的代码是否被执行无关。例如,即使条件为假,*ngIf之后的模板仍将具有此模板信息)。在Ivy中,模板信息存储在TView(以及TData和TNode)数据结构中。这些数据结构一起提供了Ivy在运行时需要的关于模板的所有静态信息。静态这个词很重要,可以将它与Ivy中另一个重要的逻辑视图概念区分开来。
