垫子扩展指示器的旋转由this animation 处理。在那里可以看到它很简单rotate(180deg)(顺时针180度)。指示器最初有rotate(45deg),当面板关闭时默认显示向下图标,当面板以顺时针动画打开时显示向上图标。
当你应用旋转时;
.mat-expansion-indicator::after {
transform: rotate(225deg) !important;
}
图标最初在面板关闭时向上旋转,单击时它顺时针旋转 180 度。此时,您无法在关闭时显示向下图标,在打开时无法显示向上图标,因为 rotate(225deg) 如果您更改它,您会因为动画顺时针开始而松动向内转动,但我们需要完全相反。
最终不可能在不覆盖默认动画的情况下进行逆时针旋转。不幸的是,Angular Material 没有任何机制来覆盖默认动画 as seen here 。
所以我的解决方案是完全禁用 mat-expansion-panel-header 上的默认动画并实现一个模仿 this animation 但逆时针方向的自定义指令。
首先禁用mat-expansion-panel-header上的默认动画;
<mat-expansion-panel-header [@.disabled]="true">
然后在styles.css 中创建新动画,并将same timing and behavior 作为默认动画。
@keyframes inwards-open {
0% { transform: rotate(0deg); }
100% { transform: rotate(-135deg); }
}
@keyframes inwards-close {
0% { transform: rotate(-135deg); }
100% { transform: rotate(0deg); }
}
.openAnimate {
animation: inwards-open 225ms cubic-bezier(0.4,0.0,0.2,1) !important;
}
.closeAnimate {
animation: inwards-close 225ms cubic-bezier(0.4,0.0,0.2,1) !important;
}
并实现一个自定义指令,根据面板打开/关闭事件处理动画状态
import { Directive, ElementRef, HostListener, AfterViewInit, OnDestroy } from '@angular/core';
import { fromEvent, Subscription } from 'rxjs';
@Directive({
selector: '[appCustomMatExpansionToggle]'
})
export class CustomMatExpansionToggleDirective implements AfterViewInit, OnDestroy {
private elem: HTMLSpanElement;
private uns: Subscription;
constructor(private elRef: ElementRef) {}
ngAfterViewInit() {
this.elem = this.elRef.nativeElement.querySelector(".mat-expansion-indicator");
this.uns = fromEvent(this.elem, 'animationend').subscribe(() => {
this.elem.classList.remove("openAnimate");
this.elem.classList.remove("closeAnimate");
});
}
@HostListener("opened")
onOpen() {
this.elem.classList.add("openAnimate");
}
@HostListener("closed")
onClose() {
this.elem.classList.add("closeAnimate");
}
ngOnDestroy() {
this.uns.unsubscribe();
}
}
最后将自定义指令应用到mat-expansion-panel
<mat-expansion-panel appCustomMatExpansionToggle>
这是一个工作演示https://stackblitz.com/edit/indicatorrotation-mp73uh