alphagov / accessible-autocomplete Goto Github PK
View Code? Open in Web Editor NEWAn autocomplete component, built to be accessible.
Home Page: https://alphagov.github.io/accessible-autocomplete/examples/
License: MIT License
An autocomplete component, built to be accessible.
Home Page: https://alphagov.github.io/accessible-autocomplete/examples/
License: MIT License
Hello,
This plugin looks really good, so is there a plan for 1.0.0?
What needs to be done to remove this ⚠️ WARNING: This project is still experimental / under development. Do not use in production. ⚠️
warning?
Thank you!
The current examples page does not make use of actual <form>
elements and doesn't illustrate this interaction, which makes testing stuff like submitting forms (using the enter key) after confirming an option (also using the enter key) difficult.
As users select different menu options using the arrow keys, the input should visually update with the selection. Right now it sort-of does, as the hint updates as you go down.
Acceptance criteria:
It's possible to have two items visibly selected - only one should be selected at any one time.
Steps to reproduce:
A possible different solution to this might be to style 'hover-selected' items differently than the 'actually-selected' items.
Things to do:
aria-live
regionPossibly others.
Possible API:
AccessibleTypeahead.enhanceSelectElement({
selectElement: document.querySelector('select'),
lang: 'en' // Implicit default
})
AccessibleTypeahead.enhanceSelectElement({
selectElement: document.querySelector('select'),
lang: 'cy' // templates: AccessibleTypeahead.welshStrings
})
AccessibleTypeahead.enhanceSelectElement({
selectElement: document.querySelector('select'),
templates: {
notFound: 'Nu s-a gasit'
}
})
Immediately after v1.0.0 I think it would be good to switch to semantic-release.
CI already outputs coverage reports so all we need for this is a Travis plugin and an API key for something like coveralls.io.
While we haven't observed users getting confused over the current behaviour (reach end -> stop), Adem recommends this here: https://twitter.com/paulmsmith/status/860047704885526528
Doing this correctly would require changing from .focus()
to a wholly aria-activedescendant
implementation, as detailed in #76.
Timer mocks would be useful for fixing some of our tests.
Should be combined with #54?
While I don't believe we've seen anyone attempt this in research, the space bar is commonly used by keyboard users to confirm things. There shouldn't be a downside to adding support for this.
It seems like the community is moving away from .jsx
with popular frameworks using the .js
extension.
When using the autoselect
option, when the user types in a query that brings up suggestions, the list of suggestions will update and visually highlight the first element, while offering audio feedback informing the user that it's selected. The user may press enter
to confirm it.
I've tested this on JAWS17 and the typeahead does not give clear enough feedback after confirming that the user has successfully chosen the first option. Other screen reader + browser combinations accomplish this usually by simply reading out the new value; JAWS17 just says "enter," and on FireFox it also says "collapsed."
Browser | JAWS17 |
---|---|
Chrome | Broken |
FireFox | Broken |
IE11 | Broken |
A possible solution is to blur and refocus the input field but a bit of investigation and testing is needed to fix this.
The typeahead contains a <Hint>
element that is responsible for displaying the grey text in this image:
I've done some accessibility testing and on JAWS17 Chrome, and NVDA Chrome/FireFox/IE11, it is possible to sometimes tab to the hint input element (even though it has tabindex="-1"
!), in which case the user will be told it's "read-only edit" and not be allowed to edit it. This only seems to occur when the screen readers are running.
There's a few solutions to try but one would be to simply not display the <Hint>
unless it's in use.
Follow up on #1 and finish it.
This project doesn't have a lot of dependencies but it would be good to use GK.
If the autocomplete code is added to a page:
selectElement: document.querySelector('#location-picker')
})
But no #location-picker
is present, it produces an error. It should do nothing if it finds the element isn't on the page.
At the moment the input is styled in a way that it'll only work if GOV.UK's base styles are in place, if you bump the font the input looks too small.
.typeahead__wrapper {
position: relative;
}
.typeahead__hint,
.typeahead__input {
-webkit-appearance: none;
border: 2px solid;
border-width: .125rem;
border-radius: 0; /* Safari 10 on iOS adds implicit border rounding. */
box-sizing: border-box;
-moz-box-sizing: border-box;
-webkit-box-sizing: border-box;
margin-bottom: 0; /* BUG: Safari 10 on macOS seems to add an implicit margin. */
width: 100%;
}
.typeahead__input {
background-color: transparent;
position: relative;
}
.typeahead__hint {
color: #BFC1C3;
position: absolute;
}
.typeahead__input:focus {
outline-offset: 0;
outline: 3px solid #ffbf47;
outline-width: .1875rem;
}
.typeahead__menu {
background-color: #fff;
border: 2px solid #0B0C0C;
border-width: .125rem;
border-top: 0;
color: #34384B;
margin: 0;
max-height: 342px;
max-height: 21.375rem;
overflow-x: hidden;
padding: 0;
width: 100%;
width: calc(100% - 4px);
width: calc(100% - .25rem);
}
.typeahead__menu--visible {
display: block;
}
.typeahead__menu--hidden {
display: none;
}
.typeahead__menu--overlay {
box-shadow: rgba(0, 0, 0, 0.256863) 0 .125rem .375rem;
left: 0;
position: absolute;
top: 100%;
z-index: 100;
}
.typeahead__menu--inline {
position: relative;
}
.typeahead__option {
border-bottom: solid #BFC1C3;
border-width: 1px 0;
border-width: .0625rem 0;
cursor: pointer;
display: block;
position: relative;
}
.typeahead__option:first-of-type {
border-top-width: 0;
}
.typeahead__option:last-of-type {
border-bottom-width: 0;
}
.typeahead__option--odd {
background-color: #FAFAFA;
}
.typeahead__option--focused {
background-color: #005EA5;
border-color: #005EA5;
color: white;
outline: none;
}
.typeahead__option--no-results {
background-color: #FAFAFA;
color: #646b6f;
cursor: not-allowed;
}
.typeahead__hint,
.typeahead__input,
.typeahead__option {
font-size: 16px;
font-size: 1rem;
line-height: 1.25;
padding: 4px;
padding: .25rem;
}
@media (min-width: 641px) {
.typeahead__hint,
.typeahead__input,
.typeahead__option {
font-size: 19px;
font-size: 1.1875rem;
line-height: 1.31579;
}
}
Add this:
.typeahead__menu--inline {
max-height: none;
overflow-x: visible;
}
This allows you to more easily import it in services that use the frontend toolkit.
Make it possible to pass an argument to the AccessibleTypeahead
function to set the required
attribute on the typeahead input field. This is useful if the need involves free text submission.
Criterion 8 currently says:
"Inform the user that N number of matches have been displayed"
I wonder if this should be:
"Inform the user when there are matches, or if there are no matches"
With another:
"(Optional) inform the user the number of matches"
I also wonder if criterion 9 should be made optional.
Reasoning: for sighted users, we don't display the number of matches - what we do indicate is whether there are matches. Is it crucial that a screen reader user is told whether there are 3 or 5 matches? or is the essential thing that they be told when there are results and when there aren't?
On iOS, when you confirm an option with VoiceOver turned on, the typeahead will select the text inside the input, which will bring up the selection edit menu (copy / paste / and so on). VoiceOver will then stop telling you that you have successfully confirmed an option to tell you what's in the selection edit menu, so it just says "menu item."
Might be good to have a bottom shadow if the menu is scrollable. The challenge would be that the shadow shouldn't appear when you're scrolled to the bottom.
There aren't any tests that check unicode strings, so we don't know if the autocomplete works with them.
When users access the "MouseGrid" feature from Dragon, it triggers a blur
event on the input that will close the list of suggestions.
When autoselect is on, an option should always be selected. This will either be the first result, or if the user has used arrow keys it may be another result. Currently using arrow keys it's possible to unselect all options.
Steps to reproduce:
(This bug would be easy to demonstrate with something like #42)
If you have a typeahead with a displayMenu: 'inline'
list of options open, then when you click on a different element in the page, these events happen: mouseDown -> blur -> mouseUp
.
By default, click events don't get registered until mouseUp
, to allow users to change their mind and drag the cursor away before letting go of the click. However, because the blur
event gets triggered before, this will collapse the typeahead menu, which will move elements beneath it in the page upwards. This "pulls the rug" underneath the mouse, and the click event won't register on the clicked element.
We shouldn't encourage the use of the placeholder attribute. Here's some details:
https://govuk-elements.herokuapp.com/form-elements/#form-hint-text
And some more details as to why:
GOV.UK Verify are currently using https://github.com/JamieAppleseed/selectToAutocomplete in an alpha product. This is a jQuery plugin that takes a select
tag as input and auto-magically transforms it into a typeahead.
The main advantage of this approach is that it makes the no-javascript fallback much easier to implement - you simply stamp out your select
and option
tags, and if the JS fails to run that's Good Enough(TM).
Of course it would still be possible to put a select
in a noscript
tag (or similar) to provide a no-javascript fallback while using accesible-typeahead
, but the "provide a select and the plugin does the rest" is a nice workflow.
If you think that would be a nice feature I'd be happy to have a play and send you a PR. What do you think?
We don't recommend users to rely exclusively on unpkg
in their service. They should use package managers or vendor the dependencies.
<label for="medical-condition-input">What is your medical condition?</label>
<input id="medical-condition-input" type="text">
AccessibleTypehead({
element: document.querySelector('#medical-condition-input'),
source: suggest
})
I wonder if there's a way we can make the deep tertiaries easy to understand the flow.
Maybe a switch statement outside of the return statement?
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/status.jsx#L55
We recently decided to refer to this as an autocomplete rather than a typeahead. Autocomplete felt more natural and appears to be in more common usage (comparing similar components and search terms).
To do:
The current examples only define 3 countries. Having at least one example with lots of countries would help with testing scrolling behaviours.
Not sure if this is a good idea, but when I use keyboard input on a select input, then press down on the keyboard, it'll open the select and let me go through them.
Webpack 2 is stable now. This project has a similar structure and is using it: https://github.com/alphagov/openregister-picker-engine
accessibleTypeahead
is not meant to be a constructor for a class, it shouldn't be capitalised.
Here's the problem:
#6 is the problem: when the user hides the on-screen keyboard, the blur
event fires on the textbox, in iOS 10. I don't believe any other device does this including earlier versions of iOS.
I wonder if we can fix this by the approach we take to building this component.
Currently, the Javascript listens for the text box blur
event and hides the suggestion list.
Here's a very early thought of mine...
Don't hide the suggestions on blur
. Instead hide the suggestions when the user presses the tab key.
But what about clicking/tapping elsewhere on the page? In this case we should also hide the suggestions.
@tvararu raised concerns with listening to events that are outside of the components segment of the Document Tree.
I don't share this concern. This is the nature of developing Javascript components in the browser. It might also be that a component listens to load
/scroll
/resize
events at the window
/document
/body
level, for example.
As long as a component does not stop propagation/bubbling then this is, in my book, absolutely no problem.
Raising this here to open up the discussion. Critique welcomed.
Right now the tests are a bit hairy compared with what can be done in the React world, spoke to @tvararu and we think it'd be interesting to have this project as React by default, and then allow Preact to be swapped in at prod build time.
Risks with this is we need to ensure test coverage across a React build and Preact build...
When scanning the repo, there's a few variables that take a little bit to figure out what they do because of their names:
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/typeahead.jsx#L4
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/typeahead.jsx#L333
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/typeahead.jsx#L228
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/typeahead.jsx#L184
Here are a few:
<script src="preact.js"></script>
<script src="lodash.debounce.js"></script>
<!-- Standalone build without all the dependencies. -->
<script src="accessible-typeahead.standalone.min.js"></script>
<script>
AccessibleTypeahead()
</script>
// In package.json
{
"dependencies": {
"lodash.debounce": "*",
"preact": "*",
// ...
}
}
// Then maybe?
import AccessibleTypeahead from 'accessible-typeahead/standalone'
AccessibleTypeahead()
import {h} from 'preact' /** @jsx h */
import AccessibleTypeahead from 'accessible-typeahead/preact'
<AccessibleTypeahead />
import React from 'react'
import AccessibleTypeahead from 'accessible-typeahead/react'
<AccessibleTypeahead />
Currently the component uses both .focus()
and aria-activedescendant
to announce the focused option.
According to spec a composite widget like this, should keep focus on the textbox and focus should be managed by aria-attributes (and CSS for visual highlighting), which is what I have done in my demo.
It would be good to investigate how well this works for AT.
I did some light testing previously where it seemed like this property was not being used by assistive technologies in any perceivable way, but there's a lingering question if we should add it anyway.
I suppose you could argue that you only should expose things that can be themed so this may be fine?
https://github.com/alphagov/accessible-typeahead/blob/enhance-select-element/src/status.jsx#L42
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.