本文介绍了如何让Angular2 RC1知道改变的DOM的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这实际上是从,使用一个更简单的用例。关于如何让Angular2知道有外部添加的包含Angular指令的DOM元素。在这种情况下,我添加一个新的点击按钮,其点击事件永远不会被绑定。 Imo我认为Zone会自动检测组件模板中的任何变化,显然它不会。任何人都可以使代码工作,而无需为按钮创建新的组件,并通过 DynamicLoaderComponent 加载它的巨大开销?



注意:我已经添加了 NgZone ChangeDetectorRef

以下是plunkr中完整示例的链接:



这是组件的相关摘录:



<$来自'@ angular / core'的$ {

@Component({
选择器:'我的')pre> import {Component,AfterViewInit,ChangeDetectorRef,NgZone,Renderer} app',
providers:[],
template:`
< div>
< p>< button on-click =clickMe()>作品< / button>< / p>

< div id =insert-here>< / div>

< / div>
`,
指令:[]
导出类App实现AfterViewInit {
构造函数(private ref:ChangeDetectorRef,private ngZone:NgZone,private renderer:Renderer){

}

clickMe(){
alert(Yay,it works);
}

ngAfterViewInit(){
let newButton = document.createElement(button);
newButton.setAttribute(on-click,clickMe());
let textNode = document.createTextNode(This does not);
newButton.appendChild(textNode);
document.getElementById(insert-here)。appendChild(newButton);

//请让我的按钮工作:
this.ref.detectChanges();
}

}


解决方案

区域根本不在乎DOM。区域只修补异步API,如 addEventListener() setTimeout(),...然后只检查模型变化。



Angular假定它负责DOM。当模型改变时,DOM更改为Angular,而不是相反。



没有办法使Angular创建用于匹配HTML的组件或指令,或动态添加HTML的解析绑定。 Angular只为HTML中添加了静态添加到组件的模板。



DynamicaComponentLoader (已弃用)或 ViewContainerRef.createComponent()是动态添加组件的方法。



可以使用容易的包装元素声明性地添加动态组件,如(还包含新的 ViewContainerRef.createComponent()的Plunker示例


This is actually a spin off from here, with a much simpler use case, though. It is about how to let Angular2 know that there are externally added DOM elements containing Angular directives. In this case, I add a new click button whose on-click event is never bound. Imo I thought Zone would automatically detect any changes in the templates of their components, obviously it doesn't. Is anyone able to make that code work without the immense overhead of creating a new component for the button and load it via DynamicLoaderComponent ?

Note: I've already added NgZone and ChangeDetectorRef to play around with. Neither worked for me.

Here is a link to the full example at plunkr: plnkr.co/edit/hf180P6nkxXtJDusPdLb

And this is an relevant excerpt from the component:

import {Component, AfterViewInit, ChangeDetectorRef, NgZone, Renderer} from '@angular/core'

@Component({
    selector: 'my-app',
providers: [],
template: `
<div>
<p><button on-click="clickMe()">This works</button></p>

<div id="insert-here"></div>

</div>
`,
directives: []
})
export class App implements AfterViewInit {
constructor(private ref:ChangeDetectorRef, private ngZone:NgZone, private renderer:Renderer) {

}

clickMe() {
alert("Yay, it works");
}

ngAfterViewInit() {
    let newButton = document.createElement("button");
    newButton.setAttribute("on-click","clickMe()");
    let textNode = document.createTextNode("This does not");
    newButton.appendChild(textNode);
    document.getElementById("insert-here").appendChild(newButton);

    // please make my button work:
    this.ref.detectChanges();
}

}
解决方案

Zone doesn't care about the DOM at all. Zone only patches async APIs like addEventListener(), setTimeout(), ... and then checks only the model for changes.

Angular assumes that it is in charge of the DOM. The DOM is updated by Angular when the model changed, not the other way around.

There is no way to make Angular create components or directives for matching HTML or resolve bindings for HTML added dynamically. Angular does this only for HTML added statically to the template of a component.

DynamicaComponentLoader (deprecated) or ViewContainerRef.createComponent() are the way to go for adding components dynamically.

You can use wrapper element that makes it easy to declaratively add dynamic components like explained in Angular 2 dynamic tabs with user-click chosen components (also contains a Plunker example for the new ViewContainerRef.createComponent()

这篇关于如何让Angular2 RC1知道改变的DOM的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-02 04:46