【问题标题】:Angular ngIf use @Output() result for conditionAngular ngIf 使用 @Output() 结果作为条件
【发布时间】:2017-11-07 12:30:55
【问题描述】:

我有一个 card-list 组件,它应该显示 card 组件或 card-edit 组件的元素,具体取决于 wasEditClicked 是否开启卡片组件是真还是假。

卡片列表组件的模板如下:

<div class="loop" *ngFor="let guest of guests">
    <div *ngIf="true;else elseBlock">
        <app-guest-card [guest]="guest"></app-guest-card>
    </div>
    <ng-template #elseBlock>
        <app-guest-card-edit [guest]="guest"></app-guest-card-edit>
    </ng-template>
</div>

我想将 ngIf 条件绑定到 wasEditClicked 布尔值。

My CardComponent(不同于上面显示的 Card-List 组件)如下所示:

export class GuestCardComponent implements OnInit {

  @Input() public guest: Guest;
  @Output() public wasEditClicked = new EventEmitter<boolean>();

  constructor() { }

  ngOnInit() {
  }

  onEdit() {
    this.wasEditClicked.emit(true);
  }

}

【问题讨论】:

  • ngOnInit(): void { this.isWasEditClicked = this.wasEditClicked .observers.length &gt; 0; }

标签: angular


【解决方案1】:

我会创建一个“包装器”组件来保存卡片的编辑和只读版本。它将具有 guest 的 Input 一个 editClicked 的属性和一个名为 aFunction 的函数,该函数采用布尔值。在 aFunction 中,您将 editClicked 设置为 true/false。所以是这样的:

<div>
 <app-guest-card *ngIf="editClicked;else #elseBlock" [guest]="guest" 
  (wasEditClicked)="aFunction($event)">
 </app-guest-card>
 <ng-template #elseBlock>
    <app-guest-card-edit [guest]="guest"></app-guest-card-edit>
 </ng-template>
</div>

那么在您的顶级组件中它将是

<div *ngFor="let guest of guests">
  <app-wrapper [guest]="guest"></app-wrapper>
</div>

这允许一个组件只需要担心一张客人卡片而不是整个列表。

【讨论】:

    【解决方案2】:

    你用错了方法:给你的条件一个变量,比如说showIt

    <div class="loop" *ngFor="let guest of guests">
        <div *ngIf="showIt;else elseBlock">
            <app-guest-card [guest]="guest" (onEdit)="showIt = $event"></app-guest-card>
        </div>
        <ng-template #elseBlock>
            <app-guest-card-edit [guest]="guest" (onEdit)="showIt = $event"></app-guest-card-edit>
        </ng-template>
    </div>
    

    然后设置点击时的值:

    export class GuestCardComponent implements OnInit {
      @Input() public guest: Guest;
      @Output() public wasEditClicked = new EventEmitter<boolean>();
    
      constructor() { }
    
      ngOnInit() {}
    
      onEdit() {
        this.wasEditClicked.emit(true);
      }
    
    }
    

    【讨论】:

    • 您在 GuestCard 中定义了 showIt,但尝试在 Card-List 中的条件下使用它。我认为那行不通
    • 我的错,我读错了你的代码!我编辑了我的答案,请随意查看
    • 你在card-list component.ts文件中定义showIt吗?我的 ngIf 语句说变量未定义
    • 你甚至不应该定义它,但如果它给你一个错误,你在 notGuestCardComponent 的组件中定义它
    • 这也行不通。 (onEdit)="showIt = $event" 调用 Card 组件中的 onEdit 时似乎没有做任何事情
    【解决方案3】:

    我要添加另一个答案,因为它是另一种解决方案。

    您可以做一个双向绑定,例如 ngModel。

    这是你的做法:

    let emitValue = false;
    @Output() public emitChange = new EventEmitter<boolean>();
    
    @Input() get emit() { return this.emitValue; }
    set emit(value: boolean) { this.emitValue = value; this.emitChange.emit(this.emitValue); }
    

    现在在你的 HTML 中你可以做的是

    <app-guest-card [guest]="guest" [(emit)]="showIt"></app-guest-card>
    

    【讨论】:

    • 当然,您仍然在 *ngIf 中使用 showIt
    • 我无法绑定到“emit”,因为它不是“app-guest-card”的已知属性。
    • 我的错,我不能在我的电脑上测试 Angular 代码,我是靠记忆写的。我更新了我的代码,欢迎再次查看。
    • 那还是不行。错误:装饰器不能应用于同名的多个 get/set 访问器。
    • 2 / 3 ... 现在应该可以了。如果没有,请参阅this page
    猜你喜欢
    • 1970-01-01
    • 2017-08-18
    • 2019-03-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-13
    • 2018-03-02
    • 1970-01-01
    相关资源
    最近更新 更多