From 69980806e8dcd3ab97b9183f1438d3458f86a932 Mon Sep 17 00:00:00 2001 From: Kristiyan Kostadinov Date: Fri, 4 Mar 2022 14:36:02 +0100 Subject: [PATCH] fixup! fix(material/dialog): don't wait for animation before moving focus --- src/material/dialog/dialog-config.ts | 3 +++ src/material/dialog/dialog-container.ts | 14 ++++++++++++-- src/material/dialog/dialog.spec.ts | 4 ++-- tools/public_api_guard/material/dialog.md | 3 +++ 4 files changed, 20 insertions(+), 4 deletions(-) diff --git a/src/material/dialog/dialog-config.ts b/src/material/dialog/dialog-config.ts index 2265e3a4e422..9fa06481bf1f 100644 --- a/src/material/dialog/dialog-config.ts +++ b/src/material/dialog/dialog-config.ts @@ -110,6 +110,9 @@ export class MatDialogConfig { */ restoreFocus?: boolean = true; + /** Whether to wait for the opening animation to finish before trapping focus. */ + delayFocusTrap?: boolean = true; + /** Scroll strategy to be used for the dialog. */ scrollStrategy?: ScrollStrategy; diff --git a/src/material/dialog/dialog-container.ts b/src/material/dialog/dialog-container.ts index 927cc42656c3..162b3e94d9c8 100644 --- a/src/material/dialog/dialog-container.ts +++ b/src/material/dialog/dialog-container.ts @@ -117,8 +117,6 @@ export abstract class _MatDialogContainerBase extends BasePortalOutlet { if (this._document) { this._elementFocusedBeforeDialogWasOpened = _getFocusedElementPierceShadowDom(); } - - this._trapFocus(); } /** @@ -326,6 +324,10 @@ export class MatDialogContainer extends _MatDialogContainerBase { /** Callback, invoked whenever an animation on the host completes. */ _onAnimationDone({toState, totalTime}: AnimationEvent) { if (toState === 'enter') { + if (this._config.delayFocusTrap) { + this._trapFocus(); + } + this._animationStateChanged.next({state: 'opened', totalTime}); } else if (toState === 'exit') { this._restoreFocus(); @@ -350,4 +352,12 @@ export class MatDialogContainer extends _MatDialogContainerBase { // view container is using OnPush change detection. this._changeDetectorRef.markForCheck(); } + + override _initializeWithAttachedContent() { + super._initializeWithAttachedContent(); + + if (!this._config.delayFocusTrap) { + this._trapFocus(); + } + } } diff --git a/src/material/dialog/dialog.spec.ts b/src/material/dialog/dialog.spec.ts index e8cc2fd602cd..c874e01e4389 100644 --- a/src/material/dialog/dialog.spec.ts +++ b/src/material/dialog/dialog.spec.ts @@ -1388,7 +1388,7 @@ describe('MatDialog', () => { tick(500); viewContainerFixture.detectChanges(); - expect(lastFocusOrigin).toBe(null); + expect(lastFocusOrigin!).toBe('program'); dispatchKeyboardEvent(document.body, 'keydown', ESCAPE); @@ -1421,7 +1421,7 @@ describe('MatDialog', () => { tick(500); viewContainerFixture.detectChanges(); - expect(lastFocusOrigin).toBe(null); + expect(lastFocusOrigin!).toBe('program'); const backdrop = overlayContainerElement.querySelector( '.cdk-overlay-backdrop', diff --git a/tools/public_api_guard/material/dialog.md b/tools/public_api_guard/material/dialog.md index b5a73b5b9181..e8cbe9d65967 100644 --- a/tools/public_api_guard/material/dialog.md +++ b/tools/public_api_guard/material/dialog.md @@ -165,6 +165,7 @@ export class MatDialogConfig { closeOnNavigation?: boolean; componentFactoryResolver?: ComponentFactoryResolver; data?: D | null; + delayFocusTrap?: boolean; direction?: Direction; disableClose?: boolean; hasBackdrop?: boolean; @@ -185,6 +186,8 @@ export class MatDialogConfig { // @public export class MatDialogContainer extends _MatDialogContainerBase { + // (undocumented) + _initializeWithAttachedContent(): void; _onAnimationDone({ toState, totalTime }: AnimationEvent_2): void; _onAnimationStart({ toState, totalTime }: AnimationEvent_2): void; _startExitAnimation(): void;