mirror of
https://github.com/fergalmoran/turnstone.git
synced 2025-12-25 19:28:26 +00:00
Add ARIA accessbility attributes to elements
This commit is contained in:
312
package-lock.json
generated
312
package-lock.json
generated
@@ -9,6 +9,7 @@
|
|||||||
"version": "0.3.0",
|
"version": "0.3.0",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"first-of-type": "^1.0.0",
|
"first-of-type": "^1.0.0",
|
||||||
|
"nanoid": "^3.3.1",
|
||||||
"prop-types": "^15.8.1",
|
"prop-types": "^15.8.1",
|
||||||
"react-use": "^17.3.2",
|
"react-use": "^17.3.2",
|
||||||
"setify": "^1.0.4",
|
"setify": "^1.0.4",
|
||||||
@@ -16,6 +17,7 @@
|
|||||||
"use-debounce": "^7.0.1"
|
"use-debounce": "^7.0.1"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
"@testing-library/react": "^12.1.3",
|
||||||
"@testing-library/react-hooks": "^7.0.2",
|
"@testing-library/react-hooks": "^7.0.2",
|
||||||
"@vitejs/plugin-react": "^1.0.7",
|
"@vitejs/plugin-react": "^1.0.7",
|
||||||
"c8": "^7.11.0",
|
"c8": "^7.11.0",
|
||||||
@@ -594,6 +596,113 @@
|
|||||||
"node": ">= 8.0.0"
|
"node": ">= 8.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@testing-library/dom": {
|
||||||
|
"version": "8.11.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/@testing-library/dom/-/dom-8.11.3.tgz",
|
||||||
|
"integrity": "sha512-9LId28I+lx70wUiZjLvi1DB/WT2zGOxUh46glrSNMaWVx849kKAluezVzZrXJfTKKoQTmEOutLes/bHg4Bj3aA==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"@babel/code-frame": "^7.10.4",
|
||||||
|
"@babel/runtime": "^7.12.5",
|
||||||
|
"@types/aria-query": "^4.2.0",
|
||||||
|
"aria-query": "^5.0.0",
|
||||||
|
"chalk": "^4.1.0",
|
||||||
|
"dom-accessibility-api": "^0.5.9",
|
||||||
|
"lz-string": "^1.4.4",
|
||||||
|
"pretty-format": "^27.0.2"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/ansi-styles": {
|
||||||
|
"version": "4.3.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
|
||||||
|
"integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"color-convert": "^2.0.1"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=8"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/chalk": {
|
||||||
|
"version": "4.1.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
|
||||||
|
"integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"ansi-styles": "^4.1.0",
|
||||||
|
"supports-color": "^7.1.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=10"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/chalk/chalk?sponsor=1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/color-convert": {
|
||||||
|
"version": "2.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz",
|
||||||
|
"integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"color-name": "~1.1.4"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=7.0.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/color-name": {
|
||||||
|
"version": "1.1.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz",
|
||||||
|
"integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/has-flag": {
|
||||||
|
"version": "4.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
|
||||||
|
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
|
||||||
|
"dev": true,
|
||||||
|
"engines": {
|
||||||
|
"node": ">=8"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/dom/node_modules/supports-color": {
|
||||||
|
"version": "7.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
|
||||||
|
"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"has-flag": "^4.0.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=8"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/@testing-library/react": {
|
||||||
|
"version": "12.1.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/@testing-library/react/-/react-12.1.3.tgz",
|
||||||
|
"integrity": "sha512-oCULRXWRrBtC9m6G/WohPo1GLcLesH7T4fuKzRAKn1CWVu9BzXtqLXDDTA6KhFNNtRwLtfSMr20HFl+Qrdrvmg==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"@babel/runtime": "^7.12.5",
|
||||||
|
"@testing-library/dom": "^8.0.0",
|
||||||
|
"@types/react-dom": "*"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=12"
|
||||||
|
},
|
||||||
|
"peerDependencies": {
|
||||||
|
"react": "*",
|
||||||
|
"react-dom": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/@testing-library/react-hooks": {
|
"node_modules/@testing-library/react-hooks": {
|
||||||
"version": "7.0.2",
|
"version": "7.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/@testing-library/react-hooks/-/react-hooks-7.0.2.tgz",
|
"resolved": "https://registry.npmjs.org/@testing-library/react-hooks/-/react-hooks-7.0.2.tgz",
|
||||||
@@ -623,6 +732,12 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@types/aria-query": {
|
||||||
|
"version": "4.2.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/@types/aria-query/-/aria-query-4.2.2.tgz",
|
||||||
|
"integrity": "sha512-HnYpAE1Y6kRyKM/XkEuiRQhTHvkzMBurTHnpFLYLBGPIylZNPs9jJcuOOYWxPLJCSEtmZT0Y8rHDokKN7rRTig==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"node_modules/@types/chai": {
|
"node_modules/@types/chai": {
|
||||||
"version": "4.3.0",
|
"version": "4.3.0",
|
||||||
"resolved": "https://registry.npmjs.org/@types/chai/-/chai-4.3.0.tgz",
|
"resolved": "https://registry.npmjs.org/@types/chai/-/chai-4.3.0.tgz",
|
||||||
@@ -873,6 +988,15 @@
|
|||||||
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
|
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"node_modules/aria-query": {
|
||||||
|
"version": "5.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.0.0.tgz",
|
||||||
|
"integrity": "sha512-V+SM7AbUwJ+EBnB8+DXs0hPZHO0W6pqBcc0dW90OwtVG02PswOu/teuARoLQjdDOH+t9pJgGnW5/Qmouf3gPJg==",
|
||||||
|
"dev": true,
|
||||||
|
"engines": {
|
||||||
|
"node": ">=6.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/array-includes": {
|
"node_modules/array-includes": {
|
||||||
"version": "3.1.4",
|
"version": "3.1.4",
|
||||||
"resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz",
|
"resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz",
|
||||||
@@ -1393,6 +1517,12 @@
|
|||||||
"node": ">=6.0.0"
|
"node": ">=6.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/dom-accessibility-api": {
|
||||||
|
"version": "0.5.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/dom-accessibility-api/-/dom-accessibility-api-0.5.11.tgz",
|
||||||
|
"integrity": "sha512-7X6GvzjYf4yTdRKuCVScV+aA9Fvh5r8WzWrXBH9w82ZWB/eYDMGCnazoC/YAqAzUJWHzLOnZqr46K3iEyUhUvw==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"node_modules/electron-to-chromium": {
|
"node_modules/electron-to-chromium": {
|
||||||
"version": "1.4.68",
|
"version": "1.4.68",
|
||||||
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.68.tgz",
|
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.68.tgz",
|
||||||
@@ -3238,6 +3368,15 @@
|
|||||||
"get-func-name": "^2.0.0"
|
"get-func-name": "^2.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/lz-string": {
|
||||||
|
"version": "1.4.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/lz-string/-/lz-string-1.4.4.tgz",
|
||||||
|
"integrity": "sha1-wNjq82BZ9wV5bh40SBHPTEmNOiY=",
|
||||||
|
"dev": true,
|
||||||
|
"bin": {
|
||||||
|
"lz-string": "bin/bin.js"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/make-dir": {
|
"node_modules/make-dir": {
|
||||||
"version": "3.1.0",
|
"version": "3.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz",
|
||||||
@@ -3462,10 +3601,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/nanoid": {
|
"node_modules/nanoid": {
|
||||||
"version": "3.2.0",
|
"version": "3.3.1",
|
||||||
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
|
||||||
"integrity": "sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA==",
|
"integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw==",
|
||||||
"dev": true,
|
|
||||||
"bin": {
|
"bin": {
|
||||||
"nanoid": "bin/nanoid.cjs"
|
"nanoid": "bin/nanoid.cjs"
|
||||||
},
|
},
|
||||||
@@ -3908,6 +4046,38 @@
|
|||||||
"node": ">= 0.8.0"
|
"node": ">= 0.8.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/pretty-format": {
|
||||||
|
"version": "27.5.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-27.5.1.tgz",
|
||||||
|
"integrity": "sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==",
|
||||||
|
"dev": true,
|
||||||
|
"dependencies": {
|
||||||
|
"ansi-regex": "^5.0.1",
|
||||||
|
"ansi-styles": "^5.0.0",
|
||||||
|
"react-is": "^17.0.1"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pretty-format/node_modules/ansi-styles": {
|
||||||
|
"version": "5.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz",
|
||||||
|
"integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==",
|
||||||
|
"dev": true,
|
||||||
|
"engines": {
|
||||||
|
"node": ">=10"
|
||||||
|
},
|
||||||
|
"funding": {
|
||||||
|
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/pretty-format/node_modules/react-is": {
|
||||||
|
"version": "17.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/react-is/-/react-is-17.0.2.tgz",
|
||||||
|
"integrity": "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"node_modules/prop-types": {
|
"node_modules/prop-types": {
|
||||||
"version": "15.8.1",
|
"version": "15.8.1",
|
||||||
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
|
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
|
||||||
@@ -5440,6 +5610,84 @@
|
|||||||
"picomatch": "^2.2.2"
|
"picomatch": "^2.2.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"@testing-library/dom": {
|
||||||
|
"version": "8.11.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/@testing-library/dom/-/dom-8.11.3.tgz",
|
||||||
|
"integrity": "sha512-9LId28I+lx70wUiZjLvi1DB/WT2zGOxUh46glrSNMaWVx849kKAluezVzZrXJfTKKoQTmEOutLes/bHg4Bj3aA==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"@babel/code-frame": "^7.10.4",
|
||||||
|
"@babel/runtime": "^7.12.5",
|
||||||
|
"@types/aria-query": "^4.2.0",
|
||||||
|
"aria-query": "^5.0.0",
|
||||||
|
"chalk": "^4.1.0",
|
||||||
|
"dom-accessibility-api": "^0.5.9",
|
||||||
|
"lz-string": "^1.4.4",
|
||||||
|
"pretty-format": "^27.0.2"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"ansi-styles": {
|
||||||
|
"version": "4.3.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz",
|
||||||
|
"integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"color-convert": "^2.0.1"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"chalk": {
|
||||||
|
"version": "4.1.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz",
|
||||||
|
"integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"ansi-styles": "^4.1.0",
|
||||||
|
"supports-color": "^7.1.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"color-convert": {
|
||||||
|
"version": "2.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz",
|
||||||
|
"integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"color-name": "~1.1.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"color-name": {
|
||||||
|
"version": "1.1.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz",
|
||||||
|
"integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
|
"has-flag": {
|
||||||
|
"version": "4.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
|
||||||
|
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
|
"supports-color": {
|
||||||
|
"version": "7.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
|
||||||
|
"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"has-flag": "^4.0.0"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@testing-library/react": {
|
||||||
|
"version": "12.1.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/@testing-library/react/-/react-12.1.3.tgz",
|
||||||
|
"integrity": "sha512-oCULRXWRrBtC9m6G/WohPo1GLcLesH7T4fuKzRAKn1CWVu9BzXtqLXDDTA6KhFNNtRwLtfSMr20HFl+Qrdrvmg==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"@babel/runtime": "^7.12.5",
|
||||||
|
"@testing-library/dom": "^8.0.0",
|
||||||
|
"@types/react-dom": "*"
|
||||||
|
}
|
||||||
|
},
|
||||||
"@testing-library/react-hooks": {
|
"@testing-library/react-hooks": {
|
||||||
"version": "7.0.2",
|
"version": "7.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/@testing-library/react-hooks/-/react-hooks-7.0.2.tgz",
|
"resolved": "https://registry.npmjs.org/@testing-library/react-hooks/-/react-hooks-7.0.2.tgz",
|
||||||
@@ -5453,6 +5701,12 @@
|
|||||||
"react-error-boundary": "^3.1.0"
|
"react-error-boundary": "^3.1.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"@types/aria-query": {
|
||||||
|
"version": "4.2.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/@types/aria-query/-/aria-query-4.2.2.tgz",
|
||||||
|
"integrity": "sha512-HnYpAE1Y6kRyKM/XkEuiRQhTHvkzMBurTHnpFLYLBGPIylZNPs9jJcuOOYWxPLJCSEtmZT0Y8rHDokKN7rRTig==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"@types/chai": {
|
"@types/chai": {
|
||||||
"version": "4.3.0",
|
"version": "4.3.0",
|
||||||
"resolved": "https://registry.npmjs.org/@types/chai/-/chai-4.3.0.tgz",
|
"resolved": "https://registry.npmjs.org/@types/chai/-/chai-4.3.0.tgz",
|
||||||
@@ -5666,6 +5920,12 @@
|
|||||||
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
|
"integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"aria-query": {
|
||||||
|
"version": "5.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/aria-query/-/aria-query-5.0.0.tgz",
|
||||||
|
"integrity": "sha512-V+SM7AbUwJ+EBnB8+DXs0hPZHO0W6pqBcc0dW90OwtVG02PswOu/teuARoLQjdDOH+t9pJgGnW5/Qmouf3gPJg==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"array-includes": {
|
"array-includes": {
|
||||||
"version": "3.1.4",
|
"version": "3.1.4",
|
||||||
"resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz",
|
"resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.4.tgz",
|
||||||
@@ -6048,6 +6308,12 @@
|
|||||||
"esutils": "^2.0.2"
|
"esutils": "^2.0.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"dom-accessibility-api": {
|
||||||
|
"version": "0.5.11",
|
||||||
|
"resolved": "https://registry.npmjs.org/dom-accessibility-api/-/dom-accessibility-api-0.5.11.tgz",
|
||||||
|
"integrity": "sha512-7X6GvzjYf4yTdRKuCVScV+aA9Fvh5r8WzWrXBH9w82ZWB/eYDMGCnazoC/YAqAzUJWHzLOnZqr46K3iEyUhUvw==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"electron-to-chromium": {
|
"electron-to-chromium": {
|
||||||
"version": "1.4.68",
|
"version": "1.4.68",
|
||||||
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.68.tgz",
|
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.68.tgz",
|
||||||
@@ -7307,6 +7573,12 @@
|
|||||||
"get-func-name": "^2.0.0"
|
"get-func-name": "^2.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"lz-string": {
|
||||||
|
"version": "1.4.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/lz-string/-/lz-string-1.4.4.tgz",
|
||||||
|
"integrity": "sha1-wNjq82BZ9wV5bh40SBHPTEmNOiY=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"make-dir": {
|
"make-dir": {
|
||||||
"version": "3.1.0",
|
"version": "3.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz",
|
||||||
@@ -7476,10 +7748,9 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"nanoid": {
|
"nanoid": {
|
||||||
"version": "3.2.0",
|
"version": "3.3.1",
|
||||||
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz",
|
||||||
"integrity": "sha512-fmsZYa9lpn69Ad5eDn7FMcnnSR+8R34W9qJEijxYhTbfOWzr22n1QxCMzXLK+ODyW2973V3Fux959iQoUxzUIA==",
|
"integrity": "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw=="
|
||||||
"dev": true
|
|
||||||
},
|
},
|
||||||
"natural-compare": {
|
"natural-compare": {
|
||||||
"version": "1.4.0",
|
"version": "1.4.0",
|
||||||
@@ -7789,6 +8060,31 @@
|
|||||||
"integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==",
|
"integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"pretty-format": {
|
||||||
|
"version": "27.5.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-27.5.1.tgz",
|
||||||
|
"integrity": "sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"ansi-regex": "^5.0.1",
|
||||||
|
"ansi-styles": "^5.0.0",
|
||||||
|
"react-is": "^17.0.1"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"ansi-styles": {
|
||||||
|
"version": "5.2.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz",
|
||||||
|
"integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
|
"react-is": {
|
||||||
|
"version": "17.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/react-is/-/react-is-17.0.2.tgz",
|
||||||
|
"integrity": "sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==",
|
||||||
|
"dev": true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"prop-types": {
|
"prop-types": {
|
||||||
"version": "15.8.1",
|
"version": "15.8.1",
|
||||||
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
|
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
|
||||||
|
|||||||
@@ -26,6 +26,7 @@
|
|||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"first-of-type": "^1.0.0",
|
"first-of-type": "^1.0.0",
|
||||||
|
"nanoid": "^3.3.1",
|
||||||
"prop-types": "^15.8.1",
|
"prop-types": "^15.8.1",
|
||||||
"react-use": "^17.3.2",
|
"react-use": "^17.3.2",
|
||||||
"setify": "^1.0.4",
|
"setify": "^1.0.4",
|
||||||
@@ -33,6 +34,7 @@
|
|||||||
"use-debounce": "^7.0.1"
|
"use-debounce": "^7.0.1"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
"@testing-library/react": "^12.1.3",
|
||||||
"@testing-library/react-hooks": "^7.0.2",
|
"@testing-library/react-hooks": "^7.0.2",
|
||||||
"@vitejs/plugin-react": "^1.0.7",
|
"@vitejs/plugin-react": "^1.0.7",
|
||||||
"c8": "^7.11.0",
|
"c8": "^7.11.0",
|
||||||
|
|||||||
28
src/App.jsx
28
src/App.jsx
@@ -8,18 +8,22 @@ const styles = {
|
|||||||
|
|
||||||
const App = () => {
|
const App = () => {
|
||||||
return (
|
return (
|
||||||
<Turnstone
|
<>
|
||||||
autoFocus={true}
|
<label htmlFor="autocomplete">Search:</label>
|
||||||
data={fruits}
|
<Turnstone
|
||||||
dataSearchType={'startswith'}
|
autoFocus={true}
|
||||||
debounceWait={0}
|
clearButton={true}
|
||||||
itemGroupsAreImmutable={true}
|
data={fruits}
|
||||||
maxItems={10}
|
dataSearchType={'startswith'}
|
||||||
noItemsMessage={'No matching fruit found'}
|
debounceWait={0}
|
||||||
placeholder={'Type something fruity'}
|
id={'autocomplete'}
|
||||||
styles={styles}
|
itemGroupsAreImmutable={true}
|
||||||
minQueryLength={1}
|
maxItems={10}
|
||||||
/>
|
noItemsMessage={'No matching fruit found'}
|
||||||
|
placeholder={'Type something fruity'}
|
||||||
|
styles={styles}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
body {
|
body {
|
||||||
margin: 0;
|
margin: 30px;
|
||||||
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',
|
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',
|
||||||
'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
|
'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
|
||||||
sans-serif;
|
sans-serif;
|
||||||
|
|||||||
@@ -2,14 +2,21 @@
|
|||||||
|
|
||||||
exports[`Container > Component renders correctly 1`] = `
|
exports[`Container > Component renders correctly 1`] = `
|
||||||
<div
|
<div
|
||||||
|
aria-expanded={false}
|
||||||
|
aria-haspopup="listbox"
|
||||||
|
aria-owns="undefined-dropdown"
|
||||||
className="query-container-class"
|
className="query-container-class"
|
||||||
|
role="combobox"
|
||||||
style={
|
style={
|
||||||
{
|
{
|
||||||
|
"display": "inline-block",
|
||||||
"position": "relative",
|
"position": "relative",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
<input
|
<input
|
||||||
|
aria-autocomplete="both"
|
||||||
|
aria-controls="undefined-dropdown"
|
||||||
autoCapitalize="off"
|
autoCapitalize="off"
|
||||||
autoComplete="off"
|
autoComplete="off"
|
||||||
autoCorrect="off"
|
autoCorrect="off"
|
||||||
@@ -31,6 +38,7 @@ exports[`Container > Component renders correctly 1`] = `
|
|||||||
type="text"
|
type="text"
|
||||||
/>
|
/>
|
||||||
<input
|
<input
|
||||||
|
aria-hidden="true"
|
||||||
autoCapitalize="off"
|
autoCapitalize="off"
|
||||||
autoComplete="off"
|
autoComplete="off"
|
||||||
autoCorrect="off"
|
autoCorrect="off"
|
||||||
|
|||||||
@@ -2,9 +2,12 @@
|
|||||||
|
|
||||||
exports[`Item > Component renders correctly 1`] = `
|
exports[`Item > Component renders correctly 1`] = `
|
||||||
<div
|
<div
|
||||||
|
aria-label="Chicago, Illinois, United States"
|
||||||
|
aria-selected={[Function]}
|
||||||
className="item-class top-item-class"
|
className="item-class top-item-class"
|
||||||
onMouseDown={[Function]}
|
onMouseDown={[Function]}
|
||||||
onMouseEnter={[Function]}
|
onMouseEnter={[Function]}
|
||||||
|
role="option"
|
||||||
style={
|
style={
|
||||||
{
|
{
|
||||||
"overflow": "hidden",
|
"overflow": "hidden",
|
||||||
@@ -23,9 +26,12 @@ exports[`Item > Component renders correctly 1`] = `
|
|||||||
|
|
||||||
exports[`Item > Link changes the class when hovered 1`] = `
|
exports[`Item > Link changes the class when hovered 1`] = `
|
||||||
<div
|
<div
|
||||||
|
aria-label="Chicago, Illinois, United States"
|
||||||
|
aria-selected={[Function]}
|
||||||
className="highlighted-item-class top-item-class"
|
className="highlighted-item-class top-item-class"
|
||||||
onMouseDown={[Function]}
|
onMouseDown={[Function]}
|
||||||
onMouseEnter={[Function]}
|
onMouseEnter={[Function]}
|
||||||
|
role="option"
|
||||||
style={
|
style={
|
||||||
{
|
{
|
||||||
"overflow": "hidden",
|
"overflow": "hidden",
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import React, { useState, useRef, useContext } from 'react'
|
import React, { useState, useMemo, useRef, useContext } from 'react'
|
||||||
import { StateContext } from '../context/state'
|
import { StateContext } from '../context/state'
|
||||||
import Items from './items'
|
import Items from './items'
|
||||||
import { useDebounce } from 'use-debounce'
|
import { useDebounce } from 'use-debounce'
|
||||||
@@ -25,12 +25,16 @@ export default function Container(props) {
|
|||||||
// Destructure props
|
// Destructure props
|
||||||
const {
|
const {
|
||||||
autoFocus,
|
autoFocus,
|
||||||
|
clearButton,
|
||||||
|
clearButtonAriaLabel,
|
||||||
|
clearButtonText,
|
||||||
debounceWait,
|
debounceWait,
|
||||||
defaultItemGroups,
|
defaultItemGroups,
|
||||||
defaultItemGroupsAreImmutable,
|
defaultItemGroupsAreImmutable,
|
||||||
displayField,
|
displayField,
|
||||||
data,
|
data,
|
||||||
dataSearchType,
|
dataSearchType,
|
||||||
|
id,
|
||||||
isDisabled,
|
isDisabled,
|
||||||
itemGroupsAreImmutable,
|
itemGroupsAreImmutable,
|
||||||
maxItems,
|
maxItems,
|
||||||
@@ -56,6 +60,8 @@ export default function Container(props) {
|
|||||||
]
|
]
|
||||||
} = props
|
} = props
|
||||||
|
|
||||||
|
const dropdownId = `${id}-dropdown`
|
||||||
|
|
||||||
// Global state from context
|
// Global state from context
|
||||||
const { state, dispatch } = useContext(StateContext)
|
const { state, dispatch } = useContext(StateContext)
|
||||||
const { customStyles } = state
|
const { customStyles } = state
|
||||||
@@ -117,15 +123,15 @@ export default function Container(props) {
|
|||||||
if (typeof f === 'function') f(queryInput.current.value, highlightedItem)
|
if (typeof f === 'function') f(queryInput.current.value, highlightedItem)
|
||||||
}
|
}
|
||||||
|
|
||||||
const isX = () => {
|
const hasClearButton = () => {
|
||||||
return !!state.query
|
return clearButton && !!state.query
|
||||||
}
|
}
|
||||||
|
|
||||||
const isDropdown = () => {
|
const isExpanded = useMemo(() => {
|
||||||
if (hasFocus && !state.query && defaultItemGroups) return true
|
if (hasFocus && !state.query && defaultItemGroups) return true
|
||||||
if (state.query.length < minQueryLength) return false
|
if (state.query.length < minQueryLength) return false
|
||||||
return hasFocus && state.query
|
return hasFocus && !!state.query
|
||||||
}
|
}, [hasFocus, state.query, defaultItemGroups, minQueryLength])
|
||||||
|
|
||||||
// Handle different keypresses and call the appropriate action creators
|
// Handle different keypresses and call the appropriate action creators
|
||||||
const checkKey = (evt) => {
|
const checkKey = (evt) => {
|
||||||
@@ -157,7 +163,8 @@ export default function Container(props) {
|
|||||||
dispatch(setQuery(queryInput.current.value))
|
dispatch(setQuery(queryInput.current.value))
|
||||||
}
|
}
|
||||||
|
|
||||||
const handleX = (evt) => {
|
const handleClearButton = (evt) => {
|
||||||
|
console.log('handleClearButton')
|
||||||
evt.preventDefault()
|
evt.preventDefault()
|
||||||
clearState()
|
clearState()
|
||||||
}
|
}
|
||||||
@@ -181,8 +188,15 @@ export default function Container(props) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<React.Fragment>
|
<React.Fragment>
|
||||||
<div className={customStyles.queryContainer} style={defaultStyles.queryContainer}>
|
<div
|
||||||
|
className={customStyles.queryContainer}
|
||||||
|
style={defaultStyles.queryContainer}
|
||||||
|
role='combobox'
|
||||||
|
aria-expanded={isExpanded}
|
||||||
|
aria-owns={dropdownId}
|
||||||
|
aria-haspopup='listbox'>
|
||||||
<input
|
<input
|
||||||
|
id={id}
|
||||||
className={customStyles.query}
|
className={customStyles.query}
|
||||||
style={defaultStyles.query}
|
style={defaultStyles.query}
|
||||||
disabled={isDisabled}
|
disabled={isDisabled}
|
||||||
@@ -198,6 +212,8 @@ export default function Container(props) {
|
|||||||
onInput={handleInput}
|
onInput={handleInput}
|
||||||
onFocus={handleFocus}
|
onFocus={handleFocus}
|
||||||
onBlur={handleBlur}
|
onBlur={handleBlur}
|
||||||
|
aria-autocomplete='both'
|
||||||
|
aria-controls={dropdownId}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<input
|
<input
|
||||||
@@ -211,15 +227,23 @@ export default function Container(props) {
|
|||||||
spellCheck='false'
|
spellCheck='false'
|
||||||
tabIndex='-1'
|
tabIndex='-1'
|
||||||
readOnly='readonly'
|
readOnly='readonly'
|
||||||
|
aria-hidden='true'
|
||||||
ref={typeaheadInput}
|
ref={typeaheadInput}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{isX() && (
|
{hasClearButton() && (
|
||||||
<div className={customStyles.x} style={defaultStyles.x} onMouseDown={handleX} />
|
<div
|
||||||
|
className={customStyles.clearButton}
|
||||||
|
style={defaultStyles.clearButton}
|
||||||
|
onMouseDown={handleClearButton}
|
||||||
|
tabIndex={-1}
|
||||||
|
role='button'
|
||||||
|
aria-label={clearButtonAriaLabel}>{clearButtonText}</div>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{isDropdown() && (
|
{isExpanded && (
|
||||||
<Items
|
<Items
|
||||||
|
id={dropdownId}
|
||||||
items={state.items}
|
items={state.items}
|
||||||
noItemsMessage={noItemsMessage}
|
noItemsMessage={noItemsMessage}
|
||||||
/>
|
/>
|
||||||
|
|||||||
@@ -22,9 +22,11 @@ export default function Item(props) {
|
|||||||
return item.text.split(regex)
|
return item.text.split(regex)
|
||||||
}, [splitChar, item])
|
}, [splitChar, item])
|
||||||
|
|
||||||
const divClassName = useMemo(() => {
|
const isHighlighted = () => highlighted && index === highlighted.index
|
||||||
|
|
||||||
|
const divClassName = () => {
|
||||||
let itemStyle = customStyles[
|
let itemStyle = customStyles[
|
||||||
(highlighted && index === highlighted.index)
|
(isHighlighted())
|
||||||
? 'highlightedItem'
|
? 'highlightedItem'
|
||||||
: 'item'
|
: 'item'
|
||||||
]
|
]
|
||||||
@@ -32,7 +34,7 @@ export default function Item(props) {
|
|||||||
return (index === 0 && customStyles.topItem)
|
return (index === 0 && customStyles.topItem)
|
||||||
? `${itemStyle} ${customStyles.topItem}`
|
? `${itemStyle} ${customStyles.topItem}`
|
||||||
: itemStyle
|
: itemStyle
|
||||||
}, [customStyles, highlighted, index])
|
}
|
||||||
|
|
||||||
const handleMouseEnter = () => {
|
const handleMouseEnter = () => {
|
||||||
dispatch(setHighlighted(index))
|
dispatch(setHighlighted(index))
|
||||||
@@ -63,10 +65,13 @@ export default function Item(props) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
className={divClassName}
|
className={divClassName()}
|
||||||
style={defaultStyles.item}
|
style={defaultStyles.item}
|
||||||
onMouseEnter={handleMouseEnter}
|
onMouseEnter={handleMouseEnter}
|
||||||
onMouseDown={handleClick}>
|
onMouseDown={handleClick}
|
||||||
|
role='option'
|
||||||
|
aria-selected={isHighlighted}
|
||||||
|
aria-label={item.text}>
|
||||||
{itemElement()}
|
{itemElement()}
|
||||||
</div>
|
</div>
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -5,13 +5,13 @@ import ItemFirst from './itemFirst'
|
|||||||
import Item from './item'
|
import Item from './item'
|
||||||
|
|
||||||
export default function Items(props) {
|
export default function Items(props) {
|
||||||
const { items, noItemsMessage } = props
|
const { id, items, noItemsMessage } = props
|
||||||
const { state } = useContext(StateContext)
|
const { state } = useContext(StateContext)
|
||||||
const { customStyles } = state
|
const { customStyles } = state
|
||||||
|
|
||||||
const itemElements = () => {
|
const itemElements = () => {
|
||||||
return (
|
return (
|
||||||
<div className={customStyles.dropdown} style={defaultStyles.dropdown}>
|
<div id={id} className={customStyles.dropdown} style={defaultStyles.dropdown}>
|
||||||
{items.map((item, index) =>
|
{items.map((item, index) =>
|
||||||
index === 0 || item.groupIndex !== items[index - 1].groupIndex ? (
|
index === 0 || item.groupIndex !== items[index - 1].groupIndex ? (
|
||||||
<ItemFirst
|
<ItemFirst
|
||||||
@@ -30,7 +30,7 @@ export default function Items(props) {
|
|||||||
|
|
||||||
const noItemsMsg = () => {
|
const noItemsMsg = () => {
|
||||||
return (
|
return (
|
||||||
<div className={customStyles.dropdown} style={defaultStyles.dropdown}>
|
<div id={id} className={customStyles.dropdown} style={defaultStyles.dropdown}>
|
||||||
<div className={customStyles.noItems}>{noItemsMessage}</div>
|
<div className={customStyles.noItems}>{noItemsMessage}</div>
|
||||||
</div>
|
</div>
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
const styles = {
|
const styles = {
|
||||||
queryContainer: {
|
queryContainer: {
|
||||||
|
display: 'inline-block',
|
||||||
position: 'relative'
|
position: 'relative'
|
||||||
},
|
},
|
||||||
query: {
|
query: {
|
||||||
@@ -13,8 +14,9 @@ const styles = {
|
|||||||
top: 0,
|
top: 0,
|
||||||
left: 0
|
left: 0
|
||||||
},
|
},
|
||||||
x: {
|
clearButton: {
|
||||||
position: 'absolute',
|
position: 'absolute',
|
||||||
|
display: 'inline-block',
|
||||||
zIndex: 2
|
zIndex: 2
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
import PropTypes from 'prop-types'
|
||||||
|
import { nanoid } from 'nanoid'
|
||||||
import { StateContextProvider } from './context/state'
|
import { StateContextProvider } from './context/state'
|
||||||
import isUndefined from './utils/isUndefined'
|
import isUndefined from './utils/isUndefined'
|
||||||
import Container from './components/container'
|
import Container from './components/container'
|
||||||
@@ -9,8 +10,12 @@ import Container from './components/container'
|
|||||||
// Set prop defaults before passing them on to components
|
// Set prop defaults before passing them on to components
|
||||||
const propDefaults = {
|
const propDefaults = {
|
||||||
autoFocus: false,
|
autoFocus: false,
|
||||||
|
clearButton: false,
|
||||||
|
clearButtonAriaLabel: 'Clear contents',
|
||||||
|
clearButtonText: '×',
|
||||||
debounceWait: 250,
|
debounceWait: 250,
|
||||||
defaultItemGroupsAreImmutable: true,
|
defaultItemGroupsAreImmutable: true,
|
||||||
|
id: nanoid(),
|
||||||
isDisabled: false,
|
isDisabled: false,
|
||||||
itemGroupsAreImmutable: true,
|
itemGroupsAreImmutable: true,
|
||||||
maxItems: 10,
|
maxItems: 10,
|
||||||
@@ -37,6 +42,9 @@ const msgOneOnly = `Both a "data" prop and an "itemGroups" prop were provided. P
|
|||||||
const requiredPropsAreMissing = (props) => isUndefined(props.data) && isUndefined(props.itemGroups)
|
const requiredPropsAreMissing = (props) => isUndefined(props.data) && isUndefined(props.itemGroups)
|
||||||
Turnstone.propTypes = {
|
Turnstone.propTypes = {
|
||||||
autoFocus: PropTypes.bool,
|
autoFocus: PropTypes.bool,
|
||||||
|
clearButton: PropTypes.bool,
|
||||||
|
clearButtonAriaLabel: PropTypes.string,
|
||||||
|
clearButtonText: PropTypes.string,
|
||||||
data: (props) => {
|
data: (props) => {
|
||||||
if(requiredPropsAreMissing(props)) return new Error(msgBothRequired)
|
if(requiredPropsAreMissing(props)) return new Error(msgBothRequired)
|
||||||
if(!isUndefined(props.data) && !isUndefined(props.itemGroups)) return new Error(msgOneOnly)
|
if(!isUndefined(props.data) && !isUndefined(props.itemGroups)) return new Error(msgOneOnly)
|
||||||
@@ -51,6 +59,7 @@ Turnstone.propTypes = {
|
|||||||
defaultItemGroups: PropTypes.array,
|
defaultItemGroups: PropTypes.array,
|
||||||
defaultItemGroupsAreImmutable: PropTypes.bool,
|
defaultItemGroupsAreImmutable: PropTypes.bool,
|
||||||
displayField: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
|
displayField: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
|
||||||
|
id: PropTypes.string,
|
||||||
itemGroups: (props) => {
|
itemGroups: (props) => {
|
||||||
if(requiredPropsAreMissing(props)) return new Error(msgBothRequired)
|
if(requiredPropsAreMissing(props)) return new Error(msgBothRequired)
|
||||||
if(!isUndefined(props.data) && !isUndefined(props.itemGroups)) return new Error(msgOneOnly)
|
if(!isUndefined(props.data) && !isUndefined(props.itemGroups)) return new Error(msgOneOnly)
|
||||||
|
|||||||
@@ -24,8 +24,16 @@ describe('Turnstone', () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
test('Turnstone component passes all props to Container component along with default props', () => {
|
test('Turnstone component passes all props to Container component along with default props', () => {
|
||||||
expect(component.root.children[0].children[0].props).toEqual({
|
const props = {...component.root.children[0].children[0].props}
|
||||||
|
|
||||||
|
// The id prop is randomly generated so must be excluded
|
||||||
|
delete props.id
|
||||||
|
|
||||||
|
expect(props).toEqual({
|
||||||
autoFocus: false,
|
autoFocus: false,
|
||||||
|
clearButton: false,
|
||||||
|
clearButtonAriaLabel: 'Clear contents',
|
||||||
|
clearButtonText: '×',
|
||||||
debounceWait: 250,
|
debounceWait: 250,
|
||||||
defaultItemGroupsAreImmutable: true,
|
defaultItemGroupsAreImmutable: true,
|
||||||
isDisabled: false,
|
isDisabled: false,
|
||||||
|
|||||||
Reference in New Issue
Block a user