【问题标题】:ViewChild binding with compiler checking带有编译器检查的 ViewChild 绑定
【发布时间】:2018-06-05 00:06:49
【问题描述】:

我使用 ViewChild 的方式如下:

@Component({
    selector: 'demo',
    template: `<input type="text" #firstnameCtrl [(ngModel)]="firstname" />`
})
export class DemoComponent {
    public firstname: string;
    @ViewChild('firstnameCtrl') firstElementCtrl: ElementRef;
}

如果有人在模板中将导出的变量 #firstnameCtrl 更改为 #firstnameElement,则应用程序已损坏,但未引发编译器(也未在 AOT 中)。

那么有没有一种首选的方法来以更节省的方式绑定 ViewChild?

谢谢!

【问题讨论】:

    标签: angular viewchild


    【解决方案1】:

    https://angular.io/api/core/ViewChild 显示了通过对象绑定孩子的示例。 把代码复制到这里,以防万一以后链接失效:

    您可以使用 ViewChild 从视图 DOM 中获取与选择器匹配的第一个元素或指令。如果视图 DOM 发生变化,并且新的子元素与选择器匹配,则属性将被更新。

    在调用 ngAfterViewInit 回调之前设置视图查询。

    元数据属性:

    selector - 用于查询的指令类型或名称。 read - 从查询的元素中读取不同的标记。

    import {Component, Directive, Input, ViewChild} from '@angular/core';
    @Directive({selector: 'pane'})
    export class Pane {
       @Input() id: string;
    }
    
    @Component({
      selector: 'example-app',
      template: `
        <pane id="1" *ngIf="shouldShow"></pane>
        <pane id="2" *ngIf="!shouldShow"></pane>
    
        <button (click)="toggle()">Toggle</button>
    
        <div>Selected: {{selectedPane}}</div> 
      `,
    })
    export class ViewChildComp {
      @ViewChild(Pane)
      set pane(v: Pane) {
        setTimeout(() => { this.selectedPane = v.id; }, 0);
      }
      selectedPane: string = '';
      shouldShow = true;
      toggle() { this.shouldShow = !this.shouldShow; }
    }
    

    【讨论】:

    • 这不是 100% 干净的解决方案,因为如果更改了 id 属性,那么应用程序将被破坏而没有任何编译器错误。所以我需要一种类似于 FormControl 的方法(例如 )。因为我使用的是模板驱动方法,所以我需要一个 ViewChild 的解决方案。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-07-05
    • 2019-06-18
    • 2017-12-04
    • 1970-01-01
    • 1970-01-01
    • 2017-12-15
    • 1970-01-01
    相关资源
    最近更新 更多