javascript - 使用 Angular (v4) AnimationBuilder 使宽度无响应

标签 javascript angular typescript angular-animations

@angular/animations: v4.4.6

我的目标是使用AnimationBuilder 创建一个简单的水平打开和关闭动画。除了动画元素的宽度变得固定之外,我大部分时间都在工作。使用触发器实现相同的动画效果如预期,并且宽度对不同的视口(viewport)尺寸保持响应。

我有一个运行示例 here .

如您所见,如果您调整视口(viewport)的宽度,由 AnimationBuilder 设置动画的 div 的宽度不会相应调整。但是使用动画触发器的 div 的宽度会。

如何使用 AnimationBuilder 才能获得与使用触发器完全相同的结果?

您可以在上面的链接中查看和编辑代码,但我将其复制在下面以供引用:

应用程序组件.ts

import { Component, ViewChild, ElementRef, AfterViewInit } from '@angular/core';
import { trigger, state, style, transition, animate, AnimationBuilder, AnimationPlayer } from '@angular/animations';

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ],
  animations: [
    trigger('collapse', [
      state('open', style({ width: '*' })),
      state('close', style({ width: 0 })),
      transition('open => close', [
        style({ width: '*' }),
        animate(200, style({ width: 0 }))
      ]),
      transition('close => open', [
        style({ width: 0 }),
        animate(200, style({ width: '*' }))
      ])
    ])
  ]
})
export class AppComponent implements AfterViewInit  {
  isOpen = true;
  get collapseState() {
    return this.isOpen ? 'open' : 'close';
  }
  @ViewChild('withBuilder') elementRef: ElementRef;
  private openPlayer: AnimationPlayer;
  private closePlayer: AnimationPlayer;

  constructor(private animationBuilder: AnimationBuilder) { }

  ngAfterViewInit() {
    this.openPlayer = this.animationBuilder
      .build([
        style({ width: 0 }),
        animate(200, style({ width: '*' }))
      ])
      .create(this.elementRef.nativeElement);
    this.closePlayer = this.animationBuilder
      .build([
        style({ width: '*' }),
        animate(200, style({ width: 0 }))
      ])
      .create(this.elementRef.nativeElement);

    if (this.isOpen) {
      this.openPlayer.finish();
    } else {
      this.closePlayer.finish();
    }
  }

  toggle() {
    if (this.isOpen) {
      this.closePlayer.play();
      this.openPlayer.reset();
    } else {
      this.openPlayer.play();
      this.closePlayer.reset();
    }
    this.isOpen = !this.isOpen;
  }
}

app.component.html

<button (click)="toggle()">Toggle</button>
<h2>Without AnimationBuilder:</h2>
<div class="container" [@collapse]="collapseState"></div>
<h2>With AnimationBuilder:</h2>
<div class="container" #withBuilder></div>

应用程序组件.css

.container {
  border: 2px solid red;
  height: 200px;
}

最佳答案

AnimationBuilder 使用不处理元素状态的 TimelineAnimationEngine。全宽大小由仍在工作的动画播放器固定。

如您所见,注释中的折叠触发器删除了动画播放器并添加了 style="width: 0px"。

这是一个直接处理元素状态的可行解决方案。但它看起来很脏。并且它不处理改变方向的情况(当上一个动画还在播放时)

@ViewChild('withBuilder') elementRef: ElementRef;

isOpen = true;

private closeAnimation: AnimationFactory;
private openAnimation: AnimationFactory;

constructor(private styler: StylerComponent,
    private animationBuilder: AnimationBuilder,
    private renderer: Renderer2) {
  this.openAnimation = this.animationBuilder
      .build([
        style({width: 0}),
        animate(200, style({width: '*'})),
      ]);
  this.closeAnimation = this.animationBuilder
      .build([
        style({width: '*'}),
        animate(200, style({width: 0})),
      ]);
}

toggle() {
  console.log('toggle', this.isOpen);
  const el = this.elementRef.nativeElement;
  let player: AnimationPlayer;
  if (this.isOpen) {
    player = this.closeAnimation.create(el);
    player.onDone(() => {
      this.renderer.setStyle(el, 'width', 0);
    });
  } else {
    this.renderer.removeStyle(el, 'width');
    player = this.openAnimation.create(el);
  }
  player.onDone(() => {
    player.destroy();
  });
  player.play();
  this.isOpen = !this.isOpen;
}

关于javascript - 使用 Angular (v4) AnimationBuilder 使宽度无响应,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46943225/

相关文章:

javascript - 为什么从 Google Chrome 扩展中的 JavaScript 注入(inject)中删除了脚本标签?

javascript - 如何使用字符串创建 DOM 元素来使 Angular 单击绑定(bind)起作用?

Angular 10 : Buffer is not defined

javascript - 使用文本掩码指令进行正则表达式月份验证

javascript - 在 typescript 中使用express中的回调函数数组

javascript - 如何在 Emacs 的 javascript 模式下设置 2 个空格缩进?

javascript - 如何在中心外自定义谷歌图表标签数据

javascript - 如何使用 Firebug 或类似工具调试 JavaScript/jQuery 事件绑定(bind)?

html - 在typeScript angular 2中解码html

javascript - 在 angular2 中制作我自己的记录器