Merge pull request #783 from ing-bank/fix/keyboard-interactio-accordion

fix(accordion): fix keyboard interaction
This commit is contained in:
gerjanvangeest 2020-06-24 16:28:04 +02:00 committed by GitHub
commit 9f6fbb66a1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 40 additions and 38 deletions

View file

@ -2,41 +2,41 @@
"name": "@lion/accordion",
"version": "0.1.1",
"description": "Vertically stacked list of invokers that can be clicked to reveal or hide content associated with them.",
"license": "MIT",
"author": "ing-bank",
"homepage": "https://github.com/ing-bank/lion/",
"license": "MIT",
"publishConfig": {
"access": "public"
},
"repository": {
"type": "git",
"url": "https://github.com/ing-bank/lion.git",
"directory": "packages/accordion"
},
"main": "index.js",
"module": "index.js",
"files": [
"*.js",
"docs",
"src",
"test",
"translations"
],
"scripts": {
"prepublishOnly": "../../scripts/npm-prepublish.js",
"start": "cd ../../ && yarn dev-server --open packages/tabs/README.md",
"test": "cd ../../ && yarn test:browser --grep \"packages/tabs/test/**/*.test.js\"",
"test:watch": "cd ../../ && yarn test:browser:watch --grep \"packages/tabs/test/**/*.test.js\""
},
"keywords": [
"lion",
"web-components",
"accordion"
],
"main": "index.js",
"module": "index.js",
"files": [
"docs",
"src",
"test",
"translations",
"*.js"
],
"sideEffects": [
"lion-accordion.js"
],
"dependencies": {
"@lion/core": "0.7.2"
},
"keywords": [
"accordion",
"lion",
"web-components"
],
"publishConfig": {
"access": "public"
}
}

View file

@ -13,14 +13,14 @@ const setupInvoker = ({ element, uid, index, clickHandler, keydownHandler }) =>
element.firstElementChild.setAttribute('id', `invoker-${uid}`);
element.firstElementChild.setAttribute('aria-controls', `content-${uid}`);
element.firstElementChild.addEventListener('click', clickHandler);
element.firstElementChild.addEventListener('keyup', keydownHandler);
element.firstElementChild.addEventListener('keydown', keydownHandler);
};
const cleanInvoker = (element, clickHandler, keydownHandler) => {
element.firstElementChild.removeAttribute('id');
element.firstElementChild.removeAttribute('aria-controls');
element.firstElementChild.removeEventListener('click', clickHandler);
element.firstElementChild.removeEventListener('keyup', keydownHandler);
element.firstElementChild.removeEventListener('keydown', keydownHandler);
};
const focusInvoker = element => {
@ -190,18 +190,14 @@ export class LionAccordion extends LitElement {
case 'ArrowDown':
case 'ArrowRight':
e.preventDefault();
if (this.focusedIndex + 1 >= this._pairCount) {
this.focusedIndex = 0;
} else {
if (this.focusedIndex + 2 <= this._pairCount) {
this.focusedIndex += 1;
}
break;
case 'ArrowUp':
case 'ArrowLeft':
e.preventDefault();
if (this.focusedIndex <= 0) {
this.focusedIndex = this._pairCount - 1;
} else {
if (this.focusedIndex >= 1) {
this.focusedIndex -= 1;
}
break;

View file

@ -199,10 +199,12 @@ describe('<lion-accordion>', () => {
const invokers = el.querySelectorAll('[slot=invoker]');
el.focusedIndex = 0;
invokers[0].firstElementChild.dispatchEvent(
new KeyboardEvent('keyup', { key: 'ArrowRight' }),
new KeyboardEvent('keydown', { key: 'ArrowRight' }),
);
expect(el.focusedIndex).to.equal(1);
invokers[0].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'ArrowDown' }));
invokers[0].firstElementChild.dispatchEvent(
new KeyboardEvent('keydown', { key: 'ArrowDown' }),
);
expect(el.focusedIndex).to.equal(2);
});
@ -219,9 +221,11 @@ describe('<lion-accordion>', () => {
`);
const invokers = el.querySelectorAll('[slot=invoker]');
el.focusedIndex = 2;
invokers[2].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'ArrowLeft' }));
invokers[2].firstElementChild.dispatchEvent(
new KeyboardEvent('keydown', { key: 'ArrowLeft' }),
);
expect(el.focusedIndex).to.equal(1);
invokers[1].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'ArrowUp' }));
invokers[1].firstElementChild.dispatchEvent(new KeyboardEvent('keydown', { key: 'ArrowUp' }));
expect(el.focusedIndex).to.equal(0);
});
@ -235,18 +239,18 @@ describe('<lion-accordion>', () => {
</lion-accordion>
`);
const invokers = el.querySelectorAll('[slot=invoker]');
invokers[1].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'Home' }));
invokers[1].firstElementChild.dispatchEvent(new KeyboardEvent('keydown', { key: 'Home' }));
expect(el.focusedIndex).to.equal(0);
});
it('selects last invoker on [end]', async () => {
const el = await fixture(basicAccordion);
const invokers = el.querySelectorAll('[slot=invoker]');
invokers[0].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'End' }));
invokers[0].firstElementChild.dispatchEvent(new KeyboardEvent('keydown', { key: 'End' }));
expect(el.focusedIndex).to.equal(2);
});
it('selects first invoker on [arrow-right] if on last invoker', async () => {
it('stays on last invoker on [arrow-right]', async () => {
const el = await fixture(html`
<lion-accordion focusedIndex="2">
<h2 slot="invoker"><button>invoker 1</button></h2>
@ -259,12 +263,12 @@ describe('<lion-accordion>', () => {
`);
const invokers = el.querySelectorAll('[slot=invoker]');
invokers[2].firstElementChild.dispatchEvent(
new KeyboardEvent('keyup', { key: 'ArrowRight' }),
new KeyboardEvent('keydown', { key: 'ArrowRight' }),
);
expect(el.focusedIndex).to.equal(0);
expect(el.focusedIndex).to.equal(2);
});
it('selects last invoker on [arrow-left] if on first invoker', async () => {
it('stays on first invoker on [arrow-left]', async () => {
const el = await fixture(html`
<lion-accordion>
<h2 slot="invoker"><button>invoker 1</button></h2>
@ -276,8 +280,10 @@ describe('<lion-accordion>', () => {
</lion-accordion>
`);
const invokers = el.querySelectorAll('[slot=invoker]');
invokers[0].firstElementChild.dispatchEvent(new KeyboardEvent('keyup', { key: 'ArrowLeft' }));
expect(el.focusedIndex).to.equal(2);
invokers[0].firstElementChild.dispatchEvent(
new KeyboardEvent('keydown', { key: 'ArrowLeft' }),
);
expect(el.focusedIndex).to.equal(null);
});
});