Skip to content

Commit 9d152c0

Browse files
crisbetojelbourn
authored andcommitted
fix(autocomplete): prevent opening using arrow keys on readonly input (#9229)
A while back we started blocking being able to open an autocomplete by focusing a readonly input, however that didn't cover opening using the keyboard shortcuts. These changes also prevent users from being able to open using the keyboard. Fixes #9227.
1 parent 1e7eeab commit 9d152c0

File tree

2 files changed

+22
-3
lines changed

2 files changed

+22
-3
lines changed

src/lib/autocomplete/autocomplete-trigger.ts

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -305,7 +305,7 @@ export class MatAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
305305

306306
if (this.panelOpen || keyCode === TAB) {
307307
this.autocomplete._keyManager.onKeydown(event);
308-
} else if (isArrowKey) {
308+
} else if (isArrowKey && this._canOpen()) {
309309
this.openPanel();
310310
}
311311

@@ -319,14 +319,14 @@ export class MatAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
319319
// We need to ensure that the input is focused, because IE will fire the `input`
320320
// event on focus/blur/load if the input has a placeholder. See:
321321
// https://connect.microsoft.com/IE/feedback/details/885747/
322-
if (document.activeElement === event.target) {
322+
if (this._canOpen() && document.activeElement === event.target) {
323323
this._onChange((event.target as HTMLInputElement).value);
324324
this.openPanel();
325325
}
326326
}
327327

328328
_handleFocus(): void {
329-
if (!this._element.nativeElement.readOnly) {
329+
if (this._canOpen()) {
330330
this._attachOverlay();
331331
this._floatLabel(true);
332332
}
@@ -524,4 +524,10 @@ export class MatAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
524524
this.autocomplete._keyManager.setActiveItem(-1);
525525
}
526526

527+
/** Determines whether the panel can be opened. */
528+
private _canOpen(): boolean {
529+
const element: HTMLInputElement = this._element.nativeElement;
530+
return !element.readOnly && !element.disabled;
531+
}
532+
527533
}

src/lib/autocomplete/autocomplete.spec.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,19 @@ describe('MatAutocomplete', () => {
134134
expect(trigger.panelOpen).toBe(false, 'Expected panel to stay closed.');
135135
}));
136136

137+
it('should not open using the arrow keys when the input is readonly', fakeAsync(() => {
138+
const trigger = fixture.componentInstance.trigger;
139+
input.readOnly = true;
140+
fixture.detectChanges();
141+
142+
expect(trigger.panelOpen).toBe(false, 'Expected panel state to start out closed.');
143+
dispatchKeyboardEvent(input, 'keydown', DOWN_ARROW);
144+
flush();
145+
146+
fixture.detectChanges();
147+
expect(trigger.panelOpen).toBe(false, 'Expected panel to stay closed.');
148+
}));
149+
137150
it('should open the panel programmatically', () => {
138151
expect(fixture.componentInstance.trigger.panelOpen)
139152
.toBe(false, `Expected panel state to start out closed.`);

0 commit comments

Comments
 (0)