Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/typescript/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Angular 2如何获取Angular以检测在Angular之外所做的更改?_Javascript_Typescript_Angular_Angular2 Changedetection - Fatal编程技术网

Javascript Angular 2如何获取Angular以检测在Angular之外所做的更改?

Javascript Angular 2如何获取Angular以检测在Angular之外所做的更改?,javascript,typescript,angular,angular2-changedetection,Javascript,Typescript,Angular,Angular2 Changedetection,我试图创建一个简单的示例项目来测试angular 2更改检测机制:我在主索引页的脚本标记中创建一个纯javascript对象。它包含以下内容: var Tryout = {}; Tryout.text = "Original text here"; Tryout.printme = function(){ console.log(Tryout.text); } Tryout.changeme

我试图创建一个简单的示例项目来测试angular 2更改检测机制:我在主索引页的脚本标记中创建一个纯javascript对象。它包含以下内容:

        var Tryout = {};
        Tryout.text = "Original text here";
        Tryout.printme = function(){
            console.log(Tryout.text);
        }
        Tryout.changeme = function(){
            Tryout.text = "Change was made";
        }
一个函数用于控制台记录日志,另一个函数用于更改文本属性

现在在Angular 2中,代码如下所示:

import {Component} from "angular2/core"

@Component({
    selector: 'my-app',
    template: `
        <h1>{{TryoutRef.text}}</h1>
        <input type="text" [(ngModel)]="TryoutRef.text">
        <button (click)="consoleLogMe()">Console Log</button>
        <button (click)="changeMe()">Change me inside</button>
    `
})

export class MyApp{

    TryoutRef:any = Tryout;
    constructor(){
    }
    changeMe(){
        this.TryoutRef.changeme();
    }
    consoleLogMe(){
        console.log(this.TryoutRef.text);
    }

}
declare var Tryout:string;
从“angular2/core”导入{Component}
@组成部分({
选择器:“我的应用程序”,
模板:`
{{TryoutRef.text}
控制台日志
在里面给我换衣服
`
})
导出类MyApp{
试用期参考:任何=试用期;
构造函数(){
}
changeMe(){
this.TryoutRef.changeme();
}
consoleLogMe(){
console.log(this.TryoutRef.text);
}
}
声明变量试用:字符串;
我想做的是: 当我用onclick调用函数Tryout.printme()时(完全在angular之外),我希望angular能够检测到更改并更新屏幕

我成功地做到了这一点:当我从组件调用Tryout.printme()时(changeme()函数调用Tryout.printme()),Angular检测到更改并更新UI,这很好。此外,当我从外部angular更改并从angular调用consoleLogMe()时,它会记录更改的文本并更新UI

我想我需要在Angular运行的同一区域中执行Tryout.changeme()。有什么想法吗?我有一个用纯javascript/jquery完成的大项目,现在我需要慢慢地将handlebar模板重写为angular2组件,而不涉及模型(还没有)。为此,我需要强制模型在与angular相同的区域中执行

如果我想在Angular 1中做类似的事情,我只需要$scope。$apply就行了

下面是示例中的gif:


您可以通过在Angular应用程序中导出
NgZone
来完成此操作。 通常,您应该在Angular内部执行所有操作,但是如果您真的想在Angular之外执行逻辑,您需要获得正确的
区域,正如您所说的那样

这个技巧是滥用Angular的依赖项注入,并将注入的
区域
挂在
窗口
对象上,如图所示。声明对
NgZone
的依赖项,并将其分配给
window.zoneImpl
进行导出

//our root app component
import {Component, NgZone} from 'angular2/core'

@Component({
  selector: 'my-app',
  template: `
    <div>
      <h2>Hello {{name}}</h2>

    </div>
  `,
})
export class App {
  constructor(zone: NgZone) {
    this.name = 'Angular2'
    window.app = this
    window.zoneImpl = zone
  }
}
//我们的根应用程序组件
从'angular2/core'导入{Component,NgZone}
@组成部分({
选择器:“我的应用程序”,
模板:`
你好{{name}
`,
})
导出类应用程序{
建造商(区域:NgZone){
this.name='Angular2'
window.app=这个
window.zoneImpl=zone
}
}
角度引导后,应该有一个
zoneImpl
全局变量。您可以使用
run
方法启动

zoneImpl.run(()=>window.app.name=“new name!”)


为什么组件文件中有
Tryout
类型
string
?另一个快速而难看的攻击是,在引导后,使用
setTimeout
使Angular知道您的代码
NgZone
已修补此全局功能。请检查plunkr(消息:“预览已过期或项目不存在”)是否已过期。警告一句:确保(如上所示)将您的window.zoneImpl变量命名为window.zone以外的其他名称。显然,Angular使用window.zone,如果写入它,它会把事情搞砸。另请参见:在Angular内部(因此在Angular区域内部)设置事件侦听器。然后在角度区域之外进行更改时触发该事件。我只需将NgZone注入到所有组件中,并将所有外部回调封装到
NgZone中。运行(()=>{doSomething();});