1
1
import { QueryList } from '@angular/core' ;
2
- import { FocusKeyManager } from './focus-key-manager' ;
2
+ import { fakeAsync , tick } from '@angular/core/testing' ;
3
+ import { FocusKeyManager , FOCUS_KEY_MANAGER_DEBOUNCE_INTERVAL } from './focus-key-manager' ;
3
4
import { DOWN_ARROW , UP_ARROW , TAB , HOME , END } from '../keyboard/keycodes' ;
4
5
import { ListKeyManager } from './list-key-manager' ;
5
6
import { ActiveDescendantKeyManager } from './activedescendant-key-manager' ;
6
7
7
8
class FakeFocusable {
8
9
disabled = false ;
9
10
focus ( ) { }
11
+
12
+ getFocusableLabel ( ) {
13
+ return this . _label ;
14
+ }
15
+
16
+ constructor ( private _label ?: string ) { }
10
17
}
11
18
12
19
class FakeHighlightable {
@@ -21,6 +28,7 @@ class FakeQueryList<T> extends QueryList<T> {
21
28
toArray ( ) {
22
29
return this . items ;
23
30
}
31
+ get first ( ) { return this . items [ 0 ] ; }
24
32
}
25
33
26
34
export class FakeEvent {
@@ -356,9 +364,9 @@ describe('Key managers', () => {
356
364
357
365
beforeEach ( ( ) => {
358
366
itemList . items = [
359
- new FakeFocusable ( ) ,
360
- new FakeFocusable ( ) ,
361
- new FakeFocusable ( )
367
+ new FakeFocusable ( 'one' ) ,
368
+ new FakeFocusable ( 'two' ) ,
369
+ new FakeFocusable ( 'three' )
362
370
] ;
363
371
364
372
keyManager = new FocusKeyManager ( itemList ) ;
@@ -371,40 +379,81 @@ describe('Key managers', () => {
371
379
spyOn ( itemList . items [ 2 ] , 'focus' ) ;
372
380
} ) ;
373
381
374
- it ( 'should focus subsequent items when down arrow is pressed' , ( ) => {
375
- keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
382
+ it ( 'should focus subsequent items when down arrow is pressed' , ( ) => {
383
+ keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
376
384
377
- expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
378
- expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
379
- expect ( itemList . items [ 2 ] . focus ) . not . toHaveBeenCalled ( ) ;
385
+ expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
386
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
387
+ expect ( itemList . items [ 2 ] . focus ) . not . toHaveBeenCalled ( ) ;
380
388
381
- keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
382
- expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
383
- expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
384
- expect ( itemList . items [ 2 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
385
- } ) ;
389
+ keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
390
+ expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
391
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
392
+ expect ( itemList . items [ 2 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
393
+ } ) ;
386
394
387
- it ( 'should focus previous items when up arrow is pressed' , ( ) => {
388
- keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
395
+ it ( 'should focus previous items when up arrow is pressed' , ( ) => {
396
+ keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
389
397
390
- expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
391
- expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
398
+ expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
399
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
392
400
393
- keyManager . onKeydown ( UP_ARROW_EVENT ) ;
401
+ keyManager . onKeydown ( UP_ARROW_EVENT ) ;
394
402
395
- expect ( itemList . items [ 0 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
396
- expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
397
- } ) ;
403
+ expect ( itemList . items [ 0 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
404
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalledTimes ( 1 ) ;
405
+ } ) ;
398
406
399
- it ( 'should allow setting the focused item without calling focus' , ( ) => {
400
- expect ( keyManager . activeItemIndex )
401
- . toBe ( 0 , `Expected first item of the list to be active.` ) ;
407
+ it ( 'should allow setting the focused item without calling focus' , ( ) => {
408
+ expect ( keyManager . activeItemIndex )
409
+ . toBe ( 0 , `Expected first item of the list to be active.` ) ;
402
410
403
- keyManager . updateActiveItemIndex ( 1 ) ;
404
- expect ( keyManager . activeItemIndex )
405
- . toBe ( 1 , `Expected activeItemIndex to update after calling updateActiveItemIndex().` ) ;
406
- expect ( itemList . items [ 1 ] . focus ) . not . toHaveBeenCalledTimes ( 1 ) ;
407
- } ) ;
411
+ keyManager . updateActiveItemIndex ( 1 ) ;
412
+ expect ( keyManager . activeItemIndex )
413
+ . toBe ( 1 , `Expected activeItemIndex to update after calling updateActiveItemIndex().` ) ;
414
+ expect ( itemList . items [ 1 ] . focus ) . not . toHaveBeenCalledTimes ( 1 ) ;
415
+ } ) ;
416
+
417
+ it ( 'should debounce the input key presses' , fakeAsync ( ( ) => {
418
+ keyManager . onKeydown ( new FakeEvent ( 79 ) as KeyboardEvent ) ; // types "o"
419
+ keyManager . onKeydown ( new FakeEvent ( 78 ) as KeyboardEvent ) ; // types "n"
420
+ keyManager . onKeydown ( new FakeEvent ( 69 ) as KeyboardEvent ) ; // types "e"
421
+
422
+ expect ( itemList . items [ 0 ] . focus ) . not . toHaveBeenCalled ( ) ;
423
+
424
+ tick ( FOCUS_KEY_MANAGER_DEBOUNCE_INTERVAL ) ;
425
+
426
+ expect ( itemList . items [ 0 ] . focus ) . toHaveBeenCalled ( ) ;
427
+ } ) ) ;
428
+
429
+ it ( 'should focus the first item that starts with a letter' , fakeAsync ( ( ) => {
430
+ keyManager . onKeydown ( new FakeEvent ( 84 ) as KeyboardEvent ) ; // types "t"
431
+
432
+ tick ( FOCUS_KEY_MANAGER_DEBOUNCE_INTERVAL ) ;
433
+
434
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalled ( ) ;
435
+ } ) ) ;
436
+
437
+ it ( 'should focus the first item that starts with sequence of letters' , fakeAsync ( ( ) => {
438
+ keyManager . onKeydown ( new FakeEvent ( 84 ) as KeyboardEvent ) ; // types "t"
439
+ keyManager . onKeydown ( new FakeEvent ( 72 ) as KeyboardEvent ) ; // types "h"
440
+
441
+ tick ( FOCUS_KEY_MANAGER_DEBOUNCE_INTERVAL ) ;
442
+
443
+ expect ( itemList . items [ 1 ] . focus ) . not . toHaveBeenCalled ( ) ;
444
+ expect ( itemList . items [ 2 ] . focus ) . toHaveBeenCalled ( ) ;
445
+ } ) ) ;
446
+
447
+ it ( 'should cancel any pending timers if a non-input key is pressed' , fakeAsync ( ( ) => {
448
+ keyManager . onKeydown ( new FakeEvent ( 84 ) as KeyboardEvent ) ; // types "t"
449
+ keyManager . onKeydown ( new FakeEvent ( 72 ) as KeyboardEvent ) ; // types "h"
450
+ keyManager . onKeydown ( DOWN_ARROW_EVENT ) ;
451
+
452
+ tick ( FOCUS_KEY_MANAGER_DEBOUNCE_INTERVAL ) ;
453
+
454
+ expect ( itemList . items [ 2 ] . focus ) . not . toHaveBeenCalled ( ) ;
455
+ expect ( itemList . items [ 1 ] . focus ) . toHaveBeenCalled ( ) ;
456
+ } ) ) ;
408
457
409
458
} ) ;
410
459
0 commit comments