mirror of
https://github.com/angular/angular.git
synced 2026-09-14 13:54:52 +08:00
fix: improved key manager typings (#6443)
Makes the FocusKeyManager and ActivedescendantKeyManager generic which avoids having to cast the items all the time (e.g. https://github.com/angular/material2/blob/master/src/lib/autocomplete/autocomplete-trigger.ts#L234).
This commit is contained in:
committed by
Andrew Seguin
parent
85a6fff17a
commit
18c6dec61a
@@ -18,7 +18,7 @@ export interface Highlightable extends ListKeyManagerOption {
|
||||
setInactiveStyles(): void;
|
||||
}
|
||||
|
||||
export class ActiveDescendantKeyManager extends ListKeyManager<Highlightable> {
|
||||
export class ActiveDescendantKeyManager<T> extends ListKeyManager<Highlightable & T> {
|
||||
|
||||
/**
|
||||
* This method sets the active item to the item at the specified index.
|
||||
|
||||
@@ -17,7 +17,7 @@ export interface FocusableOption extends ListKeyManagerOption {
|
||||
focus(): void;
|
||||
}
|
||||
|
||||
export class FocusKeyManager extends ListKeyManager<FocusableOption> {
|
||||
export class FocusKeyManager<T> extends ListKeyManager<FocusableOption & T> {
|
||||
/**
|
||||
* This method sets the active item to the item at the specified index.
|
||||
* It also adds focuses the newly active item.
|
||||
|
||||
@@ -451,11 +451,11 @@ describe('Key managers', () => {
|
||||
});
|
||||
|
||||
describe('FocusKeyManager', () => {
|
||||
let keyManager: FocusKeyManager;
|
||||
let keyManager: FocusKeyManager<FakeFocusable>;
|
||||
|
||||
beforeEach(() => {
|
||||
itemList.items = [new FakeFocusable(), new FakeFocusable(), new FakeFocusable()];
|
||||
keyManager = new FocusKeyManager(itemList);
|
||||
keyManager = new FocusKeyManager<FakeFocusable>(itemList);
|
||||
|
||||
// first item is already focused
|
||||
keyManager.setFirstItemActive();
|
||||
@@ -503,11 +503,11 @@ describe('Key managers', () => {
|
||||
});
|
||||
|
||||
describe('ActiveDescendantKeyManager', () => {
|
||||
let keyManager: ActiveDescendantKeyManager;
|
||||
let keyManager: ActiveDescendantKeyManager<FakeHighlightable>;
|
||||
|
||||
beforeEach(fakeAsync(() => {
|
||||
itemList.items = [new FakeHighlightable(), new FakeHighlightable(), new FakeHighlightable()];
|
||||
keyManager = new ActiveDescendantKeyManager(itemList);
|
||||
keyManager = new ActiveDescendantKeyManager<FakeHighlightable>(itemList);
|
||||
|
||||
// first item is already focused
|
||||
keyManager.setFirstItemActive();
|
||||
|
||||
@@ -231,7 +231,7 @@ export class MdAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
|
||||
/** The currently active option, coerced to MdOption type. */
|
||||
get activeOption(): MdOption | null {
|
||||
if (this.autocomplete && this.autocomplete._keyManager) {
|
||||
return this.autocomplete._keyManager.activeItem as MdOption;
|
||||
return this.autocomplete._keyManager.activeItem;
|
||||
}
|
||||
|
||||
return null;
|
||||
@@ -439,7 +439,7 @@ export class MdAutocompleteTrigger implements ControlValueAccessor, OnDestroy {
|
||||
* Clear any previous selected option and emit a selection change event for this option
|
||||
*/
|
||||
private _clearPreviousSelectedOption(skip: MdOption) {
|
||||
this.autocomplete.options.forEach((option) => {
|
||||
this.autocomplete.options.forEach(option => {
|
||||
if (option != skip && option.selected) {
|
||||
option.deselect();
|
||||
}
|
||||
|
||||
@@ -43,7 +43,7 @@ let _uniqueAutocompleteIdCounter = 0;
|
||||
export class MdAutocomplete implements AfterContentInit {
|
||||
|
||||
/** Manages active item in option list based on key events. */
|
||||
_keyManager: ActiveDescendantKeyManager;
|
||||
_keyManager: ActiveDescendantKeyManager<MdOption>;
|
||||
|
||||
/** Whether the autocomplete panel should be visible, depending on option length. */
|
||||
showPanel = false;
|
||||
@@ -66,7 +66,7 @@ export class MdAutocomplete implements AfterContentInit {
|
||||
constructor(private _changeDetectorRef: ChangeDetectorRef) { }
|
||||
|
||||
ngAfterContentInit() {
|
||||
this._keyManager = new ActiveDescendantKeyManager(this.options).withWrap();
|
||||
this._keyManager = new ActiveDescendantKeyManager<MdOption>(this.options).withWrap();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -3,13 +3,14 @@ import {Component, DebugElement, QueryList} from '@angular/core';
|
||||
import {By} from '@angular/platform-browser';
|
||||
import {NoopAnimationsModule} from '@angular/platform-browser/animations';
|
||||
import {MdChipList, MdChipsModule} from './index';
|
||||
import {FocusKeyManager} from '../core/a11y/focus-key-manager';
|
||||
import {FocusKeyManager} from '@angular/cdk/a11y';
|
||||
import {createKeyboardEvent} from '@angular/cdk/testing';
|
||||
|
||||
import {MdInputModule} from '../input/index';
|
||||
import {LEFT_ARROW, RIGHT_ARROW, BACKSPACE, DELETE, TAB} from '../core/keyboard/keycodes';
|
||||
import {Directionality} from '../core';
|
||||
import {MdFormFieldModule} from '../form-field/index';
|
||||
import {MdChip} from './chip';
|
||||
|
||||
describe('MdChipList', () => {
|
||||
let fixture: ComponentFixture<any>;
|
||||
@@ -18,8 +19,7 @@ describe('MdChipList', () => {
|
||||
let chipListInstance: MdChipList;
|
||||
let testComponent: StandardChipList;
|
||||
let chips: QueryList<any>;
|
||||
let manager: FocusKeyManager;
|
||||
|
||||
let manager: FocusKeyManager<MdChip>;
|
||||
let dir = 'ltr';
|
||||
|
||||
beforeEach(async(() => {
|
||||
|
||||
@@ -21,7 +21,7 @@ import {
|
||||
} from '@angular/core';
|
||||
|
||||
import {MdChip} from './chip';
|
||||
import {FocusKeyManager} from '../core/a11y/focus-key-manager';
|
||||
import {FocusKeyManager} from '@angular/cdk/a11y';
|
||||
import {BACKSPACE, DELETE, LEFT_ARROW, RIGHT_ARROW, UP_ARROW} from '../core/keyboard/keycodes';
|
||||
import {Directionality} from '@angular/cdk/bidi';
|
||||
import {Subscription} from 'rxjs/Subscription';
|
||||
@@ -77,7 +77,7 @@ export class MdChipList implements AfterContentInit, OnDestroy {
|
||||
_tabIndex = 0;
|
||||
|
||||
/** The FocusKeyManager which handles focus. */
|
||||
_keyManager: FocusKeyManager;
|
||||
_keyManager: FocusKeyManager<MdChip>;
|
||||
|
||||
/** The chip components contained within this chip list. */
|
||||
chips: QueryList<MdChip>;
|
||||
@@ -87,7 +87,7 @@ export class MdChipList implements AfterContentInit, OnDestroy {
|
||||
}
|
||||
|
||||
ngAfterContentInit(): void {
|
||||
this._keyManager = new FocusKeyManager(this.chips).withWrap();
|
||||
this._keyManager = new FocusKeyManager<MdChip>(this.chips).withWrap();
|
||||
|
||||
// Prevents the chip list from capturing focus and redirecting
|
||||
// it back to the first chip when the user tabs out.
|
||||
|
||||
@@ -18,7 +18,7 @@ export interface Highlightable extends ListKeyManagerOption {
|
||||
setInactiveStyles(): void;
|
||||
}
|
||||
|
||||
export class ActiveDescendantKeyManager extends ListKeyManager<Highlightable> {
|
||||
export class ActiveDescendantKeyManager<T> extends ListKeyManager<Highlightable & T> {
|
||||
|
||||
/**
|
||||
* This method sets the active item to the item at the specified index.
|
||||
|
||||
@@ -17,7 +17,7 @@ export interface FocusableOption extends ListKeyManagerOption {
|
||||
focus(): void;
|
||||
}
|
||||
|
||||
export class FocusKeyManager extends ListKeyManager<FocusableOption> {
|
||||
export class FocusKeyManager<T> extends ListKeyManager<FocusableOption & T> {
|
||||
/**
|
||||
* This method sets the active item to the item at the specified index.
|
||||
* It also adds focuses the newly active item.
|
||||
|
||||
@@ -202,10 +202,10 @@ export class MdSelectionList extends _MdSelectionListMixinBase
|
||||
private _optionDestroyStream: Subscription;
|
||||
|
||||
/** The FocusKeyManager which handles focus. */
|
||||
_keyManager: FocusKeyManager;
|
||||
_keyManager: FocusKeyManager<MdListOption>;
|
||||
|
||||
/** The option components contained within this selection-list. */
|
||||
@ContentChildren(MdListOption) options;
|
||||
@ContentChildren(MdListOption) options: QueryList<MdListOption>;
|
||||
|
||||
/** options which are selected. */
|
||||
selectedOptions: SelectionModel<MdListOption> = new SelectionModel<MdListOption>(true);
|
||||
@@ -223,7 +223,7 @@ export class MdSelectionList extends _MdSelectionListMixinBase
|
||||
}
|
||||
|
||||
ngAfterContentInit(): void {
|
||||
this._keyManager = new FocusKeyManager(this.options).withWrap();
|
||||
this._keyManager = new FocusKeyManager<MdListOption>(this.options).withWrap();
|
||||
|
||||
if (this.disabled) {
|
||||
this._tabIndex = -1;
|
||||
|
||||
@@ -27,7 +27,7 @@ import {AnimationEvent} from '@angular/animations';
|
||||
import {MenuPositionX, MenuPositionY} from './menu-positions';
|
||||
import {throwMdMenuInvalidPositionX, throwMdMenuInvalidPositionY} from './menu-errors';
|
||||
import {MdMenuItem} from './menu-item';
|
||||
import {FocusKeyManager} from '../core/a11y/focus-key-manager';
|
||||
import {FocusKeyManager} from '@angular/cdk/a11y';
|
||||
import {MdMenuPanel} from './menu-panel';
|
||||
import {Subscription} from 'rxjs/Subscription';
|
||||
import {transformMenu, fadeInItems} from './menu-animations';
|
||||
@@ -68,7 +68,7 @@ const MD_MENU_BASE_ELEVATION = 2;
|
||||
exportAs: 'mdMenu'
|
||||
})
|
||||
export class MdMenu implements AfterContentInit, MdMenuPanel, OnDestroy {
|
||||
private _keyManager: FocusKeyManager;
|
||||
private _keyManager: FocusKeyManager<MdMenuItem>;
|
||||
private _xPosition: MenuPositionX = this._defaultOptions.xPosition;
|
||||
private _yPosition: MenuPositionY = this._defaultOptions.yPosition;
|
||||
private _previousElevation: string;
|
||||
@@ -145,7 +145,7 @@ export class MdMenu implements AfterContentInit, MdMenuPanel, OnDestroy {
|
||||
@Inject(MD_MENU_DEFAULT_OPTIONS) private _defaultOptions: MdMenuDefaultOptions) { }
|
||||
|
||||
ngAfterContentInit() {
|
||||
this._keyManager = new FocusKeyManager(this.items).withWrap();
|
||||
this._keyManager = new FocusKeyManager<MdMenuItem>(this.items).withWrap();
|
||||
this._tabSubscription = this._keyManager.tabOut.subscribe(() => this.close.emit('keydown'));
|
||||
}
|
||||
|
||||
|
||||
@@ -239,7 +239,7 @@ export class MdSelect extends _MdSelectMixinBase implements AfterContentInit, On
|
||||
_triggerWidth: number;
|
||||
|
||||
/** Manages keyboard events for options in the panel. */
|
||||
_keyManager: FocusKeyManager;
|
||||
_keyManager: FocusKeyManager<MdOption>;
|
||||
|
||||
/**
|
||||
* The width of the selected option's value. Must be set programmatically
|
||||
@@ -737,7 +737,7 @@ export class MdSelect extends _MdSelectMixinBase implements AfterContentInit, On
|
||||
|
||||
/** Sets up a key manager to listen to keyboard events on the overlay panel. */
|
||||
private _initKeyManager() {
|
||||
this._keyManager = new FocusKeyManager(this.options).withTypeAhead();
|
||||
this._keyManager = new FocusKeyManager<MdOption>(this.options).withTypeAhead();
|
||||
this._tabSubscription = this._keyManager.tabOut.subscribe(() => this.close());
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user