govuk_publishing_components 65.1.0 → 65.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (69) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/stylesheets/component_guide/application.scss +13 -15
  3. data/app/assets/stylesheets/govuk_publishing_components/all-components.scss +0 -1
  4. data/app/assets/stylesheets/govuk_publishing_components/components/_contents-list.scss +25 -0
  5. data/app/assets/stylesheets/govuk_publishing_components/components/_details.scss +34 -0
  6. data/app/assets/stylesheets/govuk_publishing_components/components/_heading.scss +1 -0
  7. data/app/assets/stylesheets/govuk_publishing_components/components/helpers/_markdown-typography.scss +4 -0
  8. data/app/assets/stylesheets/govuk_publishing_components/specific-components.scss +0 -1
  9. data/app/controllers/govuk_publishing_components/applications_page_controller.rb +1 -1
  10. data/app/controllers/govuk_publishing_components/audit_controller.rb +0 -1
  11. data/app/models/govuk_publishing_components/component_doc.rb +10 -3
  12. data/app/models/govuk_publishing_components/component_wrapper_helper_options.rb +4 -2
  13. data/app/views/govuk_publishing_components/component_guide/component_doc/_component.html.erb +1 -1
  14. data/app/views/govuk_publishing_components/component_guide/component_doc/_preview.html.erb +2 -2
  15. data/app/views/govuk_publishing_components/component_guide/show.html.erb +47 -33
  16. data/app/views/govuk_publishing_components/components/_details.html.erb +4 -0
  17. data/app/views/govuk_publishing_components/components/_devolved_nations.html.erb +2 -2
  18. data/app/views/govuk_publishing_components/components/_option_select.html.erb +2 -2
  19. data/app/views/govuk_publishing_components/components/docs/details.yml +16 -0
  20. data/lib/govuk_publishing_components/presenters/devolved_nations_helper.rb +13 -7
  21. data/lib/govuk_publishing_components/version.rb +1 -1
  22. data/node_modules/choices.js/README.md +140 -30
  23. data/node_modules/choices.js/package.json +10 -13
  24. data/node_modules/choices.js/public/assets/scripts/choices.js +144 -89
  25. data/node_modules/choices.js/public/assets/scripts/choices.min.js +2 -2
  26. data/node_modules/choices.js/public/assets/scripts/choices.mjs +144 -89
  27. data/node_modules/choices.js/public/assets/scripts/choices.search-basic.js +144 -86
  28. data/node_modules/choices.js/public/assets/scripts/choices.search-basic.min.js +2 -2
  29. data/node_modules/choices.js/public/assets/scripts/choices.search-basic.mjs +144 -86
  30. data/node_modules/choices.js/public/assets/scripts/choices.search-kmp.js +139 -77
  31. data/node_modules/choices.js/public/assets/scripts/choices.search-kmp.min.js +2 -2
  32. data/node_modules/choices.js/public/assets/scripts/choices.search-kmp.mjs +139 -77
  33. data/node_modules/choices.js/public/assets/scripts/choices.search-prefix.js +137 -76
  34. data/node_modules/choices.js/public/assets/scripts/choices.search-prefix.min.js +2 -2
  35. data/node_modules/choices.js/public/assets/scripts/choices.search-prefix.mjs +137 -76
  36. data/node_modules/choices.js/public/assets/styles/base.css +39 -9
  37. data/node_modules/choices.js/public/assets/styles/base.css.map +1 -1
  38. data/node_modules/choices.js/public/assets/styles/base.min.css +1 -1
  39. data/node_modules/choices.js/public/assets/styles/choices.css +93 -95
  40. data/node_modules/choices.js/public/assets/styles/choices.css.map +1 -1
  41. data/node_modules/choices.js/public/assets/styles/choices.min.css +1 -1
  42. data/node_modules/choices.js/public/types/src/scripts/choices.d.ts +11 -0
  43. data/node_modules/choices.js/public/types/src/scripts/components/container.d.ts +2 -0
  44. data/node_modules/choices.js/public/types/src/scripts/interfaces/choice-full.d.ts +2 -1
  45. data/node_modules/choices.js/public/types/src/scripts/interfaces/class-names.d.ts +2 -0
  46. data/node_modules/choices.js/public/types/src/scripts/interfaces/input-choice.d.ts +2 -1
  47. data/node_modules/choices.js/public/types/src/scripts/interfaces/options.d.ts +19 -3
  48. data/node_modules/choices.js/public/types/src/scripts/interfaces/store.d.ts +2 -1
  49. data/node_modules/choices.js/public/types/src/scripts/interfaces/types.d.ts +2 -1
  50. data/node_modules/choices.js/public/types/src/scripts/lib/utils.d.ts +3 -1
  51. data/node_modules/choices.js/src/scripts/choices.ts +110 -64
  52. data/node_modules/choices.js/src/scripts/components/container.ts +8 -0
  53. data/node_modules/choices.js/src/scripts/components/wrapped-select.ts +3 -1
  54. data/node_modules/choices.js/src/scripts/defaults.ts +12 -7
  55. data/node_modules/choices.js/src/scripts/interfaces/choice-full.ts +2 -1
  56. data/node_modules/choices.js/src/scripts/interfaces/class-names.ts +2 -0
  57. data/node_modules/choices.js/src/scripts/interfaces/event-choice.ts +1 -0
  58. data/node_modules/choices.js/src/scripts/interfaces/input-choice.ts +4 -2
  59. data/node_modules/choices.js/src/scripts/interfaces/options.ts +21 -3
  60. data/node_modules/choices.js/src/scripts/interfaces/store.ts +2 -1
  61. data/node_modules/choices.js/src/scripts/interfaces/types.ts +3 -1
  62. data/node_modules/choices.js/src/scripts/lib/utils.ts +27 -4
  63. data/node_modules/choices.js/src/scripts/search/kmp.ts +2 -1
  64. data/node_modules/choices.js/src/scripts/store/store.ts +4 -1
  65. data/node_modules/choices.js/src/scripts/templates.ts +6 -3
  66. data/node_modules/choices.js/src/styles/base.scss +42 -9
  67. data/node_modules/choices.js/src/styles/choices.scss +119 -93
  68. metadata +2 -3
  69. data/app/assets/stylesheets/govuk_publishing_components/components/helpers/_contents-list-helper.scss +0 -24
@@ -1,4 +1,4 @@
1
- /*! choices.js v11.1.0 | © 2025 Josh Johnson | https://github.com/jshjohnson/Choices#readme */
1
+ /*! choices.js v11.2.1 | © 2026 Josh Johnson | https://github.com/Choices-js/Choices#readme */
2
2
 
3
3
  /******************************************************************************
4
4
  Copyright (c) Microsoft Corporation.
@@ -211,9 +211,6 @@ var strToEl = (function () {
211
211
  return firstChild;
212
212
  };
213
213
  })();
214
- var resolveNoticeFunction = function (fn, value) {
215
- return typeof fn === 'function' ? fn(sanitise(value), value) : fn;
216
- };
217
214
  var resolveStringFunction = function (fn) {
218
215
  return typeof fn === 'function' ? fn() : fn;
219
216
  };
@@ -245,6 +242,26 @@ var unwrapStringForEscaped = function (s) {
245
242
  }
246
243
  return '';
247
244
  };
245
+ var getChoiceForOutput = function (choice, keyCode) {
246
+ return {
247
+ id: choice.id,
248
+ highlighted: choice.highlighted,
249
+ labelClass: choice.labelClass,
250
+ labelDescription: unwrapStringForRaw(choice.labelDescription),
251
+ customProperties: choice.customProperties,
252
+ disabled: choice.disabled,
253
+ active: choice.active,
254
+ label: choice.label,
255
+ placeholder: choice.placeholder,
256
+ value: choice.value,
257
+ groupValue: choice.group ? choice.group.label : undefined,
258
+ element: choice.element,
259
+ keyCode: keyCode,
260
+ };
261
+ };
262
+ var resolveNoticeFunction = function (fn, value, item) {
263
+ return typeof fn === 'function' ? fn(sanitise(value), unwrapStringForRaw(value), item) : fn;
264
+ };
248
265
  var escapeForTemplate = function (allowHTML, s) {
249
266
  return allowHTML ? unwrapStringForEscaped(s) : sanitise(s);
250
267
  };
@@ -412,6 +429,12 @@ var Container = /** @class */ (function () {
412
429
  Container.prototype.removeFocusState = function () {
413
430
  removeClassesFromElement(this.element, this.classNames.focusState);
414
431
  };
432
+ Container.prototype.addInvalidState = function () {
433
+ addClassesToElement(this.element, this.classNames.invalidState);
434
+ };
435
+ Container.prototype.removeInvalidState = function () {
436
+ removeClassesFromElement(this.element, this.classNames.invalidState);
437
+ };
415
438
  Container.prototype.enable = function () {
416
439
  removeClassesFromElement(this.element, this.classNames.disabledState);
417
440
  this.element.removeAttribute('aria-disabled');
@@ -877,7 +900,9 @@ var WrappedSelect = /** @class */ (function (_super) {
877
900
  highlighted: false,
878
901
  placeholder: this.extractPlaceholder && (!option.value || option.hasAttribute('placeholder')),
879
902
  labelClass: typeof option.dataset.labelClass !== 'undefined' ? stringToHtmlClass(option.dataset.labelClass) : undefined,
880
- labelDescription: typeof option.dataset.labelDescription !== 'undefined' ? option.dataset.labelDescription : undefined,
903
+ labelDescription: typeof option.dataset.labelDescription !== 'undefined'
904
+ ? { trusted: option.dataset.labelDescription }
905
+ : undefined,
881
906
  customProperties: parseCustomProperties(option.dataset.customProperties),
882
907
  };
883
908
  };
@@ -923,6 +948,7 @@ var DEFAULT_CLASSNAMES = {
923
948
  selectedState: ['is-selected'],
924
949
  flippedState: ['is-flipped'],
925
950
  loadingState: ['is-loading'],
951
+ invalidState: ['is-invalid'],
926
952
  notice: ['choices__notice'],
927
953
  addChoice: ['choices__item--selectable', 'add-choice'],
928
954
  noResults: ['has-no-results'],
@@ -950,6 +976,7 @@ var DEFAULT_CONFIG = {
950
976
  paste: true,
951
977
  searchEnabled: true,
952
978
  searchChoices: true,
979
+ searchDisabledChoices: false,
953
980
  searchFloor: 1,
954
981
  searchResultLimit: 4,
955
982
  searchFields: ['label', 'value'],
@@ -965,6 +992,7 @@ var DEFAULT_CONFIG = {
965
992
  prependValue: null,
966
993
  appendValue: null,
967
994
  renderSelectedChoices: 'auto',
995
+ searchRenderSelectedChoices: true,
968
996
  loadingText: 'Loading...',
969
997
  noResultsText: 'No results found',
970
998
  noChoicesText: 'No choices to choose from',
@@ -973,7 +1001,9 @@ var DEFAULT_CONFIG = {
973
1001
  customAddItemText: 'Only values matching specific conditions can be added',
974
1002
  addItemText: function (value) { return "Press Enter to add <b>\"".concat(value, "\"</b>"); },
975
1003
  removeItemIconText: function () { return "Remove item"; },
976
- removeItemLabelText: function (value) { return "Remove item: ".concat(value); },
1004
+ removeItemLabelText: function (value, _valueRaw, i) {
1005
+ return "Remove item: ".concat(i ? sanitise(i.label) : value);
1006
+ },
977
1007
  maxItemText: function (maxItemCount) { return "Only ".concat(maxItemCount, " values can be added"); },
978
1008
  valueComparer: function (value1, value2) { return value1 === value2; },
979
1009
  fuseOptions: {
@@ -1274,7 +1304,8 @@ var Store = /** @class */ (function () {
1274
1304
  * Get choices that can be searched (excluding placeholders or disabled choices)
1275
1305
  */
1276
1306
  get: function () {
1277
- return this.choices.filter(function (choice) { return !choice.disabled && !choice.placeholder; });
1307
+ var context = this._context;
1308
+ return this.choices.filter(function (choice) { return !choice.placeholder && (context.searchDisabledChoices || !choice.disabled); });
1278
1309
  },
1279
1310
  enumerable: false,
1280
1311
  configurable: true
@@ -1332,9 +1363,9 @@ var NoticeTypes = {
1332
1363
  function _defineProperty(e, r, t) {
1333
1364
  return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, {
1334
1365
  value: t,
1335
- enumerable: !0,
1336
- configurable: !0,
1337
- writable: !0
1366
+ enumerable: true,
1367
+ configurable: true,
1368
+ writable: true
1338
1369
  }) : e[r] = t, e;
1339
1370
  }
1340
1371
  function ownKeys(e, r) {
@@ -1350,7 +1381,7 @@ function ownKeys(e, r) {
1350
1381
  function _objectSpread2(e) {
1351
1382
  for (var r = 1; r < arguments.length; r++) {
1352
1383
  var t = null != arguments[r] ? arguments[r] : {};
1353
- r % 2 ? ownKeys(Object(t), !0).forEach(function (r) {
1384
+ r % 2 ? ownKeys(Object(t), true).forEach(function (r) {
1354
1385
  _defineProperty(e, r, t[r]);
1355
1386
  }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) {
1356
1387
  Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r));
@@ -1362,7 +1393,7 @@ function _toPrimitive(t, r) {
1362
1393
  if ("object" != typeof t || !t) return t;
1363
1394
  var e = t[Symbol.toPrimitive];
1364
1395
  if (void 0 !== e) {
1365
- var i = e.call(t, r || "default");
1396
+ var i = e.call(t, r);
1366
1397
  if ("object" != typeof i) return i;
1367
1398
  throw new TypeError("@@toPrimitive must return a primitive value.");
1368
1399
  }
@@ -1385,16 +1416,13 @@ function _toPropertyKey(t) {
1385
1416
  function isArray(value) {
1386
1417
  return !Array.isArray ? getTag(value) === '[object Array]' : Array.isArray(value);
1387
1418
  }
1388
-
1389
- // Adapted from: https://github.com/lodash/lodash/blob/master/.internal/baseToString.js
1390
- const INFINITY = 1 / 0;
1391
1419
  function baseToString(value) {
1392
1420
  // Exit early for strings to avoid a performance hit in some environments.
1393
1421
  if (typeof value == 'string') {
1394
1422
  return value;
1395
1423
  }
1396
1424
  let result = value + '';
1397
- return result == '0' && 1 / value == -INFINITY ? '-0' : result;
1425
+ return result == '0' && 1 / value == -Infinity ? '-0' : result;
1398
1426
  }
1399
1427
  function toString(value) {
1400
1428
  return value == null ? '' : baseToString(value);
@@ -1430,7 +1458,6 @@ function isBlank(value) {
1430
1458
  function getTag(value) {
1431
1459
  return value == null ? value === undefined ? '[object Undefined]' : '[object Null]' : Object.prototype.toString.call(value);
1432
1460
  }
1433
- const EXTENDED_SEARCH_UNAVAILABLE = 'Extended search is not available';
1434
1461
  const INCORRECT_INDEX_TYPE = "Incorrect 'index' type";
1435
1462
  const LOGICAL_SEARCH_INVALID_QUERY_FOR_KEY = key => `Invalid value for key ${key}`;
1436
1463
  const PATTERN_LENGTH_TOO_LARGE = max => `Pattern length exceeds max of ${max}.`;
@@ -2684,9 +2711,7 @@ function format(results, docs, {
2684
2711
  class Fuse {
2685
2712
  constructor(docs, options = {}, index) {
2686
2713
  this.options = _objectSpread2(_objectSpread2({}, Config), options);
2687
- if (this.options.useExtendedSearch && !true) {
2688
- throw new Error(EXTENDED_SEARCH_UNAVAILABLE);
2689
- }
2714
+ if (this.options.useExtendedSearch && false) ;
2690
2715
  this._keyStore = new KeyStore(this.options.keys);
2691
2716
  this.setCollection(docs, index);
2692
2717
  }
@@ -3018,7 +3043,7 @@ var assignCustomProperties = function (el, choice, withCustomProperties) {
3018
3043
  dataset.labelClass = getClassNames(labelClass).join(' ');
3019
3044
  }
3020
3045
  if (labelDescription) {
3021
- dataset.labelDescription = labelDescription;
3046
+ dataset.labelDescription = unwrapStringForRaw(labelDescription);
3022
3047
  }
3023
3048
  if (withCustomProperties && customProperties) {
3024
3049
  if (typeof customProperties === 'string') {
@@ -3125,8 +3150,9 @@ var templates = {
3125
3150
  var removeButton = document.createElement('button');
3126
3151
  removeButton.type = 'button';
3127
3152
  addClassesToElement(removeButton, button);
3128
- setElementHtml(removeButton, true, resolveNoticeFunction(removeItemIconText, choice.value));
3129
- var REMOVE_ITEM_LABEL = resolveNoticeFunction(removeItemLabelText, choice.value);
3153
+ var eventChoice = getChoiceForOutput(choice);
3154
+ setElementHtml(removeButton, true, resolveNoticeFunction(removeItemIconText, choice.value, eventChoice));
3155
+ var REMOVE_ITEM_LABEL = resolveNoticeFunction(removeItemLabelText, choice.value, eventChoice);
3130
3156
  if (REMOVE_ITEM_LABEL) {
3131
3157
  removeButton.setAttribute('aria-label', REMOVE_ITEM_LABEL);
3132
3158
  }
@@ -3231,6 +3257,7 @@ var templates = {
3231
3257
  else {
3232
3258
  addClassesToElement(div, itemSelectable);
3233
3259
  div.dataset.choiceSelectable = '';
3260
+ div.setAttribute('aria-selected', choice.selected ? 'true' : 'false');
3234
3261
  }
3235
3262
  return div;
3236
3263
  },
@@ -3400,7 +3427,7 @@ var Choices = /** @class */ (function () {
3400
3427
  this.initialised = false;
3401
3428
  this._store = new Store(config);
3402
3429
  this._currentValue = '';
3403
- config.searchEnabled = (!isText && config.searchEnabled) || isSelectMultiple;
3430
+ config.searchEnabled = !isText && config.searchEnabled;
3404
3431
  this._canSearch = config.searchEnabled;
3405
3432
  this._isScrollingOnIe = false;
3406
3433
  this._highlightPosition = 0;
@@ -3440,6 +3467,8 @@ var Choices = /** @class */ (function () {
3440
3467
  this._onEscapeKey = this._onEscapeKey.bind(this);
3441
3468
  this._onDirectionKey = this._onDirectionKey.bind(this);
3442
3469
  this._onDeleteKey = this._onDeleteKey.bind(this);
3470
+ this._onChange = this._onChange.bind(this);
3471
+ this._onInvalid = this._onInvalid.bind(this);
3443
3472
  // If element has already been initialised with Choices, fail silently
3444
3473
  if (this.passedElement.isActive) {
3445
3474
  if (!config.silent) {
@@ -3546,7 +3575,7 @@ var Choices = /** @class */ (function () {
3546
3575
  }
3547
3576
  this._store.dispatch(highlightItem(choice, true));
3548
3577
  if (runEvent) {
3549
- this.passedElement.triggerEvent(EventType.highlightItem, this._getChoiceForOutput(choice));
3578
+ this.passedElement.triggerEvent(EventType.highlightItem, getChoiceForOutput(choice));
3550
3579
  }
3551
3580
  return this;
3552
3581
  };
@@ -3561,7 +3590,7 @@ var Choices = /** @class */ (function () {
3561
3590
  }
3562
3591
  this._store.dispatch(highlightItem(choice, false));
3563
3592
  if (runEvent) {
3564
- this.passedElement.triggerEvent(EventType.unhighlightItem, this._getChoiceForOutput(choice));
3593
+ this.passedElement.triggerEvent(EventType.unhighlightItem, getChoiceForOutput(choice));
3565
3594
  }
3566
3595
  return this;
3567
3596
  };
@@ -3571,7 +3600,7 @@ var Choices = /** @class */ (function () {
3571
3600
  _this._store.items.forEach(function (item) {
3572
3601
  if (!item.highlighted) {
3573
3602
  _this._store.dispatch(highlightItem(item, true));
3574
- _this.passedElement.triggerEvent(EventType.highlightItem, _this._getChoiceForOutput(item));
3603
+ _this.passedElement.triggerEvent(EventType.highlightItem, getChoiceForOutput(item));
3575
3604
  }
3576
3605
  });
3577
3606
  });
@@ -3583,7 +3612,7 @@ var Choices = /** @class */ (function () {
3583
3612
  _this._store.items.forEach(function (item) {
3584
3613
  if (item.highlighted) {
3585
3614
  _this._store.dispatch(highlightItem(item, false));
3586
- _this.passedElement.triggerEvent(EventType.highlightItem, _this._getChoiceForOutput(item));
3615
+ _this.passedElement.triggerEvent(EventType.highlightItem, getChoiceForOutput(item));
3587
3616
  }
3588
3617
  });
3589
3618
  });
@@ -3638,6 +3667,11 @@ var Choices = /** @class */ (function () {
3638
3667
  _this.input.focus();
3639
3668
  }
3640
3669
  _this.passedElement.triggerEvent(EventType.showDropdown);
3670
+ var activeElement = _this.choiceList.element.querySelector(getClassNamesSelector(_this.config.classNames.selectedState));
3671
+ if (activeElement !== null && !isScrolledIntoView(activeElement, _this.choiceList.element)) {
3672
+ // We use the native scrollIntoView function instead of choiceList.scrollToChildElement to avoid animated scroll.
3673
+ activeElement.scrollIntoView();
3674
+ }
3641
3675
  });
3642
3676
  return this;
3643
3677
  };
@@ -3646,6 +3680,7 @@ var Choices = /** @class */ (function () {
3646
3680
  if (!this.dropdown.isActive) {
3647
3681
  return this;
3648
3682
  }
3683
+ this._removeHighlightedChoices();
3649
3684
  requestAnimationFrame(function () {
3650
3685
  _this.dropdown.hide();
3651
3686
  _this.containerOuter.close();
@@ -3658,9 +3693,8 @@ var Choices = /** @class */ (function () {
3658
3693
  return this;
3659
3694
  };
3660
3695
  Choices.prototype.getValue = function (valueOnly) {
3661
- var _this = this;
3662
3696
  var values = this._store.items.map(function (item) {
3663
- return (valueOnly ? item.value : _this._getChoiceForOutput(item));
3697
+ return (valueOnly ? item.value : getChoiceForOutput(item));
3664
3698
  });
3665
3699
  return this._isSelectOneElement || this.config.singleModeForMultiSelect ? values[0] : values;
3666
3700
  };
@@ -3918,7 +3952,7 @@ var Choices = /** @class */ (function () {
3918
3952
  // @todo integrate with Store
3919
3953
  this._searcher.reset();
3920
3954
  if (choice.selected) {
3921
- this.passedElement.triggerEvent(EventType.removeItem, this._getChoiceForOutput(choice));
3955
+ this.passedElement.triggerEvent(EventType.removeItem, getChoiceForOutput(choice));
3922
3956
  }
3923
3957
  return this;
3924
3958
  };
@@ -4001,13 +4035,7 @@ var Choices = /** @class */ (function () {
4001
4035
  }
4002
4036
  var _a = this, config = _a.config, isSearching = _a._isSearching;
4003
4037
  var _b = this._store, activeGroups = _b.activeGroups, activeChoices = _b.activeChoices;
4004
- var renderLimit = 0;
4005
- if (isSearching && config.searchResultLimit > 0) {
4006
- renderLimit = config.searchResultLimit;
4007
- }
4008
- else if (config.renderChoiceLimit > 0) {
4009
- renderLimit = config.renderChoiceLimit;
4010
- }
4038
+ var renderLimit = isSearching ? config.searchResultLimit : config.renderChoiceLimit;
4011
4039
  if (this._isSelectElement) {
4012
4040
  var backingOptions = activeChoices.filter(function (choice) { return !choice.element; });
4013
4041
  if (backingOptions.length) {
@@ -4017,11 +4045,16 @@ var Choices = /** @class */ (function () {
4017
4045
  var fragment = document.createDocumentFragment();
4018
4046
  var renderableChoices = function (choices) {
4019
4047
  return choices.filter(function (choice) {
4020
- return !choice.placeholder && (isSearching ? !!choice.rank : config.renderSelectedChoices || !choice.selected);
4048
+ return !choice.placeholder &&
4049
+ (isSearching
4050
+ ? (config.searchRenderSelectedChoices || !choice.selected) && !!choice.rank
4051
+ : config.renderSelectedChoices || !choice.selected);
4021
4052
  });
4022
4053
  };
4054
+ var showLabel = config.appendGroupInSearch && isSearching;
4023
4055
  var selectableChoices = false;
4024
- var renderChoices = function (choices, withinGroup, groupLabel) {
4056
+ var highlightedEl = null;
4057
+ var renderChoices = function (choices, withinGroup) {
4025
4058
  if (isSearching) {
4026
4059
  // sortByRank is used to ensure stable sorting, as scores are non-unique
4027
4060
  // this additionally ensures fuseOptions.sortFn is not ignored
@@ -4031,16 +4064,20 @@ var Choices = /** @class */ (function () {
4031
4064
  choices.sort(config.sorter);
4032
4065
  }
4033
4066
  var choiceLimit = choices.length;
4034
- choiceLimit = !withinGroup && renderLimit && choiceLimit > renderLimit ? renderLimit : choiceLimit;
4067
+ choiceLimit = !withinGroup && renderLimit > 0 && choiceLimit > renderLimit ? renderLimit : choiceLimit;
4035
4068
  choiceLimit--;
4036
4069
  choices.every(function (choice, index) {
4037
4070
  // choiceEl being empty signals the contents has probably significantly changed
4038
- var dropdownItem = choice.choiceEl || _this._templates.choice(config, choice, config.itemSelectText, groupLabel);
4071
+ var dropdownItem = choice.choiceEl ||
4072
+ _this._templates.choice(config, choice, config.itemSelectText, showLabel && choice.group ? choice.group.label : undefined);
4039
4073
  choice.choiceEl = dropdownItem;
4040
4074
  fragment.appendChild(dropdownItem);
4041
4075
  if (isSearching || !choice.selected) {
4042
4076
  selectableChoices = true;
4043
4077
  }
4078
+ else if (!highlightedEl) {
4079
+ highlightedEl = dropdownItem;
4080
+ }
4044
4081
  return index < choiceLimit;
4045
4082
  });
4046
4083
  };
@@ -4050,7 +4087,7 @@ var Choices = /** @class */ (function () {
4050
4087
  }
4051
4088
  if (!this._hasNonChoicePlaceholder && !isSearching && this._isSelectOneElement) {
4052
4089
  // If we have a placeholder choice along with groups
4053
- renderChoices(activeChoices.filter(function (choice) { return choice.placeholder && !choice.group; }), false, undefined);
4090
+ renderChoices(activeChoices.filter(function (choice) { return choice.placeholder && !choice.group; }), false);
4054
4091
  }
4055
4092
  // If we have grouped options
4056
4093
  if (activeGroups.length && !isSearching) {
@@ -4059,7 +4096,7 @@ var Choices = /** @class */ (function () {
4059
4096
  }
4060
4097
  // render Choices without group first, regardless of sort, otherwise they won't be distinguishable
4061
4098
  // from the last group
4062
- renderChoices(activeChoices.filter(function (choice) { return !choice.placeholder && !choice.group; }), false, undefined);
4099
+ renderChoices(activeChoices.filter(function (choice) { return !choice.placeholder && !choice.group; }), false);
4063
4100
  activeGroups.forEach(function (group) {
4064
4101
  var groupChoices = renderableChoices(group.choices);
4065
4102
  if (groupChoices.length) {
@@ -4069,12 +4106,12 @@ var Choices = /** @class */ (function () {
4069
4106
  dropdownGroup.remove();
4070
4107
  fragment.appendChild(dropdownGroup);
4071
4108
  }
4072
- renderChoices(groupChoices, true, config.appendGroupInSearch && isSearching ? group.label : undefined);
4109
+ renderChoices(groupChoices, true);
4073
4110
  }
4074
4111
  });
4075
4112
  }
4076
4113
  else {
4077
- renderChoices(renderableChoices(activeChoices), false, undefined);
4114
+ renderChoices(renderableChoices(activeChoices), false);
4078
4115
  }
4079
4116
  }
4080
4117
  if (!selectableChoices && (isSearching || !fragment.children.length || !config.renderSelectedChoices)) {
@@ -4088,9 +4125,7 @@ var Choices = /** @class */ (function () {
4088
4125
  }
4089
4126
  this._renderNotice(fragment);
4090
4127
  this.choiceList.element.replaceChildren(fragment);
4091
- if (selectableChoices) {
4092
- this._highlightChoice();
4093
- }
4128
+ this._highlightChoice(highlightedEl);
4094
4129
  };
4095
4130
  Choices.prototype._renderItems = function () {
4096
4131
  var _this = this;
@@ -4200,23 +4235,12 @@ var Choices = /** @class */ (function () {
4200
4235
  }
4201
4236
  }
4202
4237
  };
4238
+ /**
4239
+ * @deprecated Use utils.getChoiceForOutput
4240
+ */
4203
4241
  // eslint-disable-next-line class-methods-use-this
4204
4242
  Choices.prototype._getChoiceForOutput = function (choice, keyCode) {
4205
- return {
4206
- id: choice.id,
4207
- highlighted: choice.highlighted,
4208
- labelClass: choice.labelClass,
4209
- labelDescription: choice.labelDescription,
4210
- customProperties: choice.customProperties,
4211
- disabled: choice.disabled,
4212
- active: choice.active,
4213
- label: choice.label,
4214
- placeholder: choice.placeholder,
4215
- value: choice.value,
4216
- groupValue: choice.group ? choice.group.label : undefined,
4217
- element: choice.element,
4218
- keyCode: keyCode,
4219
- };
4243
+ return getChoiceForOutput(choice, keyCode);
4220
4244
  };
4221
4245
  Choices.prototype._triggerChange = function (value) {
4222
4246
  if (value === undefined || value === null) {
@@ -4232,7 +4256,7 @@ var Choices = /** @class */ (function () {
4232
4256
  if (!items.length || !this.config.removeItems || !this.config.removeItemButton) {
4233
4257
  return;
4234
4258
  }
4235
- var id = element && parseDataSetId(element.parentElement);
4259
+ var id = element && parseDataSetId(element.closest('[data-id]'));
4236
4260
  var itemToRemove = id && items.find(function (item) { return item.id === id; });
4237
4261
  if (!itemToRemove) {
4238
4262
  return;
@@ -4421,7 +4445,7 @@ var Choices = /** @class */ (function () {
4421
4445
  var notice = '';
4422
4446
  if (canAddItem && typeof config.addItemFilter === 'function' && !config.addItemFilter(value)) {
4423
4447
  canAddItem = false;
4424
- notice = resolveNoticeFunction(config.customAddItemText, value);
4448
+ notice = resolveNoticeFunction(config.customAddItemText, value, undefined);
4425
4449
  }
4426
4450
  if (canAddItem) {
4427
4451
  var foundChoice = this._store.choices.find(function (choice) { return config.valueComparer(choice.value, value); });
@@ -4433,12 +4457,12 @@ var Choices = /** @class */ (function () {
4433
4457
  }
4434
4458
  if (!config.duplicateItemsAllowed) {
4435
4459
  canAddItem = false;
4436
- notice = resolveNoticeFunction(config.uniqueItemText, value);
4460
+ notice = resolveNoticeFunction(config.uniqueItemText, value, undefined);
4437
4461
  }
4438
4462
  }
4439
4463
  }
4440
4464
  if (canAddItem) {
4441
- notice = resolveNoticeFunction(config.addItemText, value);
4465
+ notice = resolveNoticeFunction(config.addItemText, value, undefined);
4442
4466
  }
4443
4467
  if (notice) {
4444
4468
  this._displayNotice(notice, NoticeTypes.addChoice);
@@ -4489,6 +4513,7 @@ var Choices = /** @class */ (function () {
4489
4513
  var documentElement = this._docRoot;
4490
4514
  var outerElement = this.containerOuter.element;
4491
4515
  var inputElement = this.input.element;
4516
+ var passedElement = this.passedElement.element;
4492
4517
  // capture events - can cancel event processing or propagation
4493
4518
  documentElement.addEventListener('touchend', this._onTouchEnd, true);
4494
4519
  outerElement.addEventListener('keydown', this._onKeyDown, true);
@@ -4526,12 +4551,21 @@ var Choices = /** @class */ (function () {
4526
4551
  passive: true,
4527
4552
  });
4528
4553
  }
4554
+ if (passedElement.hasAttribute('required')) {
4555
+ passedElement.addEventListener('change', this._onChange, {
4556
+ passive: true,
4557
+ });
4558
+ passedElement.addEventListener('invalid', this._onInvalid, {
4559
+ passive: true,
4560
+ });
4561
+ }
4529
4562
  this.input.addEventListeners();
4530
4563
  };
4531
4564
  Choices.prototype._removeEventListeners = function () {
4532
4565
  var documentElement = this._docRoot;
4533
4566
  var outerElement = this.containerOuter.element;
4534
4567
  var inputElement = this.input.element;
4568
+ var passedElement = this.passedElement.element;
4535
4569
  documentElement.removeEventListener('touchend', this._onTouchEnd, true);
4536
4570
  outerElement.removeEventListener('keydown', this._onKeyDown, true);
4537
4571
  outerElement.removeEventListener('mousedown', this._onMouseDown, true);
@@ -4549,6 +4583,10 @@ var Choices = /** @class */ (function () {
4549
4583
  if (inputElement.form) {
4550
4584
  inputElement.form.removeEventListener('reset', this._onFormReset);
4551
4585
  }
4586
+ if (passedElement.hasAttribute('required')) {
4587
+ passedElement.removeEventListener('change', this._onChange);
4588
+ passedElement.removeEventListener('invalid', this._onInvalid);
4589
+ }
4552
4590
  this.input.removeEventListeners();
4553
4591
  };
4554
4592
  Choices.prototype._onKeyDown = function (event) {
@@ -4798,7 +4836,7 @@ var Choices = /** @class */ (function () {
4798
4836
  */
4799
4837
  Choices.prototype._onMouseDown = function (event) {
4800
4838
  var target = event.target;
4801
- if (!(target instanceof HTMLElement)) {
4839
+ if (!(target instanceof Element)) {
4802
4840
  return;
4803
4841
  }
4804
4842
  // If we have our mouse down on the scrollbar and are on IE11...
@@ -4907,7 +4945,7 @@ var Choices = /** @class */ (function () {
4907
4945
  // Remove the focus state when the past outerContainer was the target
4908
4946
  containerOuter.removeFocusState();
4909
4947
  // Also close the dropdown if search is disabled
4910
- if (!this._canSearch) {
4948
+ if (!this.config.searchEnabled) {
4911
4949
  this.hideDropdown(true);
4912
4950
  }
4913
4951
  }
@@ -4931,13 +4969,19 @@ var Choices = /** @class */ (function () {
4931
4969
  }
4932
4970
  });
4933
4971
  };
4934
- Choices.prototype._highlightChoice = function (el) {
4935
- if (el === void 0) { el = null; }
4936
- var choices = Array.from(this.dropdown.element.querySelectorAll(selectableChoiceIdentifier));
4937
- if (!choices.length) {
4972
+ Choices.prototype._onChange = function (event) {
4973
+ if (!event.target.checkValidity()) {
4938
4974
  return;
4939
4975
  }
4940
- var passedEl = el;
4976
+ this.containerOuter.removeInvalidState();
4977
+ };
4978
+ Choices.prototype._onInvalid = function () {
4979
+ this.containerOuter.addInvalidState();
4980
+ };
4981
+ /**
4982
+ * Removes any highlighted choice options
4983
+ */
4984
+ Choices.prototype._removeHighlightedChoices = function () {
4941
4985
  var highlightedState = this.config.classNames.highlightedState;
4942
4986
  var highlightedChoices = Array.from(this.dropdown.element.querySelectorAll(getClassNamesSelector(highlightedState)));
4943
4987
  // Remove any highlighted choices
@@ -4945,6 +4989,16 @@ var Choices = /** @class */ (function () {
4945
4989
  removeClassesFromElement(choice, highlightedState);
4946
4990
  choice.setAttribute('aria-selected', 'false');
4947
4991
  });
4992
+ };
4993
+ Choices.prototype._highlightChoice = function (el) {
4994
+ if (el === void 0) { el = null; }
4995
+ var choices = Array.from(this.dropdown.element.querySelectorAll(selectableChoiceIdentifier));
4996
+ if (!choices.length) {
4997
+ return;
4998
+ }
4999
+ var passedEl = el;
5000
+ var highlightedState = this.config.classNames.highlightedState;
5001
+ this._removeHighlightedChoices();
4948
5002
  if (passedEl) {
4949
5003
  this._highlightPosition = choices.indexOf(passedEl);
4950
5004
  }
@@ -4985,9 +5039,10 @@ var Choices = /** @class */ (function () {
4985
5039
  }
4986
5040
  this._store.dispatch(addItem(item));
4987
5041
  if (withEvents) {
4988
- this.passedElement.triggerEvent(EventType.addItem, this._getChoiceForOutput(item));
5042
+ var eventChoice = getChoiceForOutput(item);
5043
+ this.passedElement.triggerEvent(EventType.addItem, eventChoice);
4989
5044
  if (userTriggered) {
4990
- this.passedElement.triggerEvent(EventType.choice, this._getChoiceForOutput(item));
5045
+ this.passedElement.triggerEvent(EventType.choice, eventChoice);
4991
5046
  }
4992
5047
  }
4993
5048
  };
@@ -5000,7 +5055,7 @@ var Choices = /** @class */ (function () {
5000
5055
  if (notice && notice.type === NoticeTypes.noChoices) {
5001
5056
  this._clearNotice();
5002
5057
  }
5003
- this.passedElement.triggerEvent(EventType.removeItem, this._getChoiceForOutput(item));
5058
+ this.passedElement.triggerEvent(EventType.removeItem, getChoiceForOutput(item));
5004
5059
  };
5005
5060
  Choices.prototype._addChoice = function (choice, withEvents, userTriggered) {
5006
5061
  if (withEvents === void 0) { withEvents = true; }
@@ -5115,25 +5170,25 @@ var Choices = /** @class */ (function () {
5115
5170
  containerInner.wrap(passedElement.element);
5116
5171
  // Wrapper inner container with outer container
5117
5172
  containerOuter.wrap(containerInner.element);
5173
+ containerOuter.element.appendChild(containerInner.element);
5174
+ containerOuter.element.appendChild(dropdownElement);
5175
+ containerInner.element.appendChild(this.itemList.element);
5176
+ dropdownElement.appendChild(this.choiceList.element);
5118
5177
  if (this._isSelectOneElement) {
5119
5178
  this.input.placeholder = this.config.searchPlaceholderValue || '';
5179
+ if (this.config.searchEnabled) {
5180
+ dropdownElement.insertBefore(this.input.element, dropdownElement.firstChild);
5181
+ }
5120
5182
  }
5121
5183
  else {
5184
+ if (!this._isSelectMultipleElement || this.config.searchEnabled) {
5185
+ containerInner.element.appendChild(this.input.element);
5186
+ }
5122
5187
  if (this._placeholderValue) {
5123
5188
  this.input.placeholder = this._placeholderValue;
5124
5189
  }
5125
5190
  this.input.setWidth();
5126
5191
  }
5127
- containerOuter.element.appendChild(containerInner.element);
5128
- containerOuter.element.appendChild(dropdownElement);
5129
- containerInner.element.appendChild(this.itemList.element);
5130
- dropdownElement.appendChild(this.choiceList.element);
5131
- if (!this._isSelectOneElement) {
5132
- containerInner.element.appendChild(this.input.element);
5133
- }
5134
- else if (this.config.searchEnabled) {
5135
- dropdownElement.insertBefore(this.input.element, dropdownElement.firstChild);
5136
- }
5137
5192
  this._highlightPosition = 0;
5138
5193
  this._isSearching = false;
5139
5194
  };
@@ -5215,7 +5270,7 @@ var Choices = /** @class */ (function () {
5215
5270
  throw new TypeError("".concat(caller, " called for an element which has multiple instances of Choices initialised on it"));
5216
5271
  }
5217
5272
  };
5218
- Choices.version = '11.1.0';
5273
+ Choices.version = '11.2.1';
5219
5274
  return Choices;
5220
5275
  }());
5221
5276