fix(drawer): show backdrop in "side" mode if hasBackdrop is explicitly set to true (#10251)

Currently we only use `hasBackdrop` to hide the backdrop, however setting it to `true` explicitly also expresses an intent that the consumer might want the backdrop to always be shown. These changes make it so backdrop will also be shown for `side` drawers if `hasBackdrop` is set to `true`.
This commit is contained in:
Kristiyan Kostadinov
2018-03-06 10:41:34 -05:00
committed by Jeremy Elbourn
parent 0c64b15f3d
commit 583fe151fd
6 changed files with 62 additions and 14 deletions
+2 -1
View File
@@ -4,7 +4,7 @@
<div class="demo-sidenav-area" *ngIf="isLaunched">
<mat-toolbar *ngIf="showHeader && !coverHeader">Header</mat-toolbar>
<mat-sidenav-container>
<mat-sidenav-container [hasBackdrop]="hasBackdrop">
<mat-sidenav #start (open)="myinput.focus()" [mode]="mode"
[fixedInViewport]="fixed" [fixedTopGap]="fixedTop" [fixedBottomGap]="fixedBottom">
Start Side Sidenav
@@ -41,6 +41,7 @@
<h3>Sidenav</h3>
<button mat-button (click)="start.toggle(undefined, 'mouse')">Toggle Start Side Sidenav</button>
<button mat-button (click)="end.toggle(undefined, 'mouse')">Toggle End Side Sidenav</button>
<mat-checkbox [(ngModel)]="hasBackdrop">Has backdrop</mat-checkbox>
<mat-checkbox [(ngModel)]="fixed">Fixed mode</mat-checkbox>
<mat-checkbox [(ngModel)]="coverHeader">Sidenav covers header/footer</mat-checkbox>
</div>
+1
View File
@@ -25,6 +25,7 @@ export class SidenavDemo {
showHeader = false;
showFooter = false;
modeIndex = 0;
hasBackdrop: boolean;
get mode() { return ['side', 'over', 'push'][this.modeIndex]; }
get fixedTop() { return this.fixed && this.showHeader && !this.coverHeader ? 64 : 0; }
get fixedBottom() { return this.fixed && this.showFooter && !this.coverHeader ? 64 : 0; }
+6
View File
@@ -45,6 +45,12 @@ $mat-drawer-over-drawer-z-index: 4;
overflow: hidden;
}
}
// When the consumer explicitly enabled the backdrop,
// we have to pull the side drawers above it.
&.mat-drawer-container-explicit-backdrop .mat-drawer-side {
z-index: $mat-drawer-backdrop-z-index;
}
}
.mat-drawer-backdrop {
+32 -2
View File
@@ -643,6 +643,35 @@ describe('MatDrawerContainer', () => {
expect(fixture.nativeElement.querySelector('.mat-drawer-backdrop')).toBeFalsy();
}));
it('should be able to explicitly enable the backdrop in `side` mode', fakeAsync(() => {
const fixture = TestBed.createComponent(BasicTestApp);
const root = fixture.nativeElement;
fixture.componentInstance.drawer.mode = 'side';
fixture.detectChanges();
fixture.componentInstance.drawer.open();
fixture.detectChanges();
tick();
fixture.detectChanges();
let backdrop = root.querySelector('.mat-drawer-backdrop.mat-drawer-shown');
expect(backdrop).toBeFalsy();
fixture.componentInstance.hasBackdrop = true;
fixture.detectChanges();
backdrop = root.querySelector('.mat-drawer-backdrop.mat-drawer-shown');
expect(backdrop).toBeTruthy();
expect(fixture.componentInstance.drawer.opened).toBe(true);
backdrop.click();
fixture.detectChanges();
tick();
expect(fixture.componentInstance.drawer.opened).toBe(false);
}));
});
@@ -666,7 +695,7 @@ class DrawerContainerTwoDrawerTestApp {
@Component({
template: `
<mat-drawer-container (backdropClick)="backdropClicked()" [hasBackdrop]="hasBackdrop">
<mat-drawer #drawer position="start"
<mat-drawer #drawer="matDrawer" position="start"
(opened)="open()"
(openedStart)="openStart()"
(closed)="close()"
@@ -683,8 +712,9 @@ class BasicTestApp {
closeCount = 0;
closeStartCount = 0;
backdropClickedCount = 0;
hasBackdrop = true;
hasBackdrop: boolean | null = null;
@ViewChild('drawer') drawer: MatDrawer;
@ViewChild('drawerButton') drawerButton: ElementRef;
@ViewChild('openButton') openButton: ElementRef;
@ViewChild('closeButton') closeButton: ElementRef;
+20 -11
View File
@@ -430,6 +430,7 @@ export class MatDrawer implements AfterContentInit, AfterContentChecked, OnDestr
styleUrls: ['drawer.css'],
host: {
'class': 'mat-drawer-container',
'[class.mat-drawer-container-explicit-backdrop]': '_backdropOverride',
},
changeDetection: ChangeDetectionStrategy.OnPush,
encapsulation: ViewEncapsulation.None,
@@ -458,19 +459,23 @@ export class MatDrawerContainer implements AfterContentInit, OnDestroy {
set autosize(value: boolean) { this._autosize = coerceBooleanProperty(value); }
private _autosize: boolean;
/** Whether the drawer container should have a backdrop while one of the sidenavs is open. */
/**
* Whether the drawer container should have a backdrop while one of the sidenavs is open.
* If explicitly set to `true`, the backdrop will be enabled for drawers in the `side`
* mode as well.
*/
@Input()
get hasBackdrop() {
if (this._hasBackdrop == null) {
if (this._backdropOverride == null) {
return !this._start || this._start.mode !== 'side' || !this._end || this._end.mode !== 'side';
}
return this._hasBackdrop;
return this._backdropOverride;
}
set hasBackdrop(value: any) {
this._hasBackdrop = value == null ? null : coerceBooleanProperty(value);
this._backdropOverride = value == null ? null : coerceBooleanProperty(value);
}
private _hasBackdrop: boolean | null;
_backdropOverride: boolean | null;
/** Event emitted when the drawer backdrop is clicked. */
@Output() readonly backdropClick: EventEmitter<void> = new EventEmitter<void>();
@@ -663,8 +668,8 @@ export class MatDrawerContainer implements AfterContentInit, OnDestroy {
/** Whether the container is being pushed to the side by one of the drawers. */
private _isPushed() {
return (this._isDrawerOpen(this._start) && this._start!.mode != 'over') ||
(this._isDrawerOpen(this._end) && this._end!.mode != 'over');
return (this._isDrawerOpen(this._start) && this._start.mode != 'over') ||
(this._isDrawerOpen(this._end) && this._end.mode != 'over');
}
_onBackdropClicked() {
@@ -675,16 +680,20 @@ export class MatDrawerContainer implements AfterContentInit, OnDestroy {
_closeModalDrawer() {
// Close all open drawers where closing is not disabled and the mode is not `side`.
[this._start, this._end]
.filter(drawer => drawer && !drawer.disableClose && drawer.mode !== 'side')
.filter(drawer => drawer && !drawer.disableClose && this._canHaveBackdrop(drawer))
.forEach(drawer => drawer!.close());
}
_isShowingBackdrop(): boolean {
return (this._isDrawerOpen(this._start) && this._start!.mode != 'side')
|| (this._isDrawerOpen(this._end) && this._end!.mode != 'side');
return (this._isDrawerOpen(this._start) && this._canHaveBackdrop(this._start)) ||
(this._isDrawerOpen(this._end) && this._canHaveBackdrop(this._end));
}
private _isDrawerOpen(drawer: MatDrawer | null): boolean {
private _canHaveBackdrop(drawer: MatDrawer): boolean {
return drawer.mode !== 'side' || !!this._backdropOverride;
}
private _isDrawerOpen(drawer: MatDrawer | null): drawer is MatDrawer {
return drawer != null && drawer.opened;
}
+1
View File
@@ -106,6 +106,7 @@ export class MatSidenav extends MatDrawer {
styleUrls: ['drawer.css'],
host: {
'class': 'mat-drawer-container mat-sidenav-container',
'[class.mat-drawer-container-explicit-backdrop]': '_backdropOverride',
},
changeDetection: ChangeDetectionStrategy.OnPush,
encapsulation: ViewEncapsulation.None,