govuk_publishing_components 43.3.0 → 43.4.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/images/govuk_publishing_components/icon-autocomplete-search-suggestion.svg +4 -0
  3. data/app/assets/javascripts/govuk_publishing_components/components/search-with-autocomplete.js +123 -0
  4. data/app/assets/stylesheets/govuk_publishing_components/components/_layout-super-navigation-header.scss +5 -4
  5. data/app/assets/stylesheets/govuk_publishing_components/components/_phase-banner.scss +0 -2
  6. data/app/assets/stylesheets/govuk_publishing_components/components/_search-with-autocomplete.scss +200 -0
  7. data/app/views/govuk_publishing_components/components/_layout_header.html.erb +16 -40
  8. data/app/views/govuk_publishing_components/components/_search.html.erb +16 -14
  9. data/app/views/govuk_publishing_components/components/_search_with_autocomplete.html.erb +27 -0
  10. data/app/views/govuk_publishing_components/components/docs/layout_header.yml +0 -41
  11. data/app/views/govuk_publishing_components/components/docs/phase_banner.yml +4 -0
  12. data/app/views/govuk_publishing_components/components/docs/search_with_autocomplete.yml +61 -0
  13. data/lib/govuk_publishing_components/version.rb +1 -1
  14. data/node_modules/accessible-autocomplete/CHANGELOG.md +390 -0
  15. data/node_modules/accessible-autocomplete/CODEOWNERS +2 -0
  16. data/node_modules/accessible-autocomplete/CONTRIBUTING.md +161 -0
  17. data/node_modules/accessible-autocomplete/LICENSE.txt +20 -0
  18. data/node_modules/accessible-autocomplete/Procfile +1 -0
  19. data/node_modules/accessible-autocomplete/README.md +490 -0
  20. data/node_modules/accessible-autocomplete/accessibility-criteria.md +42 -0
  21. data/node_modules/accessible-autocomplete/app.json +15 -0
  22. data/node_modules/accessible-autocomplete/babel.config.js +29 -0
  23. data/node_modules/accessible-autocomplete/dist/accessible-autocomplete.min.css +3 -0
  24. data/node_modules/accessible-autocomplete/dist/accessible-autocomplete.min.css.map +1 -0
  25. data/node_modules/accessible-autocomplete/dist/accessible-autocomplete.min.js +2 -0
  26. data/node_modules/accessible-autocomplete/dist/accessible-autocomplete.min.js.map +1 -0
  27. data/node_modules/accessible-autocomplete/dist/lib/accessible-autocomplete.preact.min.js +2 -0
  28. data/node_modules/accessible-autocomplete/dist/lib/accessible-autocomplete.preact.min.js.map +1 -0
  29. data/node_modules/accessible-autocomplete/dist/lib/accessible-autocomplete.react.min.js +2 -0
  30. data/node_modules/accessible-autocomplete/dist/lib/accessible-autocomplete.react.min.js.map +1 -0
  31. data/node_modules/accessible-autocomplete/examples/form-single.html +379 -0
  32. data/node_modules/accessible-autocomplete/examples/form.html +673 -0
  33. data/node_modules/accessible-autocomplete/examples/index.html +738 -0
  34. data/node_modules/accessible-autocomplete/examples/preact/index.html +346 -0
  35. data/node_modules/accessible-autocomplete/examples/react/index.html +347 -0
  36. data/node_modules/accessible-autocomplete/package.json +93 -0
  37. data/node_modules/accessible-autocomplete/postcss.config.js +16 -0
  38. data/node_modules/accessible-autocomplete/preact.js +1 -0
  39. data/node_modules/accessible-autocomplete/react.js +1 -0
  40. data/node_modules/accessible-autocomplete/scripts/check-staged.mjs +16 -0
  41. data/node_modules/accessible-autocomplete/src/autocomplete.css +167 -0
  42. data/node_modules/accessible-autocomplete/src/autocomplete.js +608 -0
  43. data/node_modules/accessible-autocomplete/src/dropdown-arrow-down.js +11 -0
  44. data/node_modules/accessible-autocomplete/src/status.js +125 -0
  45. data/node_modules/accessible-autocomplete/src/wrapper.js +60 -0
  46. data/node_modules/accessible-autocomplete/test/functional/dropdown-arrow-down.js +46 -0
  47. data/node_modules/accessible-autocomplete/test/functional/index.js +793 -0
  48. data/node_modules/accessible-autocomplete/test/functional/wrapper.js +339 -0
  49. data/node_modules/accessible-autocomplete/test/integration/index.js +309 -0
  50. data/node_modules/accessible-autocomplete/test/karma.config.js +46 -0
  51. data/node_modules/accessible-autocomplete/test/wdio.config.js +123 -0
  52. data/node_modules/accessible-autocomplete/webpack.config.mjs +244 -0
  53. metadata +46 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e7369ec3598e82bdea2bd09f8afddd660fb7993009b0eea7fc8ca9b4a3c9cc52
4
- data.tar.gz: 0343c704ff03e4e030ac919e2e3e21168955d15863087d394f633e4afe7e26a2
3
+ metadata.gz: ac704d6393454fd55a51395e672359ee86f2fbd731c4570bf8052f9444e14d73
4
+ data.tar.gz: ff7cfc46ec1fb8663116a6926bcd4323d87d8a20ba004f0683bcecabaa18488f
5
5
  SHA512:
6
- metadata.gz: 3a45ed3d3cfb9876c887cb3a44136620867ced84f5fa843de75396d003db13c04a0fa6aacc734bfa63ad29a209690d291f0129faefe2d87f84d9aa43a0b63a9a
7
- data.tar.gz: 8a9bb44e81fd88a14926e9fefe075384ac937fd6174fc6429e641b2ff7c9cf1521228b7c22fbd2eb19228eede4e8fe9b64f9b64cec5dbdbc1b067b15a48d4915
6
+ metadata.gz: bed10adab8a2ed2a3b571ee8b0290fc7380a2725aee1a04fe905d7799d46142455e14c7b4f7152a8bb3f6d521a273aa7de36f648036e89f20e302e0cd3093f38
7
+ data.tar.gz: 7dbcd83b8b7443f2906fb4bbfd9c8abe26a234d9bd3acd2c6d986625264f5bffcdf4d6ccadc9ed1c099e0f886863bfd3676ba562dee4b116139bc4ab37b3d7cf
@@ -0,0 +1,4 @@
1
+ <svg width="20" height="40" viewBox="0 -10 20 40" fill="none" xmlns="http://www.w3.org/2000/svg">
2
+ <path d="M8.902 14.4681C12.3859 14.4681 15.2102 11.6438 15.2102 8.15981C15.2102 4.67586 12.3859 1.85156 8.902 1.85156C5.41805 1.85156 2.59375 4.67586 2.59375 8.15981C2.59375 11.6438 5.41805 14.4681 8.902 14.4681Z" stroke="#505a5f" stroke-width="2"/>
3
+ <path d="M13.2344 12.8584L19.5904 19.2144" stroke="#505a5f" stroke-width="2"/>
4
+ </svg>
@@ -0,0 +1,123 @@
1
+ /* global accessibleAutocomplete, fetch */
2
+ //= require accessible-autocomplete/dist/accessible-autocomplete.min.js
3
+
4
+ window.GOVUK = window.GOVUK || {}
5
+ window.GOVUK.Modules = window.GOVUK.Modules || {};
6
+
7
+ (function (Modules) {
8
+ class GemSearchWithAutocomplete {
9
+ constructor ($module) {
10
+ this.$module = $module
11
+
12
+ this.$originalInput = this.$module.querySelector('input')
13
+ this.$inputWrapper = this.$module.querySelector('.js-search-input-wrapper')
14
+ this.$form = this.$module.closest('form')
15
+
16
+ this.sourceUrl = this.$module.getAttribute('data-source-url')
17
+ this.sourceKey = this.$module.getAttribute('data-source-key')
18
+ }
19
+
20
+ init () {
21
+ const configOptions = {
22
+ element: this.$inputWrapper,
23
+ id: this.$originalInput.id,
24
+ name: this.$originalInput.name,
25
+ inputClasses: this.$originalInput.classList,
26
+ defaultValue: this.$originalInput.value,
27
+ cssNamespace: 'gem-c-search-with-autocomplete',
28
+ confirmOnBlur: false,
29
+ showNoOptionsFound: false,
30
+ source: this.getResults.bind(this),
31
+ onConfirm: this.submitContainingForm.bind(this),
32
+ templates: {
33
+ suggestion: this.constructSuggestionHTMLString.bind(this)
34
+ },
35
+ tStatusNoResults: () => 'No search suggestions found',
36
+ tStatusQueryTooShort: (minQueryLength) => `Type in ${minQueryLength} or more characters for search suggestions`,
37
+ tStatusResults: (length, contentSelectedOption) => {
38
+ const words = {
39
+ result: (length === 1) ? 'search suggestion' : 'search suggestions',
40
+ is: (length === 1) ? 'is' : 'are'
41
+ }
42
+
43
+ return `${length} ${words.result} ${words.is} available. ${contentSelectedOption}`
44
+ },
45
+ tAssistiveHint: () => 'When search suggestions are available use up and down arrows to review and enter to select. Touch device users, explore by touch or with swipe gestures.'
46
+ }
47
+ accessibleAutocomplete(configOptions)
48
+
49
+ // The accessible-autocomplete component is meant to generate a new input element rather than enhancing an existing one, so we need to do some cleanup here.
50
+ this.$autocompleteInput = this.$inputWrapper.querySelector(
51
+ '.gem-c-search-with-autocomplete__input'
52
+ )
53
+ // Ensure the new input element generated by accessible-autocomplete has the correct type
54
+ this.$autocompleteInput.setAttribute('type', 'search')
55
+ // Remove the original input from the DOM
56
+ this.$originalInput.parentNode.removeChild(this.$originalInput)
57
+ }
58
+
59
+ // Callback used by accessible-autocomplete to generate the HTML for each suggestion based on
60
+ // the values returned from the source
61
+ constructSuggestionHTMLString (result) {
62
+ const sanitizedResult = this.sanitizeResult(result)
63
+ const inputValue = this.$inputWrapper.querySelector('input').value.toLowerCase()
64
+
65
+ const index = sanitizedResult.toLowerCase().indexOf(inputValue)
66
+
67
+ let html = sanitizedResult
68
+ if (index !== -1) {
69
+ const before = sanitizedResult.slice(0, index)
70
+ const match = sanitizedResult.slice(index, index + inputValue.length)
71
+ const after = sanitizedResult.slice(index + inputValue.length)
72
+
73
+ html = `${before}<mark class="gem-c-search-with-autocomplete__suggestion-highlight">${match}</mark>${after}`
74
+ }
75
+
76
+ return `
77
+ <div class="gem-c-search-with-autocomplete__option-wrapper">
78
+ <span class="gem-c-search-with-autocomplete__suggestion-icon"></span>
79
+ <span class="gem-c-search-with-autocomplete__suggestion-text">${html}</span>
80
+ </div>
81
+ `
82
+ }
83
+
84
+ // Callback used by accessible-autocomplete to fetch results from the source
85
+ getResults (query, populateResults) {
86
+ const url = new URL(this.sourceUrl)
87
+ url.searchParams.set('q', query)
88
+ fetch(url, { headers: { Accept: 'application/json' } })
89
+ .then(response => response.json())
90
+ .then((data) => { populateResults(data[this.sourceKey]) })
91
+ .catch(() => { populateResults([]) })
92
+ }
93
+
94
+ // Callback used by accessible-autocomplete to submit the containing form when a suggestion is
95
+ // confirmed by the user (e.g. by pressing Enter or clicking on it)
96
+ submitContainingForm (value) {
97
+ if (this.$form) {
98
+ // The accessible-autocomplete component calls this callback _before_ it updates its
99
+ // internal state, so the value of the input field is not yet updated when this callback is
100
+ // called. We need to force the value to be updated before submitting the form, but the rest
101
+ // of the state can catch up later.
102
+ this.$autocompleteInput.value = value
103
+
104
+ if (this.$form.requestSubmit) {
105
+ this.$form.requestSubmit()
106
+ } else {
107
+ // Fallback for certain Grade C browsers that don't support `requestSubmit`
108
+ this.$form.submit()
109
+ }
110
+ }
111
+ }
112
+
113
+ // Sanitises a result coming back from the source to prevent XSS issues if the result happens to
114
+ // contain HTML.
115
+ sanitizeResult (value) {
116
+ const scratch = document.createElement('div')
117
+ scratch.textContent = value
118
+ return scratch.innerHTML
119
+ }
120
+ }
121
+
122
+ Modules.GemSearchWithAutocomplete = GemSearchWithAutocomplete
123
+ })(window.GOVUK.Modules)
@@ -608,10 +608,6 @@ $after-button-padding-left: govuk-spacing(4);
608
608
  // Styles for search toggle button.
609
609
  .gem-c-layout-super-navigation-header__search-toggle-button {
610
610
  background: none;
611
-
612
- &.gem-c-layout-super-navigation-header__search-toggle-button--blue-background {
613
- background: $govuk-brand-colour;
614
- }
615
611
  border: 0;
616
612
  color: govuk-colour("white");
617
613
  cursor: pointer;
@@ -619,6 +615,11 @@ $after-button-padding-left: govuk-spacing(4);
619
615
  padding: govuk-spacing(3);
620
616
  position: relative;
621
617
  width: $search-width-or-height;
618
+
619
+ &.gem-c-layout-super-navigation-header__search-toggle-button--blue-background {
620
+ background: $govuk-brand-colour;
621
+ }
622
+
622
623
  @include govuk-font($size: 19, $weight: "bold", $line-height: 20px);
623
624
 
624
625
  @include focus-and-focus-visible {
@@ -9,8 +9,6 @@
9
9
  }
10
10
 
11
11
  .gem-c-phase-banner--inverse {
12
- background: $govuk-brand-colour;
13
-
14
12
  .govuk-phase-banner__content__tag {
15
13
  background: govuk-colour("white");
16
14
  color: $govuk-brand-colour;
@@ -0,0 +1,200 @@
1
+ @import "govuk_publishing_components/individual_component_support";
2
+
3
+ // These styles are adapted from the original Accessible Autocomplete component stylesheet, mostly
4
+ // to remove superfluous styles that are already provided by the GOV.UK Design System, and to adapt
5
+ // the styling to match the new GOV.UK search box designs (e.g. to remove the zebra striping on
6
+ // rows, adjust whitespace, and manage the tweaked markup we use in the suggestion template).
7
+ //
8
+ // Note that most selectors targetted within this file are those constructed by the Accessible
9
+ // Autocomplete component, so they may not 100% match our own component conventions.
10
+ //
11
+ // see https://github.com/alphagov/accessible-autocomplete/blob/main/src/autocomplete.css
12
+
13
+ // Helps to make the autocomplete menu as wide as the entire search box _including_ the submit
14
+ // button, not just the width of the input field.
15
+ @mixin enhance-autocomplete-menu-width($button-size) {
16
+ margin-right: -$button-size;
17
+ }
18
+
19
+ $input-size: 40px;
20
+ $large-input-size: 50px;
21
+
22
+ .gem-c-search-with-autocomplete__wrapper {
23
+ position: relative;
24
+ }
25
+
26
+ .gem-c-search-with-autocomplete__menu {
27
+ margin: 0;
28
+ padding: 0;
29
+ overflow-x: hidden;
30
+ background-color: govuk-colour("white");
31
+ border: 1px solid $govuk-border-colour;
32
+ border-top: 0;
33
+
34
+ @include enhance-autocomplete-menu-width($input-size);
35
+ }
36
+
37
+ .gem-c-search-with-autocomplete__menu--visible {
38
+ display: block;
39
+ }
40
+
41
+ .gem-c-search-with-autocomplete__menu--hidden {
42
+ display: none;
43
+ }
44
+
45
+ .gem-c-search-with-autocomplete__menu--inline {
46
+ position: relative;
47
+ }
48
+
49
+ .gem-c-search-with-autocomplete__option {
50
+ display: block;
51
+ cursor: pointer;
52
+
53
+ @include govuk-font(19);
54
+
55
+ // Ensure only the option itself receives pointer events
56
+ & > * {
57
+ pointer-events: none;
58
+ }
59
+
60
+ // Accessible Autocomplete's iOS screenreader inset has broken CSS which hasn't been fixed
61
+ // upstream, and means that its text is not just visible to screenreader users, but displayed
62
+ // for everyone. This span is added dynamically only on iOS and not given a class, so we need to
63
+ // target it in a roundabout way and make it invisible to non-screenreader users.
64
+ & > span {
65
+ clip: rect(0 0 0 0);
66
+ clip-path: inset(50%);
67
+ height: 1px;
68
+ overflow: hidden;
69
+ position: absolute;
70
+ white-space: nowrap;
71
+ width: 1px;
72
+ }
73
+ }
74
+
75
+ // Common styling for _all_ focus states, including keyboard focus, mouse hover, and keyboard focus
76
+ // but mouse on another option.
77
+ .gem-c-search-with-autocomplete__option--focused,
78
+ .gem-c-search-with-autocomplete__option:hover,
79
+ .gem-c-search-with-autocomplete__option:focus-visible {
80
+ background-color: govuk-colour("light-grey");
81
+ outline: none;
82
+
83
+ @include govuk-link-decoration;
84
+ @include govuk-link-hover-decoration;
85
+
86
+ .gem-c-search-with-autocomplete__suggestion-icon {
87
+ background-color: $govuk-text-colour;
88
+ }
89
+ }
90
+
91
+ // Styling specifically _only_ for keyboard focus
92
+ .gem-c-search-with-autocomplete__option:focus-visible {
93
+ .gem-c-search-with-autocomplete__suggestion-text {
94
+ background-color: $govuk-focus-colour;
95
+ }
96
+ }
97
+
98
+ .gem-c-search-with-autocomplete__option-wrapper {
99
+ display: flex;
100
+ align-items: center;
101
+ margin: 0 govuk-spacing(3);
102
+ padding: govuk-spacing(1) 0;
103
+ border-bottom: 1px solid govuk-colour("mid-grey");
104
+ }
105
+
106
+ .gem-c-search-with-autocomplete__option:last-child .gem-c-search-with-autocomplete__option-wrapper {
107
+ border-bottom: 0;
108
+ }
109
+
110
+ .gem-c-search-with-autocomplete__suggestion-icon {
111
+ width: calc($input-size / 2);
112
+ height: $input-size;
113
+ margin-right: govuk-spacing(2);
114
+ flex: none;
115
+ mask-image: url("govuk_publishing_components/icon-autocomplete-search-suggestion.svg");
116
+ -webkit-mask-image: url("govuk_publishing_components/icon-autocomplete-search-suggestion.svg");
117
+ background-color: $govuk-secondary-text-colour;
118
+ }
119
+
120
+ .gem-c-search-with-autocomplete__suggestion-text {
121
+ font-weight: bold;
122
+ }
123
+
124
+ .gem-c-search-with-autocomplete__suggestion-highlight {
125
+ font-weight: normal;
126
+ background: none;
127
+ }
128
+
129
+ // Tweak the look and feel for the autocomplete in large mode
130
+ .gem-c-search-with-autocomplete.gem-c-search-with-autocomplete--large {
131
+ .gem-c-search-with-autocomplete__menu {
132
+ @include enhance-autocomplete-menu-width($large-input-size);
133
+ }
134
+
135
+ .gem-c-search-with-autocomplete__option {
136
+ min-height: $large-input-size;
137
+ }
138
+ }
139
+
140
+ // Fix top border styling on "borderless" search input when rendered on a GOV.UK blue background
141
+ .gem-c-search-with-autocomplete.gem-c-search-with-autocomplete--on-govuk-blue {
142
+ .gem-c-search-with-autocomplete__menu {
143
+ border-top: 1px solid $govuk-border-colour;
144
+ }
145
+ }
146
+
147
+ // High contrast mode adjustments
148
+ @media (forced-colors: active) {
149
+ .gem-c-search-with-autocomplete__menu {
150
+ border-color: FieldText;
151
+ }
152
+
153
+ .gem-c-search-with-autocomplete__option {
154
+ forced-color-adjust: none; // opt out of all default forced-colors adjustments
155
+ background-color: Field;
156
+ color: FieldText;
157
+ }
158
+
159
+ .gem-c-search-with-autocomplete__option--focused,
160
+ .gem-c-search-with-autocomplete__option:hover,
161
+ .gem-c-search-with-autocomplete__option:focus-visible {
162
+ background-color: Highlight;
163
+ color: HighlightText;
164
+ border-color: FieldText;
165
+
166
+ .gem-c-search-with-autocomplete__suggestion-text {
167
+ background: none;
168
+ }
169
+
170
+ .gem-c-search-with-autocomplete__suggestion-highlight {
171
+ color: HighlightText;
172
+ }
173
+
174
+ .gem-c-search-with-autocomplete__suggestion-icon {
175
+ background-color: HighlightText;
176
+ }
177
+ }
178
+
179
+ // Allow mouse hover styling to take precedence over keyboard focus styling
180
+ .gem-c-search-with-autocomplete__option:focus-visible:not(:hover) {
181
+ background-color: SelectedItem;
182
+ color: SelectedItemText;
183
+
184
+ .gem-c-search-with-autocomplete__suggestion-highlight {
185
+ color: SelectedItemText;
186
+ }
187
+
188
+ .gem-c-search-with-autocomplete__suggestion-icon {
189
+ background-color: SelectedItemText;
190
+ }
191
+ }
192
+
193
+ .gem-c-search-with-autocomplete__suggestion-highlight {
194
+ color: FieldText;
195
+ }
196
+
197
+ .gem-c-search-with-autocomplete__suggestion-icon {
198
+ background-color: FieldText;
199
+ }
200
+ }
@@ -8,58 +8,34 @@
8
8
  product_name ||= nil
9
9
  remove_bottom_border ||= false
10
10
  search ||= false
11
- search_left ||= false
12
11
  width_class = full_width ? "govuk-header__container--full-width" : "govuk-width-container"
13
12
  logo_link ||= "/"
14
13
 
15
14
  header_classes = %w[gem-c-layout-header govuk-header]
16
15
  header_classes << "gem-c-layout-header--#{environment}" if environment
17
16
  header_classes << "gem-c-layout-header--no-bottom-border" if remove_bottom_border
18
- header_classes << "gem-c-layout-header--search-left" if search_left
19
17
  %>
20
18
 
21
19
  <header class="<%= header_classes.join(' ') %>" role="banner" data-module="govuk-header">
22
20
  <div class="govuk-header__container <%= width_class %>">
23
- <% if search_left %>
24
- <div class="govuk-grid-row">
25
- <div class="gem-c-layout-header__logo govuk-grid-column-one-third-from-desktop">
26
- <%= render "govuk_publishing_components/components/layout_header/header_logo", {
27
- environment: environment,
28
- logo_link: logo_link,
29
- product_name: product_name,
30
- } %>
31
- </div>
21
+ <div class="govuk-grid-row">
22
+ <div class="gem-c-layout-header__logo govuk-grid-column-one-half">
23
+ <%= render "govuk_publishing_components/components/layout_header/header_logo", {
24
+ environment: environment,
25
+ logo_link: logo_link,
26
+ product_name: product_name,
27
+ } %>
32
28
  </div>
33
- <div class="govuk-grid-row">
34
- <div class="govuk-grid-column-full govuk-grid-column-one-third-from-desktop gem-c-layout-header__search govuk-!-display-none-print">
35
- <%= render "govuk_publishing_components/components/layout_header/search" %>
29
+ <% if navigation_items.any? %>
30
+ <div class="govuk-header__content gem-c-header__content govuk-grid-column-full govuk-!-display-none-print">
31
+ <%= render "govuk_publishing_components/components/layout_header/navigation_items", navigation_items: navigation_items, navigation_aria_label: navigation_aria_label %>
36
32
  </div>
37
- <% if navigation_items.any? %>
38
- <div class="govuk-header__content gem-c-header__content govuk-grid-column-full govuk-!-display-none-print">
39
- <%= render "govuk_publishing_components/components/layout_header/navigation_items", navigation_items: navigation_items, navigation_aria_label: navigation_aria_label %>
40
- </div>
41
- <% end %>
42
- </div>
43
- <% else %>
44
- <div class="govuk-grid-row">
45
- <div class="gem-c-layout-header__logo govuk-grid-column-one-half">
46
- <%= render "govuk_publishing_components/components/layout_header/header_logo", {
47
- environment: environment,
48
- logo_link: logo_link,
49
- product_name: product_name,
50
- } %>
33
+ <% end %>
34
+ <% if search %>
35
+ <div class="govuk-grid-column-one-half gem-c-layout-header__search govuk-!-display-none-print">
36
+ <%= render "govuk_publishing_components/components/layout_header/search" %>
51
37
  </div>
52
- <% if navigation_items.any? %>
53
- <div class="govuk-header__content gem-c-header__content govuk-grid-column-full govuk-!-display-none-print">
54
- <%= render "govuk_publishing_components/components/layout_header/navigation_items", navigation_items: navigation_items, navigation_aria_label: navigation_aria_label %>
55
- </div>
56
- <% end %>
57
- <% if search %>
58
- <div class="govuk-grid-column-one-half gem-c-layout-header__search govuk-!-display-none-print">
59
- <%= render "govuk_publishing_components/components/layout_header/search" %>
60
- </div>
61
- <% end %>
62
- </div>
63
- <% end %>
38
+ <% end %>
39
+ </div>
64
40
  </div>
65
41
  </header>
@@ -61,20 +61,22 @@
61
61
  <%= tag_label %>
62
62
  <% end %>
63
63
  <div class="gem-c-search__item-wrapper">
64
- <%= tag.input(
65
- aria: {
66
- controls: aria_controls,
67
- },
68
- enterkeyhint: "search",
69
- class: "gem-c-search__item gem-c-search__input js-class-toggle",
70
- id: id,
71
- name: name,
72
- title: t("components.search_box.input_title"),
73
- type: "search",
74
- value: value,
75
- autocorrect: correction_value,
76
- autocapitalize: correction_value,
77
- ) %>
64
+ <div class="js-search-input-wrapper">
65
+ <%= tag.input(
66
+ aria: {
67
+ controls: aria_controls,
68
+ },
69
+ enterkeyhint: "search",
70
+ class: "gem-c-search__item gem-c-search__input js-class-toggle",
71
+ id: id,
72
+ name: name,
73
+ title: t("components.search_box.input_title"),
74
+ type: "search",
75
+ value: value,
76
+ autocorrect: correction_value,
77
+ autocapitalize: correction_value,
78
+ ) %>
79
+ </div>
78
80
  <div class="gem-c-search__item gem-c-search__submit-wrapper">
79
81
  <%= tag.button class: "gem-c-search__submit", type: "submit", data: data_attributes, enterkeyhint: "search" do %>
80
82
  <%= button_text %>
@@ -0,0 +1,27 @@
1
+ <%
2
+ add_gem_component_stylesheet("search-with-autocomplete")
3
+
4
+ source_url = local_assigns[:source_url]
5
+ source_key = local_assigns[:source_key]
6
+
7
+ if source_url.nil? || source_key.nil?
8
+ raise ArgumentError, "The search_with_autocomplete component requires source_url and source_key"
9
+ end
10
+
11
+ search_component_options = local_assigns.except(:autocomplete, :source_url, :source_key).merge(
12
+ # The `search` component has an inline label by default, but this conflicts with the accessible-
13
+ # autocomplete component's markup and styling. Every potential use of this component is in
14
+ # situations where we want the label not to be inline anyway, so we override the default here.
15
+ inline_label: false
16
+ )
17
+
18
+ classes = %w[gem-c-search-with-autocomplete]
19
+ classes << "gem-c-search-with-autocomplete--large" if local_assigns[:size] == "large"
20
+ classes << "gem-c-search-with-autocomplete--on-govuk-blue" if local_assigns[:on_govuk_blue]
21
+ %>
22
+ <%= tag.div(
23
+ class: classes.join(" "),
24
+ data: { module: "gem-search-with-autocomplete", source_url:, source_key: }
25
+ ) do %>
26
+ <%= render "govuk_publishing_components/components/search", search_component_options %>
27
+ <% end %>
@@ -41,47 +41,6 @@ examples:
41
41
  - text: Hidden on desktop
42
42
  href: "item-3"
43
43
  show_only_in_collapsed_menu: true
44
- with_left_search_and_navigation:
45
- description: This supports pages where the search appears on the left with multiple navigation links on the right, such as the [How government works](https://www.gov.uk/government/how-government-works) page
46
- data:
47
- search_left: true
48
- navigation_items:
49
- - text: Departments
50
- href: "item-1"
51
- - text: Worldwide
52
- href: "item-2"
53
- - text: How government works
54
- href: "item-3"
55
- - text: Get involved
56
- href: "item-4"
57
- - text: Consultations
58
- href: "item-4"
59
- - text: Statistics
60
- href: "item-5"
61
- - text: News and communications
62
- href: "item-6"
63
- active: true
64
- with_custom_navigation_aria_label:
65
- description: The navigation has `aria-label="Top level"` by default. This option is here for when the `aria-label` needs to be more descriptive than that.
66
- data:
67
- search_left: true
68
- navigation_aria_label: "Departments and policy"
69
- navigation_items:
70
- - text: Departments
71
- href: "item-1"
72
- - text: Worldwide
73
- href: "item-2"
74
- - text: How government works
75
- href: "item-3"
76
- - text: Get involved
77
- href: "item-4"
78
- - text: Consultations
79
- href: "item-4"
80
- - text: Statistics
81
- href: "item-5"
82
- - text: News and communications
83
- href: "item-6"
84
- active: true
85
44
  with_navigation_link_data_attributes:
86
45
  description: Supports adding data attributes i.e for tracking
87
46
  data:
@@ -27,11 +27,15 @@ examples:
27
27
  data:
28
28
  phase: beta
29
29
  inverse: true
30
+ context:
31
+ dark_background: true
30
32
  inverse_for_blue_background_with_app_name:
31
33
  data:
32
34
  app_name: Skittles Maker
33
35
  phase: beta
34
36
  inverse: true
37
+ context:
38
+ dark_background: true
35
39
  without_ga4_tracking:
36
40
  description: |
37
41
  Disables GA4 tracking on the banner. Tracking is enabled by default. This includes link tracking on the component itself, and allows pageviews to record the presence of the banner on page load.
@@ -0,0 +1,61 @@
1
+ name: Search with autocomplete (experimental)
2
+ description: |
3
+ A version of the search component enhanced with the ability to fetch and display search
4
+ suggestions from a remote source as a user types.
5
+ body: |
6
+ This component uses [Accessible Autocomplete](https://github.com/alphagov/accessible-autocomplete)
7
+ to enhance the [`search` component's](/component-guide/search) input element.
8
+ If the user does not have JavaScript enabled, the search component will function as normal.
9
+
10
+ The Accessible Autocomplete component generates its own input field (rather than working on the
11
+ existing one). We then remove the old input field from the DOM, and enhance the component to:
12
+
13
+ * give it the correct attributes and classes from the original input field
14
+ * fetch suggestions from a remote URL as the user types
15
+ * highlight parts of suggestions where they match the user's input
16
+ * submit the form the component is contained in when a suggestion is selected
17
+
18
+ The component will fetch results from the provided `source_url`, which should always return a JSON
19
+ response with a single object at the root, which has a property `source_key` containing an array
20
+ of strings. The component will then display these strings as suggestions to the user.
21
+
22
+ Note that the inline label on the `search` component conflicts with the markup and styling
23
+ generated internally by Accessible Autocomplete. Our current designs do not foresee us using
24
+ autocomplete on a search box with an inline label, and this component will always force the
25
+ `inline_label` option on its nested `search` component to be `false`.
26
+
27
+ Note that this component has undergone a DAC audit in September 2024, but should be considered
28
+ experimental until it has been AB tested on GOV.UK.
29
+ accessibility_criteria: |
30
+ This component should meet the accessibility acceptance criteria outlined in the [nested search
31
+ component](/component-guide/search#accessibility-acceptance-criteria), as well as those of the
32
+ external [Accessible Autocomplete
33
+ Component](https://github.com/alphagov/accessible-autocomplete/blob/master/accessibility-criteria.md)
34
+ project.
35
+ examples:
36
+ default:
37
+ data:
38
+ source_url: 'https://www.gov.uk/api/search.json?suggest=autocomplete'
39
+ source_key: suggested_autocomplete
40
+ set_input_value:
41
+ data:
42
+ source_url: 'https://www.gov.uk/api/search.json?suggest=autocomplete'
43
+ source_key: suggested_autocomplete
44
+ value: "driving licence"
45
+ homepage:
46
+ description: For use on the homepage.
47
+ data:
48
+ source_url: 'https://www.gov.uk/api/search.json?suggest=autocomplete'
49
+ source_key: suggested_autocomplete
50
+ label_text: "Search"
51
+ on_govuk_blue: true
52
+ label_size: "s"
53
+ homepage: true
54
+ size: "large"
55
+ context:
56
+ dark_background: true
57
+ complex_custom_label:
58
+ data:
59
+ source_url: 'https://www.gov.uk/api/search.json?suggest=autocomplete'
60
+ source_key: suggested_autocomplete
61
+ label_text: <h2 class="govuk-heading-m govuk-!-margin-bottom-1">Search GOV.UK</h2>
@@ -1,3 +1,3 @@
1
1
  module GovukPublishingComponents
2
- VERSION = "43.3.0".freeze
2
+ VERSION = "43.4.1".freeze
3
3
  end