提问者:小点点

在Angular 2中的模板内键入铸件


我正在从事Angular项目(Angular 4.0.0),在将抽象类的属性绑定到ngModel时遇到问题,因为我首先需要将其转换为实际的具体类,以便访问该属性。

i、 我有一个AbstractEvent类,这是一个具体的实现事件,它有一个布尔属性'acknowledged',我需要通过ngModel的双向绑定来设置一个复选框。

我当前在DOM中有以下元素:

<input type="checkbox" *ngIf="event.end" [(ngModel)]="(event as Event).acknowledged" 
                                          [disabled]="(event as Event).acknowledged">

不幸的是,这是抛出以下错误:

未捕获错误:模板分析错误:[(事件为事件)。已确认]

谷歌搜索似乎表明这可能是因为在模板中使用“as”时不支持使用它?虽然我对此不确定。

我也不知道如何在驱动模板的typescript文件中为它编写函数,因为这会破坏我需要的ngModel上的双向绑定。

如果有人有任何方法可以绕过这一点,或执行正确的角度模板类型铸造我会非常感激!


共3个答案

匿名用户

如果你不关心类型控制。

在Angular 8和更高版本中

[(ngModel)]="$any(event).acknowledged"

来自官方文件:https://angular.io/guide/template-typecheck#disabling-type-checking-using-any

@Component({
  selector: 'my-component',
  template: '{{$any(person).addresss.street}}'
})
class MyComponent {
  person?: Person;
}

匿名用户

这是不可能的,因为无法从模板中引用事件

as在模板绑定表达式中也不受支持) 您需要首先使其可用:

class MyComponent {
  EventType = Event;

那这个应该能行

[(ngModel)]="(event as EventType).acknowledged"

<罢工>

更新

class MyComponent {
  asEvent(val) : Event { return val; }

然后用它作为

[(ngModel)]="asEvent(event).acknowledged"

匿名用户

如前所述,使用基本方法调用将对性能产生影响。

更好的方法是使用管道,这两个方面你都能做到最好。只需定义一个铸管:

@Pipe({
  name: 'cast',
  pure: true
})
export class CastPipe implements PipeTransform {  
  transform(value: any, args?: any): Event {
    return value;
  }
}

然后在模板中,在需要强制转换时使用event|cast

这样,更改检测保持高效,并且键入是安全的(鉴于请求的类型更改当然是合理的)。

不幸的是,由于name属性的原因,我看不到一种方法可以使用此泛型,因此您必须为每种类型定义一个新管道。