Skip to content

Commit 27a08cc

Browse files
crisbetommalerba
authored andcommitted
fix(tabs): disable all animations when using NoopAnimationsModule (#11395)
Currently some animations in the tab components don't get disabled, when using the `NoopAnimationsModule`, because they don't go through the Angular animations. These changes ensure that everything will be disabled. Fixes #10590.
1 parent 86c626a commit 27a08cc

File tree

10 files changed

+45
-13
lines changed

10 files changed

+45
-13
lines changed

src/material/tabs/_tabs-common.scss

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
@import '../core/style/variables';
2+
@import '../core/style/noop-animation';
23
@import '../../cdk/a11y/a11y';
34

45
$mat-tab-bar-height: 48px !default;
@@ -61,6 +62,7 @@ $mat-tab-animation-duration: 500ms !default;
6162
@mixin ink-bar {
6263
$height: 2px;
6364

65+
@include _noop-animation();
6466
position: absolute;
6567
bottom: 0;
6668
height: $height;

src/material/tabs/ink-bar.ts

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,8 @@
66
* found in the LICENSE file at https://angular.io/license
77
*/
88

9-
import {Directive, ElementRef, Inject, InjectionToken, NgZone} from '@angular/core';
9+
import {Directive, ElementRef, Inject, InjectionToken, NgZone, Optional} from '@angular/core';
10+
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
1011

1112

1213
/**
@@ -46,13 +47,15 @@ export function _MAT_INK_BAR_POSITIONER_FACTORY(): _MatInkBarPositioner {
4647
selector: 'mat-ink-bar',
4748
host: {
4849
'class': 'mat-ink-bar',
50+
'[class._mat-animation-noopable]': `_animationMode === 'NoopAnimations'`,
4951
},
5052
})
5153
export class MatInkBar {
5254
constructor(
5355
private _elementRef: ElementRef<HTMLElement>,
5456
private _ngZone: NgZone,
55-
@Inject(_MAT_INK_BAR_POSITIONER) private _inkBarPositioner: _MatInkBarPositioner) { }
57+
@Inject(_MAT_INK_BAR_POSITIONER) private _inkBarPositioner: _MatInkBarPositioner,
58+
@Optional() @Inject(ANIMATION_MODULE_TYPE) public _animationMode?: string) { }
5659

5760
/**
5861
* Calculates the styles from the provided element in order to align the ink-bar to that element.

src/material/tabs/tab-group.html

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,10 @@
3131
</div>
3232
</mat-tab-header>
3333

34-
<div class="mat-tab-body-wrapper" #tabBodyWrapper>
34+
<div
35+
class="mat-tab-body-wrapper"
36+
[class._mat-animation-noopable]="_animationMode === 'NoopAnimations'"
37+
#tabBodyWrapper>
3538
<mat-tab-body role="tabpanel"
3639
*ngFor="let tab of _tabs; let i = index"
3740
[id]="_getTabContentId(i)"

src/material/tabs/tab-group.scss

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
@import '../core/style/variables';
22
@import '../core/style/layout-common';
3+
@import '../core/style/noop-animation';
34
@import './tabs-common';
45

56
.mat-tab-group {
@@ -37,6 +38,7 @@
3738

3839
// The bottom section of the view; contains the tab bodies
3940
.mat-tab-body-wrapper {
41+
@include _noop-animation();
4042
position: relative;
4143
overflow: hidden;
4244
display: flex;

src/material/tabs/tab-group.ts

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,9 @@ import {
2222
QueryList,
2323
ViewChild,
2424
ViewEncapsulation,
25-
InjectionToken,
26-
Inject,
2725
Optional,
26+
Inject,
27+
InjectionToken,
2828
} from '@angular/core';
2929
import {
3030
CanColor,
@@ -38,6 +38,7 @@ import {
3838
import {merge, Subscription} from 'rxjs';
3939
import {MatTab} from './tab';
4040
import {MatTabHeader} from './tab-header';
41+
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
4142

4243

4344
/** Used to generate unique ID's for each tab component */
@@ -171,7 +172,8 @@ export class MatTabGroup extends _MatTabGroupMixinBase implements AfterContentIn
171172

172173
constructor(elementRef: ElementRef,
173174
private _changeDetectorRef: ChangeDetectorRef,
174-
@Inject(MAT_TABS_CONFIG) @Optional() defaultConfig?: MatTabsConfig) {
175+
@Inject(MAT_TABS_CONFIG) @Optional() defaultConfig?: MatTabsConfig,
176+
@Optional() @Inject(ANIMATION_MODULE_TYPE) public _animationMode?: string) {
175177
super(elementRef);
176178
this._groupId = nextId++;
177179
this.animationDuration = defaultConfig && defaultConfig.animationDuration ?

src/material/tabs/tab-header.html

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,12 @@
1111

1212
<div class="mat-tab-label-container" #tabListContainer
1313
(keydown)="_handleKeydown($event)">
14-
<div class="mat-tab-list" #tabList role="tablist" (cdkObserveContent)="_onContentChanges()">
14+
<div
15+
class="mat-tab-list"
16+
[class._mat-animation-noopable]="_animationMode === 'NoopAnimations'"
17+
#tabList
18+
role="tablist"
19+
(cdkObserveContent)="_onContentChanges()">
1520
<div class="mat-tab-labels">
1621
<ng-content></ng-content>
1722
</div>

src/material/tabs/tab-header.scss

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
@import '../core/style/variables';
22
@import '../core/style/layout-common';
33
@import '../core/style/vendor-prefixes';
4+
@import '../core/style/noop-animation';
45
@import './tabs-common';
56

67
.mat-tab-header {
@@ -79,6 +80,7 @@
7980
}
8081

8182
.mat-tab-list {
83+
@include _noop-animation();
8284
flex-grow: 1;
8385
position: relative;
8486
transition: transform 500ms cubic-bezier(0.35, 0, 0.25, 1);

src/material/tabs/tab-header.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ import {
2121
EventEmitter,
2222
Input,
2323
NgZone,
24+
Inject,
2425
OnDestroy,
2526
Optional,
2627
Output,
@@ -36,6 +37,7 @@ import {MatInkBar} from './ink-bar';
3637
import {MatTabLabelWrapper} from './tab-label-wrapper';
3738
import {FocusKeyManager} from '@angular/cdk/a11y';
3839
import {Platform, normalizePassiveListenerOptions} from '@angular/cdk/platform';
40+
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
3941

4042

4143
/** Config used to bind passive event listeners */
@@ -165,7 +167,9 @@ export class MatTabHeader extends _MatTabHeaderMixinBase
165167
private _viewportRuler: ViewportRuler,
166168
@Optional() private _dir: Directionality,
167169
private _ngZone: NgZone,
168-
private _platform: Platform) {
170+
private _platform: Platform,
171+
// @breaking-change 9.0.0 `_animationMode` parameter to be made required.
172+
@Optional() @Inject(ANIMATION_MODULE_TYPE) public _animationMode?: string) {
169173
super();
170174

171175
// Bind the `mouseleave` event on the outside since it doesn't change anything in the view.

src/material/tabs/tab-nav-bar/tab-nav-bar.ts

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ import {merge, of as observableOf, Subject} from 'rxjs';
4747
import {takeUntil} from 'rxjs/operators';
4848
import {MatInkBar} from '../ink-bar';
4949
import {FocusMonitor} from '@angular/cdk/a11y';
50+
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
5051

5152

5253
// Boilerplate for applying mixins to MatTabNav.
@@ -222,7 +223,8 @@ export class MatTabLink extends _MatTabLinkMixinBase
222223
private _tabNavBar: MatTabNav, public _elementRef: ElementRef, ngZone: NgZone,
223224
platform: Platform,
224225
@Optional() @Inject(MAT_RIPPLE_GLOBAL_OPTIONS) globalRippleOptions: RippleGlobalOptions|null,
225-
@Attribute('tabindex') tabIndex: string, private _focusMonitor: FocusMonitor) {
226+
@Attribute('tabindex') tabIndex: string, private _focusMonitor: FocusMonitor,
227+
@Optional() @Inject(ANIMATION_MODULE_TYPE) animationMode?: string) {
226228
super();
227229

228230
this._tabLinkRipple = new RippleRenderer(this, ngZone, _elementRef, platform);
@@ -231,6 +233,10 @@ export class MatTabLink extends _MatTabLinkMixinBase
231233

232234
this.tabIndex = parseInt(tabIndex) || 0;
233235
_focusMonitor.monitor(_elementRef);
236+
237+
if (animationMode === 'NoopAnimations') {
238+
this.rippleConfig.animation = {enterDuration: 0, exitDuration: 0};
239+
}
234240
}
235241

236242
ngOnDestroy() {

tools/public_api_guard/material/tabs.d.ts

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,8 @@ export interface _MatInkBarPositioner {
1010
export declare const MAT_TABS_CONFIG: InjectionToken<{}>;
1111

1212
export declare class MatInkBar {
13-
constructor(_elementRef: ElementRef<HTMLElement>, _ngZone: NgZone, _inkBarPositioner: _MatInkBarPositioner);
13+
_animationMode?: string | undefined;
14+
constructor(_elementRef: ElementRef<HTMLElement>, _ngZone: NgZone, _inkBarPositioner: _MatInkBarPositioner, _animationMode?: string | undefined);
1415
alignToElement(element: HTMLElement): void;
1516
hide(): void;
1617
show(): void;
@@ -75,6 +76,7 @@ export declare class MatTabContent {
7576
}
7677

7778
export declare class MatTabGroup extends _MatTabGroupMixinBase implements AfterContentInit, AfterContentChecked, OnDestroy, CanColor, CanDisableRipple {
79+
_animationMode?: string | undefined;
7880
_tabBodyWrapper: ElementRef;
7981
_tabHeader: MatTabHeader;
8082
_tabs: QueryList<MatTab>;
@@ -87,7 +89,7 @@ export declare class MatTabGroup extends _MatTabGroupMixinBase implements AfterC
8789
selectedIndex: number | null;
8890
readonly selectedIndexChange: EventEmitter<number>;
8991
readonly selectedTabChange: EventEmitter<MatTabChangeEvent>;
90-
constructor(elementRef: ElementRef, _changeDetectorRef: ChangeDetectorRef, defaultConfig?: MatTabsConfig);
92+
constructor(elementRef: ElementRef, _changeDetectorRef: ChangeDetectorRef, defaultConfig?: MatTabsConfig, _animationMode?: string | undefined);
9193
_focusChanged(index: number): void;
9294
_getTabContentId(i: number): string;
9395
_getTabIndex(tab: MatTab, idx: number): number | null;
@@ -102,6 +104,7 @@ export declare class MatTabGroup extends _MatTabGroupMixinBase implements AfterC
102104
}
103105

104106
export declare class MatTabHeader extends _MatTabHeaderMixinBase implements AfterContentChecked, AfterContentInit, AfterViewInit, OnDestroy, CanDisableRipple {
107+
_animationMode?: string | undefined;
105108
_disableScrollAfter: boolean;
106109
_disableScrollBefore: boolean;
107110
_inkBar: MatInkBar;
@@ -116,7 +119,7 @@ export declare class MatTabHeader extends _MatTabHeaderMixinBase implements Afte
116119
scrollDistance: number;
117120
readonly selectFocusedIndex: EventEmitter<number>;
118121
selectedIndex: number;
119-
constructor(_elementRef: ElementRef, _changeDetectorRef: ChangeDetectorRef, _viewportRuler: ViewportRuler, _dir: Directionality, _ngZone: NgZone, _platform: Platform);
122+
constructor(_elementRef: ElementRef, _changeDetectorRef: ChangeDetectorRef, _viewportRuler: ViewportRuler, _dir: Directionality, _ngZone: NgZone, _platform: Platform, _animationMode?: string | undefined);
120123
_alignInkBarToSelectedTab(): void;
121124
_checkPaginationEnabled(): void;
122125
_checkScrollingControls(): void;
@@ -162,7 +165,7 @@ export declare class MatTabLink extends _MatTabLinkMixinBase implements OnDestro
162165
active: boolean;
163166
rippleConfig: RippleConfig & RippleGlobalOptions;
164167
readonly rippleDisabled: boolean;
165-
constructor(_tabNavBar: MatTabNav, _elementRef: ElementRef, ngZone: NgZone, platform: Platform, globalRippleOptions: RippleGlobalOptions | null, tabIndex: string, _focusMonitor: FocusMonitor);
168+
constructor(_tabNavBar: MatTabNav, _elementRef: ElementRef, ngZone: NgZone, platform: Platform, globalRippleOptions: RippleGlobalOptions | null, tabIndex: string, _focusMonitor: FocusMonitor, animationMode?: string);
166169
ngOnDestroy(): void;
167170
}
168171

0 commit comments

Comments
 (0)