Skip to content

Commit b9facd8

Browse files
CDDeltatinayuangao
authored andcommitted
feat(dialog): allow default dialog options to be configurable (#9113)
1 parent 4fdca7c commit b9facd8

File tree

3 files changed

+110
-5
lines changed

3 files changed

+110
-5
lines changed

src/lib/dialog/dialog-module.ts

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,10 @@ import {OverlayModule} from '@angular/cdk/overlay';
1212
import {PortalModule} from '@angular/cdk/portal';
1313
import {A11yModule} from '@angular/cdk/a11y';
1414
import {MatCommonModule} from '@angular/material/core';
15-
import {MatDialog, MAT_DIALOG_SCROLL_STRATEGY_PROVIDER} from './dialog';
15+
import {
16+
MatDialog,
17+
MAT_DIALOG_SCROLL_STRATEGY_PROVIDER
18+
} from './dialog';
1619
import {MatDialogContainer} from './dialog-container';
1720
import {
1821
MatDialogClose,

src/lib/dialog/dialog.spec.ts

Lines changed: 97 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,13 @@ import {MatDialogContainer} from './dialog-container';
2727
import {OverlayContainer} from '@angular/cdk/overlay';
2828
import {A, ESCAPE} from '@angular/cdk/keycodes';
2929
import {dispatchKeyboardEvent} from '@angular/cdk/testing';
30-
import {MAT_DIALOG_DATA, MatDialog, MatDialogModule, MatDialogRef} from './index';
30+
import {
31+
MAT_DIALOG_DATA,
32+
MatDialog,
33+
MatDialogModule,
34+
MatDialogRef,
35+
MAT_DIALOG_DEFAULT_OPTIONS
36+
} from './index';
3137

3238

3339
describe('MatDialog', () => {
@@ -965,6 +971,7 @@ describe('MatDialog', () => {
965971
expect(container.hasAttribute('aria-labelledby')).toBe(false);
966972
}));
967973
});
974+
968975
});
969976

970977
describe('MatDialog with a parent MatDialog', () => {
@@ -1045,6 +1052,95 @@ describe('MatDialog with a parent MatDialog', () => {
10451052
}));
10461053
});
10471054

1055+
describe('MatDialog with default options', () => {
1056+
let dialog: MatDialog;
1057+
let overlayContainer: OverlayContainer;
1058+
let overlayContainerElement: HTMLElement;
1059+
1060+
let testViewContainerRef: ViewContainerRef;
1061+
let viewContainerFixture: ComponentFixture<ComponentWithChildViewContainer>;
1062+
1063+
beforeEach(fakeAsync(() => {
1064+
const defaultConfig = {
1065+
hasBackdrop: false,
1066+
disableClose: true,
1067+
width: '100px',
1068+
height: '100px',
1069+
minWidth: '50px',
1070+
minHeight: '50px',
1071+
maxWidth: '150px',
1072+
maxHeight: '150px',
1073+
autoFocus: false,
1074+
};
1075+
1076+
TestBed.configureTestingModule({
1077+
imports: [MatDialogModule, DialogTestModule],
1078+
providers: [
1079+
{provide: MAT_DIALOG_DEFAULT_OPTIONS, useValue: defaultConfig},
1080+
],
1081+
});
1082+
1083+
TestBed.compileComponents();
1084+
}));
1085+
1086+
beforeEach(inject([MatDialog, OverlayContainer],
1087+
(d: MatDialog, oc: OverlayContainer) => {
1088+
dialog = d;
1089+
overlayContainer = oc;
1090+
overlayContainerElement = oc.getContainerElement();
1091+
}));
1092+
1093+
afterEach(() => {
1094+
overlayContainer.ngOnDestroy();
1095+
});
1096+
1097+
beforeEach(() => {
1098+
viewContainerFixture = TestBed.createComponent(ComponentWithChildViewContainer);
1099+
1100+
viewContainerFixture.detectChanges();
1101+
testViewContainerRef = viewContainerFixture.componentInstance.childViewContainer;
1102+
});
1103+
1104+
it('should use the provided defaults', () => {
1105+
dialog.open(PizzaMsg, {viewContainerRef: testViewContainerRef});
1106+
1107+
viewContainerFixture.detectChanges();
1108+
1109+
expect(overlayContainerElement.querySelector('.cdk-overlay-backdrop')).toBeFalsy();
1110+
1111+
dispatchKeyboardEvent(document.body, 'keydown', ESCAPE);
1112+
expect(overlayContainerElement.querySelector('mat-dialog-container')).toBeTruthy();
1113+
1114+
expect(document.activeElement.tagName).not.toBe('INPUT');
1115+
1116+
let overlayPane = overlayContainerElement.querySelector('.cdk-overlay-pane') as HTMLElement;
1117+
expect(overlayPane.style.width).toBe('100px');
1118+
expect(overlayPane.style.height).toBe('100px');
1119+
expect(overlayPane.style.minWidth).toBe('50px');
1120+
expect(overlayPane.style.minHeight).toBe('50px');
1121+
expect(overlayPane.style.maxWidth).toBe('150px');
1122+
expect(overlayPane.style.maxHeight).toBe('150px');
1123+
});
1124+
1125+
it('should be overridable by open() options', fakeAsync(() => {
1126+
dialog.open(PizzaMsg, {
1127+
hasBackdrop: true,
1128+
disableClose: false,
1129+
viewContainerRef: testViewContainerRef
1130+
});
1131+
1132+
viewContainerFixture.detectChanges();
1133+
1134+
expect(overlayContainerElement.querySelector('.cdk-overlay-backdrop')).toBeTruthy();
1135+
1136+
dispatchKeyboardEvent(document.body, 'keydown', ESCAPE);
1137+
viewContainerFixture.detectChanges();
1138+
flush();
1139+
1140+
expect(overlayContainerElement.querySelector('mat-dialog-container')).toBeFalsy();
1141+
}));
1142+
});
1143+
10481144

10491145
@Directive({selector: 'dir-with-view-container'})
10501146
class DirectiveWithViewContainer {

src/lib/dialog/dialog.ts

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,9 @@ import {MatDialogRef} from './dialog-ref';
4040

4141
export const MAT_DIALOG_DATA = new InjectionToken<any>('MatDialogData');
4242

43+
/** Injection token that can be used to specify default dialog options. */
44+
export const MAT_DIALOG_DEFAULT_OPTIONS =
45+
new InjectionToken<MatDialogConfig>('mat-dialog-default-options');
4346

4447
/** Injection token that determines the scroll handling while the dialog is open. */
4548
export const MAT_DIALOG_SCROLL_STRATEGY =
@@ -95,6 +98,7 @@ export class MatDialog {
9598
private _overlay: Overlay,
9699
private _injector: Injector,
97100
@Optional() location: Location,
101+
@Optional() @Inject(MAT_DIALOG_DEFAULT_OPTIONS) private _defaultOptions,
98102
@Inject(MAT_DIALOG_SCROLL_STRATEGY) private _scrollStrategy,
99103
@Optional() @SkipSelf() private _parentDialog: MatDialog) {
100104

@@ -116,7 +120,7 @@ export class MatDialog {
116120
open<T, D = any>(componentOrTemplateRef: ComponentType<T> | TemplateRef<T>,
117121
config?: MatDialogConfig<D>): MatDialogRef<T> {
118122

119-
config = _applyConfigDefaults(config);
123+
config = _applyConfigDefaults(config, this._defaultOptions || new MatDialogConfig());
120124

121125
if (config.id && this.getDialogById(config.id)) {
122126
throw Error(`Dialog with id "${config.id}" exists already. The dialog id must be unique.`);
@@ -309,8 +313,10 @@ export class MatDialog {
309313
/**
310314
* Applies default options to the dialog config.
311315
* @param config Config to be modified.
316+
* @param defaultOptions Default options provided.
312317
* @returns The new configuration object.
313318
*/
314-
function _applyConfigDefaults(config?: MatDialogConfig): MatDialogConfig {
315-
return {...new MatDialogConfig(), ...config};
319+
function _applyConfigDefaults(
320+
config?: MatDialogConfig, defaultOptions?: MatDialogConfig): MatDialogConfig {
321+
return {...defaultOptions, ...config};
316322
}

0 commit comments

Comments
 (0)