mirror of
https://github.com/angular/angular.git
synced 2026-09-14 13:54:52 +08:00
fix(autocomplete,datepicker,menu): closing parent dialog by pressing escape (#6226)
Prevents the autocomplete, datepicker and menu components from closing their parent dialog when the user presses escape. Fixes #6223.
This commit is contained in:
committed by
tinayuangao
parent
a043bec9da
commit
916d1f3bb0
@@ -298,6 +298,7 @@ export class MdAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
|
||||
_handleKeydown(event: KeyboardEvent): void {
|
||||
if (event.keyCode === ESCAPE && this.panelOpen) {
|
||||
this.closePanel();
|
||||
event.stopPropagation();
|
||||
} else if (this.activeOption && event.keyCode === ENTER && this.panelOpen) {
|
||||
this.activeOption._selectViaInteraction();
|
||||
event.preventDefault();
|
||||
|
||||
@@ -898,6 +898,7 @@ describe('MdAutocomplete', () => {
|
||||
it('should close the panel when pressing escape', async(() => {
|
||||
const trigger = fixture.componentInstance.trigger;
|
||||
const escapeEvent = createKeyboardEvent('keydown', ESCAPE);
|
||||
const stopPropagationSpy = spyOn(escapeEvent, 'stopPropagation').and.callThrough();
|
||||
|
||||
input.focus();
|
||||
|
||||
@@ -909,6 +910,7 @@ describe('MdAutocomplete', () => {
|
||||
|
||||
expect(document.activeElement).toBe(input, 'Expected input to continue to be focused.');
|
||||
expect(trigger.panelOpen).toBe(false, 'Expected panel to be closed.');
|
||||
expect(stopPropagationSpy).toHaveBeenCalled();
|
||||
});
|
||||
}));
|
||||
|
||||
|
||||
@@ -9,8 +9,13 @@ import {MdDatepickerInput} from './datepicker-input';
|
||||
import {MdInputModule} from '../input/index';
|
||||
import {MdNativeDateModule} from '../core/datetime/index';
|
||||
import {ESCAPE, OverlayContainer} from '../core';
|
||||
import {dispatchFakeEvent, dispatchMouseEvent, dispatchKeyboardEvent} from '@angular/cdk/testing';
|
||||
import {DEC, JAN} from '../core/testing/month-constants';
|
||||
import {
|
||||
dispatchFakeEvent,
|
||||
dispatchMouseEvent,
|
||||
createKeyboardEvent,
|
||||
dispatchEvent,
|
||||
} from '@angular/cdk/testing';
|
||||
|
||||
describe('MdDatepicker', () => {
|
||||
afterEach(inject([OverlayContainer], (container: OverlayContainer) => {
|
||||
@@ -134,13 +139,17 @@ describe('MdDatepicker', () => {
|
||||
let content = document.querySelector('.cdk-overlay-pane md-datepicker-content')!;
|
||||
expect(content).toBeTruthy('Expected datepicker to be open.');
|
||||
|
||||
let keyboadEvent = dispatchKeyboardEvent(content, 'keydown', ESCAPE);
|
||||
const keyboardEvent = createKeyboardEvent('keydown', ESCAPE);
|
||||
const stopPropagationSpy = spyOn(keyboardEvent, 'stopPropagation').and.callThrough();
|
||||
|
||||
dispatchEvent(content, keyboardEvent);
|
||||
fixture.detectChanges();
|
||||
|
||||
content = document.querySelector('.cdk-overlay-pane md-datepicker-content')!;
|
||||
|
||||
expect(content).toBeFalsy('Expected datepicker to be closed.');
|
||||
expect(keyboadEvent.defaultPrevented)
|
||||
expect(stopPropagationSpy).toHaveBeenCalled();
|
||||
expect(keyboardEvent.defaultPrevented)
|
||||
.toBe(true, 'Expected default ESCAPE action to be prevented.');
|
||||
});
|
||||
|
||||
|
||||
@@ -106,6 +106,7 @@ export class MdDatepickerContent<D> implements AfterContentInit {
|
||||
if (event.keyCode === ESCAPE) {
|
||||
this.datepicker.close();
|
||||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -168,6 +168,7 @@ export class MdMenu implements AfterContentInit, MdMenuPanel, OnDestroy {
|
||||
switch (event.keyCode) {
|
||||
case ESCAPE:
|
||||
this.close.emit('keydown');
|
||||
event.stopPropagation();
|
||||
break;
|
||||
case LEFT_ARROW:
|
||||
if (this.parentMenu && this.direction === 'ltr') {
|
||||
|
||||
@@ -29,7 +29,12 @@ import {
|
||||
} from './index';
|
||||
import {MENU_PANEL_TOP_PADDING} from './menu-trigger';
|
||||
import {extendObject} from '../core/util/object-extend';
|
||||
import {dispatchKeyboardEvent, dispatchMouseEvent} from '@angular/cdk/testing';
|
||||
import {
|
||||
dispatchKeyboardEvent,
|
||||
dispatchMouseEvent,
|
||||
dispatchEvent,
|
||||
createKeyboardEvent,
|
||||
} from '@angular/cdk/testing';
|
||||
|
||||
|
||||
describe('MdMenu', () => {
|
||||
@@ -103,11 +108,15 @@ describe('MdMenu', () => {
|
||||
fixture.componentInstance.trigger.openMenu();
|
||||
|
||||
const panel = overlayContainerElement.querySelector('.mat-menu-panel')!;
|
||||
dispatchKeyboardEvent(panel, 'keydown', ESCAPE);
|
||||
const event = createKeyboardEvent('keydown', ESCAPE);
|
||||
const stopPropagationSpy = spyOn(event, 'stopPropagation').and.callThrough();
|
||||
|
||||
dispatchEvent(panel, event);
|
||||
fixture.detectChanges();
|
||||
tick(500);
|
||||
|
||||
expect(overlayContainerElement.textContent).toBe('');
|
||||
expect(stopPropagationSpy).toHaveBeenCalled();
|
||||
}));
|
||||
|
||||
it('should open a custom menu', () => {
|
||||
|
||||
Reference in New Issue
Block a user