Skip to content

Commit 1833b5e

Browse files
committed
update keyboard event tests from keyup to keydown
1 parent 9161cf4 commit 1833b5e

File tree

4 files changed

+142
-43
lines changed

4 files changed

+142
-43
lines changed

packages/dialtone-vue/components/tab/tab.test.js

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ const MOCK_DEFAULT_SLOT = 'Message Slot';
88
const MOCK_GROUP_CONTEXT = {
99
disabled: false,
1010
selected: '',
11+
focusedTabId: null,
1112
};
1213

1314
const baseProps = {
@@ -388,5 +389,51 @@ describe('DtTab Tests', () => {
388389
expect(tab.attributes('tabindex')).toBe('-1');
389390
});
390391
});
392+
393+
describe('Roving tabindex', () => {
394+
describe('When focusedTabId matches this tab', () => {
395+
beforeEach(() => {
396+
mockProvide = { groupContext: { ...MOCK_GROUP_CONTEXT, selected: '', focusedTabId: MOCK_ID } };
397+
398+
updateWrapper();
399+
});
400+
401+
it('tabindex should be 0', () => {
402+
expect(tab.attributes('tabindex')).toBe('0');
403+
});
404+
405+
it('aria-selected should still be "false"', () => {
406+
expect(tab.attributes('aria-selected')).toBe('false');
407+
});
408+
});
409+
410+
describe('When focusedTabId is a different tab', () => {
411+
beforeEach(() => {
412+
mockProvide = { groupContext: { ...MOCK_GROUP_CONTEXT, selected: MOCK_PANEL_ID, focusedTabId: 'other-tab' } };
413+
414+
updateWrapper();
415+
});
416+
417+
it('tabindex should be -1 even when selected', () => {
418+
expect(tab.attributes('tabindex')).toBe('-1');
419+
});
420+
421+
it('aria-selected should still be "true"', () => {
422+
expect(tab.attributes('aria-selected')).toBe('true');
423+
});
424+
});
425+
426+
describe('When focusedTabId is null', () => {
427+
beforeEach(() => {
428+
mockProvide = { groupContext: { ...MOCK_GROUP_CONTEXT, selected: MOCK_PANEL_ID, focusedTabId: null } };
429+
430+
updateWrapper();
431+
});
432+
433+
it('tabindex should fall back to selected tab', () => {
434+
expect(tab.attributes('tabindex')).toBe('0');
435+
});
436+
});
437+
});
391438
});
392439
});

packages/dialtone-vue/components/tab/tab.vue

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
:leading-class="leadingClass"
2222
:trailing-class="trailingClass"
2323
data-qa="dt-tab"
24-
:tabindex="isSelected ? '0' : '-1'"
24+
:tabindex="isFocusTarget ? '0' : '-1'"
2525
v-bind="$attrs"
2626
v-on="tabListeners"
2727
>
@@ -211,6 +211,11 @@ export default {
211211
return this.groupContext.selected === this.panelId;
212212
},
213213
214+
isFocusTarget () {
215+
const focusedId = this.groupContext.focusedTabId;
216+
return focusedId ? focusedId === this.id : this.isSelected;
217+
},
218+
214219
buttonKind () {
215220
if (this.groupContext.outlined) {
216221
return this.groupContext.kind === 'muted' ? 'muted' : 'default';

packages/dialtone-vue/components/tab/tab_group.test.js

Lines changed: 72 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -242,11 +242,11 @@ describe('DtTabGroup Tests', () => {
242242
});
243243

244244
describe('Correct key navigation', () => {
245-
describe('On keyup left', () => {
245+
describe('On arrow left', () => {
246246
beforeEach(async () => {
247247
returnFirstEl(tabs.at(0).vm.$el).focus();
248248
await tabList.trigger('keydown.left');
249-
await tabList.trigger('keyup.space');
249+
await tabList.trigger('keydown.space');
250250
});
251251

252252
it('selected element should be correct', () => {
@@ -255,12 +255,12 @@ describe('DtTabGroup Tests', () => {
255255
});
256256
});
257257

258-
describe('On double keyup left and space', () => {
258+
describe('On double arrow left and space', () => {
259259
beforeEach(async () => {
260260
returnFirstEl(tabs.at(0).vm.$el).focus();
261261
await tabList.trigger('keydown.left');
262262
await tabList.trigger('keydown.left');
263-
await tabList.trigger('keyup.space');
263+
await tabList.trigger('keydown.space');
264264
});
265265

266266
it('selected element should be correct', () => {
@@ -273,7 +273,7 @@ describe('DtTabGroup Tests', () => {
273273
beforeEach(async () => {
274274
returnFirstEl(tabs.at(0).vm.$el).focus();
275275
await tabList.trigger('keydown.right');
276-
await tabList.trigger('keyup.enter');
276+
await tabList.trigger('keydown.enter');
277277
});
278278

279279
it('selected element should be correct', () => {
@@ -282,12 +282,12 @@ describe('DtTabGroup Tests', () => {
282282
});
283283
});
284284

285-
describe('On double keyup right and enter', () => {
285+
describe('On double arrow right and enter', () => {
286286
beforeEach(async () => {
287287
returnFirstEl(tabs.at(0).vm.$el).focus();
288288
await tabList.trigger('keydown.right');
289289
await tabList.trigger('keydown.right');
290-
await tabList.trigger('keyup.enter');
290+
await tabList.trigger('keydown.enter');
291291
});
292292

293293
it('selected element should be correct', () => {
@@ -300,7 +300,7 @@ describe('DtTabGroup Tests', () => {
300300
beforeEach(async () => {
301301
returnFirstEl(tabs.at(2).vm.$el).focus();
302302
await tabList.trigger('keydown.home');
303-
await tabList.trigger('keyup.enter');
303+
await tabList.trigger('keydown.enter');
304304
});
305305

306306
it('selected element should be correct', () => {
@@ -313,7 +313,7 @@ describe('DtTabGroup Tests', () => {
313313
beforeEach(async () => {
314314
returnFirstEl(tabs.at(0).vm.$el).focus();
315315
await tabList.trigger('keydown.end');
316-
await tabList.trigger('keyup.enter');
316+
await tabList.trigger('keydown.enter');
317317
});
318318

319319
it('selected element should be correct', () => {
@@ -346,15 +346,15 @@ describe('DtTabGroup Tests', () => {
346346
_setWrappers();
347347
});
348348

349-
it('should land on disabled tab on keyup right', async () => {
349+
it('should land on disabled tab on arrow right', async () => {
350350
returnFirstEl(tabs.at(0).vm.$el).focus();
351351
await tabList.trigger('keydown.right');
352352

353353
expect(document.activeElement.id).toBe('dt-tab-3');
354354
expect(tabs.at(0).attributes('aria-selected')).toBe('true');
355355
});
356356

357-
it('should land on disabled tab on keyup left', async () => {
357+
it('should land on disabled tab on arrow left', async () => {
358358
returnFirstEl(tabs.at(2).vm.$el).focus();
359359
await tabList.trigger('keydown.left');
360360

@@ -365,7 +365,7 @@ describe('DtTabGroup Tests', () => {
365365
it('should not select disabled tab on enter', async () => {
366366
returnFirstEl(tabs.at(0).vm.$el).focus();
367367
await tabList.trigger('keydown.right');
368-
await tabList.trigger('keyup.enter');
368+
await tabList.trigger('keydown.enter');
369369

370370
expect(tabs.at(0).attributes('aria-selected')).toBe('true');
371371
expect(tabs.at(1).attributes('aria-selected')).toBe('false');
@@ -375,7 +375,7 @@ describe('DtTabGroup Tests', () => {
375375
it('should not select disabled tab on space', async () => {
376376
returnFirstEl(tabs.at(0).vm.$el).focus();
377377
await tabList.trigger('keydown.right');
378-
await tabList.trigger('keyup.space');
378+
await tabList.trigger('keydown.space');
379379

380380
expect(tabs.at(0).attributes('aria-selected')).toBe('true');
381381
expect(tabs.at(1).attributes('aria-selected')).toBe('false');
@@ -542,10 +542,54 @@ describe('DtTabGroup Tests', () => {
542542
});
543543
});
544544

545+
describe('Roving tabindex', () => {
546+
describe('In manual mode', () => {
547+
beforeEach(() => {
548+
props.selected = optionTabs[0].panelId;
549+
delete props.activationMode;
550+
_mountWrapper();
551+
});
552+
553+
it('should move tabindex to focused tab on arrow right', async () => {
554+
returnFirstEl(tabs.at(0).vm.$el).focus();
555+
await tabList.trigger('keydown.right');
556+
557+
expect(tabs.at(1).attributes('tabindex')).toBe('0');
558+
expect(tabs.at(0).attributes('tabindex')).toBe('-1');
559+
});
560+
561+
it('should keep tabindex on focused tab after multiple arrows', async () => {
562+
returnFirstEl(tabs.at(0).vm.$el).focus();
563+
await tabList.trigger('keydown.right');
564+
await tabList.trigger('keydown.right');
565+
566+
expect(tabs.at(2).attributes('tabindex')).toBe('0');
567+
expect(tabs.at(0).attributes('tabindex')).toBe('-1');
568+
expect(tabs.at(1).attributes('tabindex')).toBe('-1');
569+
});
570+
});
571+
572+
describe('When selected prop changes externally', () => {
573+
beforeEach(async () => {
574+
_mountWrapper();
575+
returnFirstEl(tabs.at(0).vm.$el).focus();
576+
await tabList.trigger('keydown.right');
577+
});
578+
579+
it('should reset tabindex to new selected tab', async () => {
580+
props.selected = optionTabs[2].panelId;
581+
await wrapper.setProps(props);
582+
583+
expect(tabs.at(2).attributes('tabindex')).toBe('0');
584+
expect(tabs.at(1).attributes('tabindex')).toBe('-1');
585+
});
586+
});
587+
});
588+
545589
describe('Accessibility Tests', () => {
546590
beforeEach(async () => {
547591
returnFirstEl(tabs.at(0).vm.$el).focus();
548-
await tabList.trigger('keyup.enter');
592+
await tabList.trigger('keydown.enter');
549593
});
550594

551595
it('should render correct attributes', () => {
@@ -558,13 +602,13 @@ describe('DtTabGroup Tests', () => {
558602
});
559603

560604
describe('Correct aria attributes', () => {
561-
describe('Attributes after keyup left', () => {
605+
describe('Attributes after arrow left', () => {
562606
let lastTab;
563607
let lastPanel;
564608
beforeEach(async () => {
565609
returnFirstEl(tabs.at(0).vm.$el).focus();
566610
await tabList.trigger('keydown.left');
567-
await tabList.trigger('keyup.space');
611+
await tabList.trigger('keydown.space');
568612
lastTab = tabs.at(2).attributes();
569613
lastPanel = tabPanels.at(2).attributes();
570614
});
@@ -575,11 +619,11 @@ describe('DtTabGroup Tests', () => {
575619
});
576620
});
577621

578-
describe('attributes after keyup right', () => {
622+
describe('attributes after arrow right', () => {
579623
beforeEach(async () => {
580624
returnFirstEl(tabs.at(0).vm.$el).focus();
581625
await tabList.trigger('keydown.right');
582-
await tabList.trigger('keyup.enter');
626+
await tabList.trigger('keydown.enter');
583627
});
584628

585629
it(
@@ -597,7 +641,7 @@ describe('DtTabGroup Tests', () => {
597641
beforeEach(async () => {
598642
returnFirstEl(tabs.at(2).vm.$el).focus();
599643
await tabList.trigger('keydown.home');
600-
await tabList.trigger('keyup.enter');
644+
await tabList.trigger('keydown.enter');
601645
});
602646

603647
it(
@@ -615,7 +659,7 @@ describe('DtTabGroup Tests', () => {
615659
beforeEach(async () => {
616660
returnFirstEl(tabs.at(0).vm.$el).focus();
617661
await tabList.trigger('keydown.end');
618-
await tabList.trigger('keyup.enter');
662+
await tabList.trigger('keydown.enter');
619663
});
620664

621665
it(
@@ -653,7 +697,7 @@ describe('DtTabGroup Tests', () => {
653697
it('should navigate to next tab on arrow down', async () => {
654698
returnFirstEl(tabs.at(0).vm.$el).focus();
655699
await tabList.trigger('keydown.down');
656-
await tabList.trigger('keyup.enter');
700+
await tabList.trigger('keydown.enter');
657701

658702
expect(tabs.at(1).attributes('aria-selected')).toBe('true');
659703
expect(tabPanels.at(1).attributes('aria-hidden')).toBe('false');
@@ -662,7 +706,7 @@ describe('DtTabGroup Tests', () => {
662706
it('should navigate to previous tab on arrow up', async () => {
663707
returnFirstEl(tabs.at(0).vm.$el).focus();
664708
await tabList.trigger('keydown.up');
665-
await tabList.trigger('keyup.space');
709+
await tabList.trigger('keydown.space');
666710

667711
expect(tabs.at(2).attributes('aria-selected')).toBe('true');
668712
expect(tabPanels.at(2).attributes('aria-hidden')).toBe('false');
@@ -671,31 +715,31 @@ describe('DtTabGroup Tests', () => {
671715
it('should NOT navigate on arrow left', async () => {
672716
returnFirstEl(tabs.at(0).vm.$el).focus();
673717
await tabList.trigger('keydown.left');
674-
await tabList.trigger('keyup.enter');
718+
await tabList.trigger('keydown.enter');
675719

676720
expect(wrapper.emitted('change')).toBeUndefined();
677721
});
678722

679723
it('should NOT navigate on arrow right', async () => {
680724
returnFirstEl(tabs.at(0).vm.$el).focus();
681725
await tabList.trigger('keydown.right');
682-
await tabList.trigger('keyup.enter');
726+
await tabList.trigger('keydown.enter');
683727

684728
expect(wrapper.emitted('change')).toBeUndefined();
685729
});
686730

687731
it('should navigate to first tab on home', async () => {
688732
returnFirstEl(tabs.at(2).vm.$el).focus();
689733
await tabList.trigger('keydown.home');
690-
await tabList.trigger('keyup.enter');
734+
await tabList.trigger('keydown.enter');
691735

692736
expect(tabs.at(0).attributes('aria-selected')).toBe('true');
693737
});
694738

695739
it('should navigate to last tab on end', async () => {
696740
returnFirstEl(tabs.at(0).vm.$el).focus();
697741
await tabList.trigger('keydown.end');
698-
await tabList.trigger('keyup.enter');
742+
await tabList.trigger('keydown.enter');
699743

700744
expect(tabs.at(2).attributes('aria-selected')).toBe('true');
701745
});
@@ -743,15 +787,15 @@ describe('DtTabGroup Tests', () => {
743787
it('should NOT navigate on arrow up', async () => {
744788
returnFirstEl(tabs.at(0).vm.$el).focus();
745789
await tabList.trigger('keydown.up');
746-
await tabList.trigger('keyup.enter');
790+
await tabList.trigger('keydown.enter');
747791

748792
expect(wrapper.emitted('change')).toBeUndefined();
749793
});
750794

751795
it('should NOT navigate on arrow down', async () => {
752796
returnFirstEl(tabs.at(0).vm.$el).focus();
753797
await tabList.trigger('keydown.down');
754-
await tabList.trigger('keyup.enter');
798+
await tabList.trigger('keydown.enter');
755799

756800
expect(wrapper.emitted('change')).toBeUndefined();
757801
});

0 commit comments

Comments
 (0)