Skip to content

Commit

Permalink
Add accessible autocomplete component
Browse files Browse the repository at this point in the history
- this is the code for the previous version of the component, removed in #1038
- does not use the git branch or code for multiple selections, as this is not needed
- otherwise unchanged and apparently functional, but some functionality here is not required and tests are failing
  • Loading branch information
andysellick committed Nov 26, 2021
1 parent b205c47 commit 556120f
Show file tree
Hide file tree
Showing 10 changed files with 385 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
/* eslint-env jquery */
/* global accessibleAutocomplete */
// = require accessible-autocomplete/dist/accessible-autocomplete.min.js

window.GOVUK = window.GOVUK || {}
window.GOVUK.Modules = window.GOVUK.Modules || {};

(function (Modules) {
'use strict'

Modules.AccessibleAutocomplete = function () {
var $selectElem

this.start = function ($element) {
$selectElem = $element.find('select')

var configOptions = {
selectElement: document.getElementById($selectElem.attr('id')),
showAllValues: true,
confirmOnBlur: true,
preserveNullOptions: true, // https://github.com/alphagov/accessible-autocomplete#null-options
defaultValue: ''
}

configOptions.onConfirm = this.onConfirm

new accessibleAutocomplete.enhanceSelectElement(configOptions) // eslint-disable-line no-new, new-cap
// attach the onConfirm function to data attr, to call it in finder-frontend when clearing facet tags
$selectElem.data('onconfirm', this.onConfirm)
}

this.onConfirm = function (label, value, removeDropDown) {
function escapeHTML (str) {
return new window.Option(str).innerHTML
}

if ($selectElem.data('track-category') !== undefined && $selectElem.data('track-action') !== undefined) {
track($selectElem.data('track-category'), $selectElem.data('track-action'), label, $selectElem.data('track-options'))
}
// This is to compensate for the fact that the accessible-autocomplete library will not
// update the hidden select if the onConfirm function is supplied
// https://github.com/alphagov/accessible-autocomplete/issues/322
if (typeof label !== 'undefined') {
if (typeof value === 'undefined') {
value = $selectElem.children('option').filter(function () { return $(this).html() === escapeHTML(label) }).val()
}

if (typeof value !== 'undefined') {
var $option = $selectElem.find('option[value=\'' + value + '\']')
// if removeDropDown we are clearing the selection from outside the component
var selectState = typeof removeDropDown === 'undefined'
$option.prop('selected', selectState)
$selectElem.change()
}

// used to clear the autocomplete when clicking on a facet tag in finder-frontend
// very brittle but menu visibility is determined by autocomplete after this function is called
// setting autocomplete val to '' causes menu to appear, we don't want that, this solves it
// ideally will rewrite autocomplete to have better hooks in future
if (removeDropDown) {
$selectElem.closest('.gem-c-accessible-autocomplete').addClass('gem-c-accessible-autocomplete--hide-menu')
setTimeout(function () {
$('.autocomplete__menu').remove() // this element is recreated every time the user starts typing
$selectElem.closest('.gem-c-accessible-autocomplete').removeClass('gem-c-accessible-autocomplete--hide-menu')
}, 100)
}
}
}

function track (category, action, label, options) {
if (window.GOVUK.analytics && window.GOVUK.analytics.trackEvent) {
options = options || {}
options.label = label

window.GOVUK.analytics.trackEvent(category, action, options)
}
}
}
})(window.GOVUK.Modules)
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ $govuk-new-link-styles: true;
@import "govuk/components/all";

// components
@import "components/accessible-autocomplete";
@import "components/accordion";
@import "components/action-link";
@import "components/attachment";
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
@import url(asset-path("accessible-autocomplete/dist/accessible-autocomplete.min.css"));

.gem-c-accessible-autocomplete {
.autocomplete__input {
z-index: 1;
}

.autocomplete__dropdown-arrow-down {
z-index: 0;
}

.autocomplete__option {
@include govuk-font(19);
}

.autocomplete__list .autocomplete__option {
padding: 5px 6px;

&:before {
position: relative;
top: 3px;
padding-top: 2px;
}
}
}

.gem-c-accessible-autocomplete--hide-menu {
.autocomplete__menu {
display: none;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<%
id ||= "autocomplete-#{SecureRandom.hex(4)}"
label ||= nil
data_attributes ||= nil
options ||= []
selected_option ||= nil

classes = %w(gem-c-accessible-autocomplete govuk-form-group)
%>
<% if label && options.any? %>
<%= tag.div class: classes, data: { module: "accessible-autocomplete" } do %>
<%=
render "govuk_publishing_components/components/label", {
html_for: id
}.merge(label.symbolize_keys)
%>

<%=
select_tag(
id,
options_for_select(options, selected_option),
class: "govuk-select",
data: data_attributes
)
%>
<% end %>
<% end %>
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
name: Accessible autocomplete
description: An autocomplete component, built to be accessible.
body: |
This component uses the [Accessible Autocomplete](https://github.com/alphagov/accessible-autocomplete) code to create an accessible autocomplete element. The autocomplete is created with the `showAllValues`
option set to `true` and the `confirmOnBlur` option set to `false` (see [Autocomplete examples](https://alphagov.github.io/accessible-autocomplete/examples) here). It also depends upon the
[label component](https://github.com/component-guide/label).
If Javascript is disabled, the component appears as a select box, so the user can still select an option.
accessibility_criteria: |
[Accessibility acceptance criteria](https://github.com/alphagov/accessible-autocomplete/blob/master/accessibility-criteria.md)
examples:
default:
data:
label:
text: 'Countries'
options: [['', ''], ['France', 'fr'], ['Germany', 'de'], ['Sweden', 'se'], ['Switzerland', 'ch'], ['United Kingdom', 'gb'], ['United States', 'us'], ['The Separate Customs Territory of Taiwan, Penghu, Kinmen, and Matsu (Chinese Taipei)', 'tw']]
with_unique_identifier:
data:
id: 'unique-autocomplete'
label:
text: 'Countries'
options: [['', ''], ['France', 'fr'], ['Germany', 'de'], ['Sweden', 'se'], ['Switzerland', 'ch'], ['United Kingdom', 'gb'], ['United States', 'us']]
with_selected_option_chosen:
data:
id: 'selected-option-chosen-autocomplete'
label:
text: 'Countries'
options: [['', ''], ['France', 'fr'], ['Germany', 'de'], ['Sweden', 'se'], ['Switzerland', 'ch'], ['United Kingdom', 'gb'], ['United States', 'us']]
selected_option: ['United Kingdom', 'gb']
with_tracking_enabled:
description: |
This example shows tracking enabled on an autocomplete. Tracking will be enabled automatically when `track_category` and `track_action` are specified in `data_attributes`.
data:
id: 'tracking-enabled-autocomplete'
label:
text: 'Countries'
options: [['', ''], ['France', 'fr'], ['Germany', 'de'], ['Sweden', 'se'], ['Switzerland', 'ch'], ['United Kingdom', 'gb'], ['United States', 'us']]
data_attributes:
track_category: 'chosen_category'
track_action: 'chosen_action'
track_option:
custom_dimension: 'your_custom_dimension'
1 change: 1 addition & 0 deletions config/initializers/assets.rb
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@

# GOV.UK Frontend assets
Rails.application.config.assets.precompile += %w[
accessible-autocomplete/dist/accessible-autocomplete.min.css
govuk-logotype-crown.png
favicon.ico
govuk-opengraph-image.png
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
"extends": "stylelint-config-gds/scss"
},
"dependencies": {
"accessible-autocomplete": "git://github.com/alphagov/accessible-autocomplete.git",
"axe-core": "^3.5.4",
"govuk-frontend": "^3.14.0",
"jquery": "1.12.4",
Expand Down
66 changes: 66 additions & 0 deletions spec/components/accessible_autocomplete_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
require 'rails_helper'

describe "AccessibleAutocomplete", type: :view do
def component_name
"accessible_autocomplete"
end

it 'renders select element' do
render_component(
id: 'basic-autocomplete',
label: { text: "Countries" },
options: [['United Kingdom', 'gb'], ['United States', 'us']]
)

assert_select ".govuk-label", text: "Countries", for: "basic-autocomplete"
assert_select "select#basic-autocomplete"
assert_select "select[multiple]", false
assert_select "select#basic-autocomplete option[value=gb]"
assert_select "select#basic-autocomplete option[value=gb]", text: 'United Kingdom'
assert_select "select#basic-autocomplete option[value=us]"
assert_select "select#basic-autocomplete option[value=us]", text: 'United States'
end

it 'renders select element with selected value' do
render_component(
id: 'basic-autocomplete',
label: { text: "Countries" },
options: [['United Kingdom', 'gb'], ['United States', 'us']],
selected_option: ['United States', 'us']
)

assert_select ".govuk-label", text: "Countries", for: "basic-autocomplete"
assert_select "select#basic-autocomplete"
assert_select "select#basic-autocomplete option[value=gb]"
assert_select "select#basic-autocomplete option[value=us][selected]"
end

it 'does not render when no data is specified' do
assert_empty render_component({})
end

it 'does not render when no label is specified' do
assert_empty render_component(
id: 'basic-autocomplete',
options: [['United Kingdom', 'gb'], ['United States', 'us']]
)
end

it 'does not render when no options are specified' do
assert_empty render_component(
id: 'basic-autocomplete',
label: { text: "Countries" }
)
end

it 'renders the multiple selection version correctly' do
render_component(
multiple: true,
label: { text: "Countries" },
options: [['United Kingdom', 'gb'], ['United States', 'us']]
)

assert_select "select[multiple]"
assert_select ".gem-c-autocomplete__multiselect-instructions"
end
end
Loading

0 comments on commit 556120f

Please sign in to comment.