Skip to content

Commit

Permalink
feat(material/progress-bar): add default options injection token (#23363
Browse files Browse the repository at this point in the history
)

Adds an injection token that allows for the progress bar defaults to be configured.

Fixes #23329.
  • Loading branch information
crisbeto committed Aug 18, 2021
1 parent 2b81e7c commit e4b54aa
Show file tree
Hide file tree
Showing 6 changed files with 95 additions and 16 deletions.
25 changes: 20 additions & 5 deletions src/material-experimental/mdc-progress-bar/progress-bar.spec.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,18 @@
import {TestBed, ComponentFixture} from '@angular/core/testing';
import {Component, DebugElement, Type} from '@angular/core';
import {Component, DebugElement, Provider, Type} from '@angular/core';
import {By} from '@angular/platform-browser';
import {dispatchFakeEvent} from '../../cdk/testing/private';
import {MatProgressBarModule} from './index';
import {MatProgressBarModule, MAT_PROGRESS_BAR_DEFAULT_OPTIONS} from './index';
import {MatProgressBar} from './progress-bar';


describe('MDC-based MatProgressBar', () => {
function createComponent<T>(componentType: Type<T>,
imports?: Type<{}>[]): ComponentFixture<T> {
providers: Provider[] = []): ComponentFixture<T> {
TestBed.configureTestingModule({
imports: imports || [MatProgressBarModule],
declarations: [componentType]
imports: [MatProgressBarModule],
declarations: [componentType],
providers
}).compileComponents();

return TestBed.createComponent<T>(componentType);
Expand Down Expand Up @@ -152,6 +153,20 @@ describe('MDC-based MatProgressBar', () => {
.withContext('Expect aria-valuenow to be cleared in query mode.').toBe(false);
});

it('should be able to configure the default progress bar options via DI', () => {
const fixture = createComponent(BasicProgressBar, [{
provide: MAT_PROGRESS_BAR_DEFAULT_OPTIONS,
useValue: {
mode: 'buffer',
color: 'warn'
}
}]);
fixture.detectChanges();
const progressElement = fixture.debugElement.query(By.css('mat-progress-bar'))!;
expect(progressElement.componentInstance.mode).toBe('buffer');
expect(progressElement.componentInstance.color).toBe('warn');
});

});

describe('animation trigger on determinate setting', () => {
Expand Down
18 changes: 16 additions & 2 deletions src/material-experimental/mdc-progress-bar/progress-bar.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,11 @@ import {
} from '@angular/core';
import {CanColor, mixinColor} from '@angular/material-experimental/mdc-core';
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
import {ProgressAnimationEnd} from '@angular/material/progress-bar';
import {
MatProgressBarDefaultOptions,
MAT_PROGRESS_BAR_DEFAULT_OPTIONS,
ProgressAnimationEnd,
} from '@angular/material/progress-bar';
import {
MDCLinearProgressAdapter,
MDCLinearProgressFoundation,
Expand Down Expand Up @@ -67,7 +71,9 @@ export class MatProgressBar extends _MatProgressBarBase implements AfterViewInit
constructor(elementRef: ElementRef<HTMLElement>,
private _ngZone: NgZone,
@Optional() dir?: Directionality,
@Optional() @Inject(ANIMATION_MODULE_TYPE) public _animationMode?: string) {
@Optional() @Inject(ANIMATION_MODULE_TYPE) public _animationMode?: string,
@Optional() @Inject(MAT_PROGRESS_BAR_DEFAULT_OPTIONS)
defaults?: MatProgressBarDefaultOptions) {
super(elementRef);
this._isNoopAnimation = _animationMode === 'NoopAnimations';
if (dir) {
Expand All @@ -76,6 +82,14 @@ export class MatProgressBar extends _MatProgressBarBase implements AfterViewInit
this._foundation?.restartAnimation();
});
}

if (defaults) {
if (defaults.color) {
this.color = this.defaultColor = defaults.color;
}

this.mode = defaults.mode || this.mode;
}
}

/** Implements all of the logic of the MDC progress bar. */
Expand Down
2 changes: 2 additions & 0 deletions src/material-experimental/mdc-progress-bar/public-api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,6 @@ export {
MAT_PROGRESS_BAR_LOCATION,
MatProgressBarLocation,
MAT_PROGRESS_BAR_LOCATION_FACTORY,
MAT_PROGRESS_BAR_DEFAULT_OPTIONS,
MatProgressBarDefaultOptions,
} from '@angular/material/progress-bar';
24 changes: 19 additions & 5 deletions src/material/progress-bar/progress-bar.spec.ts
Original file line number Diff line number Diff line change
@@ -1,25 +1,25 @@
import {TestBed, ComponentFixture} from '@angular/core/testing';
import {Component, DebugElement, Type} from '@angular/core';
import {Component, DebugElement, Provider, Type} from '@angular/core';
import {By} from '@angular/platform-browser';
import {dispatchFakeEvent} from '../../cdk/testing/private';
import {MatProgressBarModule, MAT_PROGRESS_BAR_LOCATION} from './index';
import {MatProgressBar} from './progress-bar';
import {MatProgressBar, MAT_PROGRESS_BAR_DEFAULT_OPTIONS} from './progress-bar';


describe('MatProgressBar', () => {
let fakePath: string;

function createComponent<T>(componentType: Type<T>,
imports?: Type<{}>[]): ComponentFixture<T> {
providers: Provider[] = []): ComponentFixture<T> {
fakePath = '/fake-path';

TestBed.configureTestingModule({
imports: imports || [MatProgressBarModule],
imports: [MatProgressBarModule],
declarations: [componentType],
providers: [{
provide: MAT_PROGRESS_BAR_LOCATION,
useValue: {getPathname: () => fakePath}
}]
}, ...providers]
}).compileComponents();

return TestBed.createComponent<T>(componentType);
Expand Down Expand Up @@ -196,6 +196,20 @@ describe('MatProgressBar', () => {
.withContext('Expect aria-valuenow to be cleared in query mode.').toBe(false);
});

it('should be able to configure the default progress bar options via DI', () => {
const fixture = createComponent(BasicProgressBar, [{
provide: MAT_PROGRESS_BAR_DEFAULT_OPTIONS,
useValue: {
mode: 'buffer',
color: 'warn'
}
}]);
fixture.detectChanges();
const progressElement = fixture.debugElement.query(By.css('mat-progress-bar'))!;
expect(progressElement.componentInstance.mode).toBe('buffer');
expect(progressElement.componentInstance.color).toBe('warn');
});

});

describe('animation trigger on determinate setting', () => {
Expand Down
28 changes: 26 additions & 2 deletions src/material/progress-bar/progress-bar.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import {
ViewChild,
ViewEncapsulation,
} from '@angular/core';
import {CanColor, mixinColor} from '@angular/material/core';
import {CanColor, mixinColor, ThemePalette} from '@angular/material/core';
import {ANIMATION_MODULE_TYPE} from '@angular/platform-browser/animations';
import {fromEvent, Observable, Subscription} from 'rxjs';
import {filter} from 'rxjs/operators';
Expand Down Expand Up @@ -76,6 +76,20 @@ export function MAT_PROGRESS_BAR_LOCATION_FACTORY(): MatProgressBarLocation {

export type ProgressBarMode = 'determinate' | 'indeterminate' | 'buffer' | 'query';

/** Default `mat-progress-bar` options that can be overridden. */
export interface MatProgressBarDefaultOptions {
/** Default color of the progress bar. */
color?: ThemePalette;

/** Default mode of the progress bar. */
mode?: ProgressBarMode;
}

/** Injection token to be used to override the default options for `mat-progress-bar`. */
export const MAT_PROGRESS_BAR_DEFAULT_OPTIONS =
new InjectionToken<MatProgressBarDefaultOptions>('MAT_PROGRESS_BAR_DEFAULT_OPTIONS');


/** Counter used to generate unique IDs for progress bars. */
let progressbarId = 0;

Expand Down Expand Up @@ -111,7 +125,9 @@ export class MatProgressBar extends _MatProgressBarBase implements CanColor,
* @deprecated `location` parameter to be made required.
* @breaking-change 8.0.0
*/
@Optional() @Inject(MAT_PROGRESS_BAR_LOCATION) location?: MatProgressBarLocation) {
@Optional() @Inject(MAT_PROGRESS_BAR_LOCATION) location?: MatProgressBarLocation,
@Optional() @Inject(MAT_PROGRESS_BAR_DEFAULT_OPTIONS)
defaults?: MatProgressBarDefaultOptions) {
super(elementRef);

// We need to prefix the SVG reference with the current path, otherwise they won't work
Expand All @@ -124,6 +140,14 @@ export class MatProgressBar extends _MatProgressBarBase implements CanColor,
const path = location ? location.getPathname().split('#')[0] : '';
this._rectangleFillValue = `url('${path}#${this.progressbarId}')`;
this._isNoopAnimation = _animationMode === 'NoopAnimations';

if (defaults) {
if (defaults.color) {
this.color = this.defaultColor = defaults.color;
}

this.mode = defaults.mode || this.mode;
}
}

/** Flag that indicates whether NoopAnimations mode is set to true. */
Expand Down
14 changes: 12 additions & 2 deletions tools/public_api_guard/material/progress-bar.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ import { InjectionToken } from '@angular/core';
import { NgZone } from '@angular/core';
import { NumberInput } from '@angular/cdk/coercion';
import { OnDestroy } from '@angular/core';
import { ThemePalette } from '@angular/material/core';

// @public
export const MAT_PROGRESS_BAR_DEFAULT_OPTIONS: InjectionToken<MatProgressBarDefaultOptions>;

// @public
export const MAT_PROGRESS_BAR_LOCATION: InjectionToken<MatProgressBarLocation>;
Expand All @@ -27,7 +31,7 @@ export function MAT_PROGRESS_BAR_LOCATION_FACTORY(): MatProgressBarLocation;
// @public
export class MatProgressBar extends _MatProgressBarBase implements CanColor, AfterViewInit, OnDestroy {
constructor(elementRef: ElementRef, _ngZone: NgZone, _animationMode?: string | undefined,
location?: MatProgressBarLocation);
location?: MatProgressBarLocation, defaults?: MatProgressBarDefaultOptions);
readonly animationEnd: EventEmitter<ProgressAnimationEnd>;
// (undocumented)
_animationMode?: string | undefined;
Expand Down Expand Up @@ -56,7 +60,13 @@ export class MatProgressBar extends _MatProgressBarBase implements CanColor, Aft
// (undocumented)
static ɵcmp: i0.ɵɵComponentDeclaration<MatProgressBar, "mat-progress-bar", ["matProgressBar"], { "color": "color"; "value": "value"; "bufferValue": "bufferValue"; "mode": "mode"; }, { "animationEnd": "animationEnd"; }, never, never>;
// (undocumented)
static ɵfac: i0.ɵɵFactoryDeclaration<MatProgressBar, [null, null, { optional: true; }, { optional: true; }]>;
static ɵfac: i0.ɵɵFactoryDeclaration<MatProgressBar, [null, null, { optional: true; }, { optional: true; }, { optional: true; }]>;
}

// @public
export interface MatProgressBarDefaultOptions {
color?: ThemePalette;
mode?: ProgressBarMode;
}

// @public
Expand Down

0 comments on commit e4b54aa

Please sign in to comment.