【问题标题】:Angular Animation: animate only added item in ngFor list角度动画:动画仅在 ngFor 列表中添加项目
【发布时间】:2020-11-02 13:00:57
【问题描述】:

我在ngFor 中有一个数组项列表。我有一个简单的按钮,可以将一个项目添加到数组中。我想在添加项目时对项目应用动画,但尽管这可行,但页面上已经存在的列表项组会在页面加载时获得动画。如何将动画限制在新添加的项目上?这是在 Angular 10 中。

我发了stripped-down Stackblitz

animations: [
    trigger("myTrigger", [
      state(
        "fadeInFlash",
        style({
          opacity: "1"
        })
      ),
      transition("void => *", [
        style({ opacity: "0", transform: "translateY(20px)" }),
        animate("500ms")
      ])
    ])
  ]
<p>
  <button (click)="addItem()">Add Item</button>
</p>

<ul>
  <li *ngFor="let item of items" [@myTrigger]='state'>{{item}}</li>
</ul>

【问题讨论】:

    标签: javascript angular animation


    【解决方案1】:

    这是 stackbliz 的解决方案链接到您的问题,我刚刚使用了 Angular 动画的禁用属性。如果 flag 变量为 true,则动画将被禁用,如果为 false,则启用动画,我们在页面初始化后加载所有内容,以便动画的触发器仅适用于推送操作。

    Stackbliz

    Reference Link

    ngAfterViewInit Reference link

    编辑:为避免控制台错误ExpressionChangedAfterItHasBeenCheckedError,请在添加项目时启用动画,如下所示。甚至stackbliz代码也相应更新了,以供参考。

        addItem() {
            if (this.flag) {
              // Enabling Animation
              this.flag = !this.flag;
            }
            this.items.push("another item");
          }
    

    app.component.ts

        import { Component } from "@angular/core";
        import {
          animate,
          animateChild,
          group,
          query,
          style,
          transition,
          trigger,
          state
        } from "@angular/animations";
        
        @Component({
          selector: "my-app",
          templateUrl: "./app.component.html",
          styleUrls: ["./app.component.css"],
          animations: [
            trigger("myTrigger", [
              state(
                "fadeInFlash",
                style({
                  opacity: "1"
                })
              ),
              transition("void => *", [
                style({ opacity: "0", transform: "translateY(20px)" }),
                animate("500ms")
              ])
            ])
          ]
        })
        export class AppComponent {
          flag: boolean = true;
          items = ["item 1", "item 2", "item 3"];
          state: string = "fadeInFlash";
        
          addItem() {
            if (this.flag) {
              this.flag = !this.flag;
            }
            this.items.push("another item");
          }
        }
    

    app.component.html

        <p>
            Start editing to see some magic happen :)
        </p>
        
        
        
        <p>
            <button (click)="addItem()">Add Item</button>
        </p>
        
        <ul>
            <li *ngFor="let item of items" [@.disabled]="flag" [@myTrigger]='state'> 
            {{item}}</li>
        </ul>
    

    【讨论】:

    • 谢谢。但是有一个控制台错误:ERROR Error: ExpressionChangedAfterItHasBeenCheckedError: Expression has changed after it was checked. Previous value for '@.disabled': 'true'. Current value: 'false'.
    • 最欢迎。请检查更新的答案,该答案通过不使用生命周期挂钩来解决控制台错误问题。关于错误原因,您可以参考stackoverflow.com/questions/43375532/…
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-07-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多