@aurodesignsystem-dev/auro-formkit 0.0.0-pr1576.7 → 0.0.0-pr1577.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 (51) hide show
  1. package/components/checkbox/demo/customize.min.js +1 -1
  2. package/components/checkbox/demo/getting-started.min.js +1 -1
  3. package/components/checkbox/demo/index.min.js +1 -1
  4. package/components/checkbox/dist/index.js +1 -1
  5. package/components/checkbox/dist/registered.js +1 -1
  6. package/components/combobox/demo/customize.md +0 -40
  7. package/components/combobox/demo/customize.min.js +65 -359
  8. package/components/combobox/demo/getting-started.min.js +65 -359
  9. package/components/combobox/demo/index.min.js +65 -359
  10. package/components/combobox/dist/index.js +38 -56
  11. package/components/combobox/dist/registered.js +38 -56
  12. package/components/counter/demo/customize.min.js +11 -2
  13. package/components/counter/demo/index.min.js +11 -2
  14. package/components/counter/dist/index.js +11 -2
  15. package/components/counter/dist/registered.js +11 -2
  16. package/components/datepicker/demo/customize.min.js +12 -3
  17. package/components/datepicker/demo/index.min.js +12 -3
  18. package/components/datepicker/dist/index.js +12 -3
  19. package/components/datepicker/dist/registered.js +12 -3
  20. package/components/dropdown/demo/customize.min.js +10 -1
  21. package/components/dropdown/demo/getting-started.min.js +10 -1
  22. package/components/dropdown/demo/index.min.js +10 -1
  23. package/components/dropdown/dist/index.js +10 -1
  24. package/components/dropdown/dist/registered.js +10 -1
  25. package/components/form/demo/customize.min.js +102 -369
  26. package/components/form/demo/getting-started.min.js +102 -369
  27. package/components/form/demo/index.min.js +102 -369
  28. package/components/form/demo/registerDemoDeps.min.js +102 -369
  29. package/components/input/demo/customize.min.js +1 -1
  30. package/components/input/demo/getting-started.min.js +1 -1
  31. package/components/input/demo/index.min.js +1 -1
  32. package/components/input/dist/index.js +1 -1
  33. package/components/input/dist/registered.js +1 -1
  34. package/components/menu/demo/index.min.js +27 -303
  35. package/components/menu/dist/auro-menu-utils.d.ts +0 -30
  36. package/components/menu/dist/auro-menu.d.ts +0 -23
  37. package/components/menu/dist/index.js +27 -303
  38. package/components/menu/dist/registered.js +27 -303
  39. package/components/radio/demo/customize.min.js +1 -1
  40. package/components/radio/demo/getting-started.min.js +1 -1
  41. package/components/radio/demo/index.min.js +1 -1
  42. package/components/radio/dist/index.js +1 -1
  43. package/components/radio/dist/registered.js +1 -1
  44. package/components/select/demo/customize.md +0 -72
  45. package/components/select/demo/customize.min.js +38 -305
  46. package/components/select/demo/getting-started.min.js +38 -305
  47. package/components/select/demo/index.min.js +38 -305
  48. package/components/select/dist/index.js +11 -2
  49. package/components/select/dist/registered.js +11 -2
  50. package/custom-elements.json +1511 -1614
  51. package/package.json +1 -1
@@ -238,107 +238,6 @@ function isSelectableByValue(option) {
238
238
  !option.hasAttribute('static');
239
239
  }
240
240
 
241
- /* eslint-disable no-underscore-dangle */
242
- /**
243
- * Resolves the single selected option for a given `value`, preferring the
244
- * option tracked by `selectedKey` (a user-initiated selection) over a
245
- * first-by-value match. When multiple options share the same `value`, matching
246
- * by `value` alone cannot distinguish which one the user picked; the key
247
- * disambiguates it.
248
- *
249
- * The key is trusted only when it still resolves to an option whose `value`
250
- * matches the requested `value`. If the key is stale (option removed) or the
251
- * value was changed programmatically, resolution falls back to value matching —
252
- * preserving backward-compatible behavior for preselection and `selectByValue`.
253
- * @private
254
- * @param {Array<HTMLElement>} items - The menu's flat option list.
255
- * @param {string} value - The value to resolve.
256
- * @param {string|undefined} selectedKey - The `_optionKey` of the user-selected option, if any.
257
- * @returns {HTMLElement|undefined} The resolved option, or undefined when none match.
258
- */
259
- function resolveSelectedOption(items, value, selectedKey) {
260
- if (!items) {
261
- return undefined;
262
- }
263
-
264
- if (selectedKey !== undefined) {
265
- const keyed = items.find((item) => item._optionKey === selectedKey);
266
- if (keyed && isSelectableByValue(keyed) && keyed.value === value) {
267
- return keyed;
268
- }
269
- // Key exists but the option is gone or its value no longer matches — fall
270
- // through to value-based matching.
271
- }
272
-
273
- return items.find((item) => isSelectableByValue(item) && item.value === value);
274
- }
275
-
276
- /**
277
- * Resolves the selected options for a multi-select `value` array, preferring
278
- * options tracked by `selectedKeys` (user-initiated selections) and falling
279
- * back to value matching for any values not resolved by key. The result is
280
- * always sorted into DOM order regardless of selection sequence.
281
- * @private
282
- * @param {Array<HTMLElement>} items - The menu's flat option list.
283
- * @param {Array<string>} valueArray - The selected values.
284
- * @param {Array<string>|undefined} selectedKeys - The `_optionKey`s of the user-selected options, if any.
285
- * @returns {Array<HTMLElement>} The resolved options in DOM order.
286
- */
287
- function resolveSelectedOptions(items, valueArray, selectedKeys) {
288
- if (!items) {
289
- return [];
290
- }
291
-
292
- const resolved = [];
293
-
294
- // Track how many of each value are still available to resolve. A value that
295
- // appears N times in `valueArray` may be satisfied at most N times total across
296
- // the key pass and the value fallback below — matching by count, not presence,
297
- // on BOTH passes. This stops a duplicate value from being over-resolved: e.g.
298
- // two keyed options that both carry `SEA` cannot both match a single requested
299
- // `SEA` (which happens when `value` is set directly without clearing
300
- // `_selectedKey`, so more keys survive than the value set now asks for).
301
- const remaining = new Map();
302
- valueArray.forEach((val) => remaining.set(val, (remaining.get(val) || 0) + 1));
303
-
304
- // Resolve by key first: trust a key only when its option is still selectable
305
- // and there is still an unmatched occurrence of its value in the request set.
306
- if (Array.isArray(selectedKeys)) {
307
- selectedKeys.forEach((key) => {
308
- const keyed = items.find((item) => item._optionKey === key);
309
- if (keyed && isSelectableByValue(keyed) && (remaining.get(keyed.value) || 0) > 0 && !resolved.includes(keyed)) {
310
- resolved.push(keyed);
311
- remaining.set(keyed.value, remaining.get(keyed.value) - 1);
312
- }
313
- });
314
- }
315
-
316
- // Fall back to value matching for the occurrences not resolved by key. Iterate
317
- // the leftover per-value counts so a value that appears twice but was only
318
- // resolved once by key still matches its remaining occurrence(s).
319
- remaining.forEach((count, val) => {
320
- for (let occurrence = 0; occurrence < count; occurrence += 1) {
321
- const option = items.find((item) => isSelectableByValue(item) && item.value === val && !resolved.includes(item));
322
- if (option) {
323
- resolved.push(option);
324
- }
325
- }
326
- });
327
-
328
- // Always return in DOM order so display is consistent regardless of the order
329
- // keys/values were selected. Every resolved option came from `items`, so an
330
- // O(1) index lookup mirrors `_sortSelectedByDomOrder` and avoids the O(n)
331
- // `items.indexOf` per comparison for large combobox option sets.
332
- const indexMap = new Map(items.map((item, index) => [
333
- item,
334
- index
335
- ]));
336
- resolved.sort((optionA, optionB) => indexMap.get(optionA) - indexMap.get(optionB));
337
-
338
- return resolved;
339
- }
340
- /* eslint-enable no-underscore-dangle */
341
-
342
241
  /**
343
242
  * Helper method to dispatch custom events.
344
243
  * @param {HTMLElement} element - Element to dispatch event from.
@@ -364,14 +263,6 @@ function dispatchMenuEvent(element, eventName, detail = null) {
364
263
  // See LICENSE in the project root for license information.
365
264
 
366
265
 
367
- /**
368
- * Monotonically increasing counter used to give each menu instance a unique
369
- * `_menuInstanceId` prefix. Auto-generating the id (rather than using a random
370
- * string) keeps option keys deterministic and collision-free across menus.
371
- * @private
372
- */
373
- let menuInstanceIdCounter = 0;
374
-
375
266
 
376
267
  /**
377
268
  * The `auro-menu` element provides users a way to select from a list of options.
@@ -443,8 +334,9 @@ class AuroMenu extends AuroElement {
443
334
 
444
335
  // Instance properties (non-reactive)
445
336
 
446
- menuInstanceIdCounter += 1;
447
-
337
+ /**
338
+ * @private
339
+ */
448
340
  Object.assign(this, {
449
341
  // Root-level menu (true) or a nested submenu (false)
450
342
  rootMenu: true,
@@ -454,21 +346,6 @@ class AuroMenu extends AuroElement {
454
346
  nestingSpacer: '<span class="nestingSpacer"></span>',
455
347
  // Loading indicator for slot elements
456
348
  loadingSlots: null,
457
- // Unique id for this menu instance; prefixes every auto-generated option
458
- // key so keys never collide across menus in the same document.
459
- _menuInstanceId: `menu-${menuInstanceIdCounter}`,
460
- // Monotonically increasing counter for option key generation. Never
461
- // resets, so a key is never reused within this instance's lifetime.
462
- _optionKeyCounter: 0,
463
- // Key(s) of the option(s) the user has actively selected. A single string
464
- // in single-select, an array in multi-select, undefined when nothing is
465
- // user-selected. Used to disambiguate options that share a `value`.
466
- _selectedKey: undefined,
467
- // True only for the one updated() cycle following a user selection, so
468
- // reconciliation trusts `_selectedKey`. A `value` change from a consumer's
469
- // direct property assignment leaves this false, dropping the stale key so
470
- // reconciliation falls back to first-by-value (see updated()).
471
- _valueChangeFromSelection: false,
472
349
  });
473
350
  }
474
351
 
@@ -688,13 +565,6 @@ class AuroMenu extends AuroElement {
688
565
  return;
689
566
  }
690
567
 
691
- // A programmatic value set carries no positional intent, so drop any
692
- // `_selectedKey` left over from a prior user click. This makes reconciliation
693
- // in updated() fall back to first-by-value (single) / value-in-DOM-order
694
- // (multi), matching the documented contract for programmatic selection even
695
- // when a stale key would still resolve to a duplicate-value option.
696
- this._selectedKey = undefined;
697
-
698
568
  // `value` is a String property; stringify arrays so attribute reflection and `formattedValue` parsing stay correct.
699
569
  this.value = Array.isArray(value) ? JSON.stringify(value) : value;
700
570
  }
@@ -742,17 +612,6 @@ class AuroMenu extends AuroElement {
742
612
  updated(changedProperties) {
743
613
  super.updated(changedProperties);
744
614
 
745
- // Consume the selection-driven flag for THIS cycle up front. Clearing it
746
- // unconditionally — not only inside the `value` branch below — prevents it
747
- // from lingering `true` when a selection produces a serialized `value`
748
- // byte-identical to the current one, in which case Lit schedules no
749
- // `value`-change cycle to consume it. A lingering flag would misclassify a
750
- // later consumer's programmatic `value` set as selection-driven and keep a
751
- // stale `_selectedKey`. The reconcile path below re-sets the instance flag
752
- // after this point, so its intentional cross-cycle hand-off still works.
753
- const valueChangeFromSelection = this._valueChangeFromSelection;
754
- this._valueChangeFromSelection = false;
755
-
756
615
  // Single source of truth for 'auroMenu-selectedOption'. Selection handlers
757
616
  // mutate optionSelected and let Lit's update cycle dispatch here; the prior
758
617
  // .value comparison missed multi-select array changes and combined with the
@@ -776,17 +635,6 @@ class AuroMenu extends AuroElement {
776
635
  this.initItems();
777
636
  }
778
637
 
779
- // Distinguish a selection-driven `value` change (a user click, which set
780
- // the flag in handleSelectState / _sortSelectedByDomOrder) from a
781
- // programmatic assignment by a consumer. A programmatic set carries no
782
- // positional intent, so drop any leftover `_selectedKey` and let
783
- // reconciliation fall back to first-by-value (single) / value-in-DOM-order
784
- // (multi) — the same contract selectByValue() guarantees, even when a
785
- // stale key would otherwise still resolve to a duplicate-value option.
786
- if (!valueChangeFromSelection) {
787
- this._selectedKey = undefined;
788
- }
789
-
790
638
  // Set when reconciliation reassigns `value` below. That reassignment schedules a
791
639
  // second updated() cycle, so the `event`-attribute dispatch is deferred to that
792
640
  // cycle to avoid firing option custom events twice on the same selection.
@@ -804,55 +652,19 @@ class AuroMenu extends AuroElement {
804
652
  // Defensive default: `formattedValue` can be undefined for unexpected value types,
805
653
  // and calling `.includes` on undefined would throw during reconciliation.
806
654
  const valueArray = this.formattedValue || [];
807
- // Resolve by key first (the user's exact picks), then fall back to
808
- // value matching for any values not resolved by key — so pre-selection
809
- // and programmatic value sets keep working. Result is DOM-ordered.
810
- const matchingOptions = resolveSelectedOptions(this.items, valueArray, this._selectedKey);
655
+ const matchingOptions = this.items ? this.items.filter((item) => isSelectableByValue(item) && valueArray.includes(item.value)) : [];
811
656
  newSelected = matchingOptions.length > 0 ? matchingOptions : undefined;
812
657
 
813
- // Reconcile `value` with the selectable set. An occurrence is dropped
814
- // only when it is loaded but no selectable option can satisfy it —
815
- // every loaded item sharing that value is non-selectable, or the value
816
- // recurs more often than it has selectable options (a duplicate value
817
- // whose extra siblings are disabled/static). This is count-based, not
818
- // presence-based, so an enabled option is kept even when a disabled
819
- // sibling shares its value — mirroring how `resolveSelectedOptions`
820
- // resolves the same set. Entries with no matching item yet are
821
- // preserved so async preselection still works, and the toggle handlers
822
- // rebuild `value` from `formattedValue`, so a rejected entry cannot
823
- // resurface on the next select/deselect.
824
- const selectableByValue = new Map();
825
- const loadedValues = new Set();
826
- if (this.items) {
827
- this.items.forEach((item) => {
828
- loadedValues.add(item.value);
829
- if (isSelectableByValue(item)) {
830
- selectableByValue.set(item.value, (selectableByValue.get(item.value) || 0) + 1);
831
- }
832
- });
833
- }
834
-
835
- const reconciled = valueArray.filter((val) => {
836
- // Not loaded yet (async preselection) — keep for a later cycle.
837
- if (!loadedValues.has(val)) {
838
- return true;
839
- }
840
- // Consume one selectable option per occurrence; drop once exhausted.
841
- const remaining = selectableByValue.get(val) || 0;
842
- if (remaining > 0) {
843
- selectableByValue.set(val, remaining - 1);
844
- return true;
845
- }
846
- return false;
847
- });
848
-
849
- if (reconciled.length !== valueArray.length) {
850
- // This is an internal correction, not a consumer's programmatic set,
851
- // so preserve the selection-driven flag through the re-entrant
852
- // updated() cycle it schedules. Otherwise that cycle would treat the
853
- // reassignment as programmatic and drop `_selectedKey` mid-cascade,
854
- // flipping resolution and looping.
855
- this._valueChangeFromSelection = true;
658
+ // Reconcile `value` with the selectable set. Drop only entries whose option is
659
+ // loaded but non-selectable (disabled/static) — leaving them would desync `value`
660
+ // from `optionSelected`, and the toggle handlers rebuild `value` from `formattedValue`,
661
+ // so the rejected entry would resurface on the next select/deselect. Entries with no
662
+ // matching item yet are preserved so async preselection still works once options render.
663
+ const rejectedValues = this.items
664
+ ? this.items.filter((item) => !isSelectableByValue(item) && valueArray.includes(item.value)).map((item) => item.value)
665
+ : [];
666
+ if (rejectedValues.length > 0) {
667
+ const reconciled = valueArray.filter((val) => !rejectedValues.includes(val));
856
668
  this.value = serializeMultiSelectValue(reconciled);
857
669
  valueReconciled = true;
858
670
  }
@@ -864,11 +676,7 @@ class AuroMenu extends AuroElement {
864
676
  // `hidden` is intentionally NOT excluded: the combobox toggles
865
677
  // `hidden` as its type-ahead filter, so a filtered-out option is
866
678
  // still a valid programmatic selection.
867
- // Prefer the option the user actually selected (tracked by
868
- // `_selectedKey`) so a click on the second of two options sharing a
869
- // `value` resolves back to that exact element instead of the first
870
- // value match. Falls back to first-by-value for programmatic sets.
871
- const matchingOption = resolveSelectedOption(this.items, this.value, this._selectedKey);
679
+ const matchingOption = this.items ? this.items.find((item) => isSelectableByValue(item) && item.value === this.value) : undefined;
872
680
 
873
681
  if (matchingOption) {
874
682
  newSelected = matchingOption;
@@ -1096,14 +904,6 @@ class AuroMenu extends AuroElement {
1096
904
  }
1097
905
  });
1098
906
 
1099
- // Assign private keys once items are populated. Only the root menu assigns
1100
- // keys: its `items` is a deep query that already includes nested submenu
1101
- // options, so a single pass keys the entire tree. Nested menus skip this
1102
- // and inherit keys from the root.
1103
- if (this.rootMenu) {
1104
- this._assignOptionKeys();
1105
- }
1106
-
1107
907
  if (this.noCheckmark) {
1108
908
  this.updateItemsState(new Map([
1109
909
  [
@@ -1120,31 +920,6 @@ class AuroMenu extends AuroElement {
1120
920
  }));
1121
921
  }
1122
922
 
1123
- /**
1124
- * Assigns a private, auto-generated unique key (`_optionKey`) to each menu
1125
- * option that does not already have one. Keys are internal state on the
1126
- * element instance — never reflected as an attribute or exposed publicly —
1127
- * and let selection tracking distinguish options that share the same `value`.
1128
- *
1129
- * The `_optionKey === undefined` guard makes this idempotent: options keep the
1130
- * key they were first assigned across re-renders and slot changes, and if a
1131
- * nested menu's lifecycle runs a pass before the root, options simply wait for
1132
- * the root to key them (or keep whatever key they already hold).
1133
- * @private
1134
- */
1135
- _assignOptionKeys() {
1136
- if (!this.items) {
1137
- return;
1138
- }
1139
-
1140
- this.items.forEach((option) => {
1141
- if (option._optionKey === undefined) {
1142
- this._optionKeyCounter += 1;
1143
- option._optionKey = `${this._menuInstanceId}-${this._optionKeyCounter}`;
1144
- }
1145
- });
1146
- }
1147
-
1148
923
  // Logic Methods
1149
924
 
1150
925
  /**
@@ -1154,28 +929,24 @@ class AuroMenu extends AuroElement {
1154
929
  */
1155
930
  handleSelectState(option) {
1156
931
  if (this.multiSelect) {
932
+ const currentValue = this.formattedValue || [];
1157
933
  const currentSelected = this.optionSelected || [];
1158
934
 
935
+ if (!currentValue.includes(option.value)) {
936
+ this.value = serializeMultiSelectValue([
937
+ ...currentValue,
938
+ option.value
939
+ ]);
940
+ }
1159
941
  if (!currentSelected.includes(option)) {
1160
942
  this.optionSelected = [
1161
943
  ...currentSelected,
1162
944
  option
1163
945
  ];
1164
946
  }
1165
-
1166
- // Re-sort by DOM order and rebuild `_selectedKey`/`value` from the
1167
- // selected set so display order stays consistent with the menu, not with
1168
- // click order.
1169
- this._sortSelectedByDomOrder();
1170
947
  } else {
1171
948
  this.value = option.value;
1172
949
  this.optionSelected = option;
1173
- // Track the specific option the user selected so the value→option
1174
- // reconciliation in updated() resolves back to this exact element even
1175
- // when another option shares the same `value`.
1176
- this._selectedKey = option._optionKey;
1177
- // Mark this `value` change as selection-driven so updated() trusts the key.
1178
- this._valueChangeFromSelection = true;
1179
950
  }
1180
951
 
1181
952
  this._index = this.items.indexOf(option);
@@ -1188,22 +959,18 @@ class AuroMenu extends AuroElement {
1188
959
  */
1189
960
  handleDeselectState(option) {
1190
961
  if (this.multiSelect) {
1191
- // Remove this exact element from the selection (identity, not value — two
1192
- // options can share a `value`), then rebuild `value`/`_selectedKey` from
1193
- // the remaining set in DOM order. An empty result collapses to undefined.
1194
- this.optionSelected = this.optionSelected.filter((selected) => selected !== option);
962
+ // Remove this option from array; an empty result collapses `value` to undefined.
963
+ const newFormattedValue = (this.formattedValue || []).filter((val) => val !== option.value);
964
+ this.value = serializeMultiSelectValue(newFormattedValue);
965
+
966
+ this.optionSelected = this.optionSelected.filter((val) => val !== option);
1195
967
  if (this.optionSelected.length === 0) {
1196
968
  this.optionSelected = undefined;
1197
- this._selectedKey = undefined;
1198
- this.value = undefined;
1199
- } else {
1200
- this._sortSelectedByDomOrder();
1201
969
  }
1202
970
  } else {
1203
971
  // For single-select: Back to undefined when deselected
1204
972
  this.value = undefined;
1205
973
  this.optionSelected = undefined;
1206
- this._selectedKey = undefined;
1207
974
  }
1208
975
 
1209
976
  // Update the index tracking
@@ -1227,38 +994,9 @@ class AuroMenu extends AuroElement {
1227
994
  clearSelection() {
1228
995
  this.optionSelected = undefined;
1229
996
  this.value = undefined;
1230
- this._selectedKey = undefined;
1231
997
  this._index = -1;
1232
998
  }
1233
999
 
1234
- /**
1235
- * Re-sorts the multi-select selection into DOM order and rebuilds the derived
1236
- * `_selectedKey` and `value` from `optionSelected`. Selection is always stored
1237
- * and serialized in the order options appear in the menu, never in click
1238
- * order — so selecting C then A yields `[A, C]`.
1239
- * @private
1240
- */
1241
- _sortSelectedByDomOrder() {
1242
- if (!this.multiSelect || !Array.isArray(this.optionSelected) || !this.items) {
1243
- return;
1244
- }
1245
-
1246
- const indexMap = new Map(this.items.map((item, index) => [
1247
- item,
1248
- index
1249
- ]));
1250
-
1251
- // Sort any element no longer in `items` (a stale selection left over from a
1252
- // dynamic rebuild that the consumer has not cleared) to the END rather than
1253
- // the front, so it never displaces a live option to the head of the
1254
- // serialized order. Value reconciliation drops it on the next updated() cycle.
1255
- this.optionSelected.sort((optionA, optionB) => (indexMap.get(optionA) ?? this.items.length) - (indexMap.get(optionB) ?? this.items.length));
1256
- this._selectedKey = this.optionSelected.map((option) => option._optionKey);
1257
- this.value = serializeMultiSelectValue(this.optionSelected.map((option) => option.value));
1258
- // Mark this `value` change as selection-driven so updated() trusts the keys.
1259
- this._valueChangeFromSelection = true;
1260
- }
1261
-
1262
1000
  /**
1263
1001
  * Resets the menu to its initial state.
1264
1002
  * This is the only way to return value to undefined.
@@ -1268,7 +1006,6 @@ class AuroMenu extends AuroElement {
1268
1006
  // Reset to undefined - initial state
1269
1007
  this.value = undefined;
1270
1008
  this.optionSelected = undefined;
1271
- this._selectedKey = undefined;
1272
1009
  this._index = -1;
1273
1010
 
1274
1011
  // Clear active option state so a follow-up open/navigation starts fresh
@@ -1330,19 +1067,6 @@ class AuroMenu extends AuroElement {
1330
1067
  this.initItems();
1331
1068
  }
1332
1069
 
1333
- // Recover `_index` from the highlighted option when it has been reset to -1.
1334
- // In multi-select, deselecting the last remaining option collapses the value
1335
- // to undefined, and the updated() reconciliation resets `_index = -1` even
1336
- // though `optionActive` still points at the highlighted option. Without this,
1337
- // reading `items[-1]` returns undefined and the re-select no-ops until the
1338
- // highlight is moved away and back. Mirrors auro-combobox's reconcileMenuIndex.
1339
- if (this._index < 0 && this.optionActive && this.items) {
1340
- const activeIndex = this.items.indexOf(this.optionActive);
1341
- if (activeIndex >= 0) {
1342
- this._index = activeIndex;
1343
- }
1344
- }
1345
-
1346
1070
  // Get currently selected menu option based on index
1347
1071
  const option = this.items ? this.items[this._index] : undefined;
1348
1072
 
@@ -1227,7 +1227,7 @@ class AuroHelpText extends i$2 {
1227
1227
  }
1228
1228
  }
1229
1229
 
1230
- var formkitVersion = '202608041729';
1230
+ var formkitVersion = '202608041712';
1231
1231
 
1232
1232
  // Copyright (c) Alaska Air. All right reserved. Licensed under the Apache-2.0 license
1233
1233
  // See LICENSE in the project root for license information.
@@ -1227,7 +1227,7 @@ class AuroHelpText extends i$2 {
1227
1227
  }
1228
1228
  }
1229
1229
 
1230
- var formkitVersion = '202608041729';
1230
+ var formkitVersion = '202608041712';
1231
1231
 
1232
1232
  // Copyright (c) Alaska Air. All right reserved. Licensed under the Apache-2.0 license
1233
1233
  // See LICENSE in the project root for license information.
@@ -1227,7 +1227,7 @@ class AuroHelpText extends i$2 {
1227
1227
  }
1228
1228
  }
1229
1229
 
1230
- var formkitVersion = '202608041729';
1230
+ var formkitVersion = '202608041712';
1231
1231
 
1232
1232
  // Copyright (c) Alaska Air. All right reserved. Licensed under the Apache-2.0 license
1233
1233
  // See LICENSE in the project root for license information.
@@ -1166,7 +1166,7 @@ class AuroHelpText extends LitElement {
1166
1166
  }
1167
1167
  }
1168
1168
 
1169
- var formkitVersion = '202608041729';
1169
+ var formkitVersion = '202608041712';
1170
1170
 
1171
1171
  // Copyright (c) Alaska Air. All right reserved. Licensed under the Apache-2.0 license
1172
1172
  // See LICENSE in the project root for license information.
@@ -1166,7 +1166,7 @@ class AuroHelpText extends LitElement {
1166
1166
  }
1167
1167
  }
1168
1168
 
1169
- var formkitVersion = '202608041729';
1169
+ var formkitVersion = '202608041712';
1170
1170
 
1171
1171
  // Copyright (c) Alaska Air. All right reserved. Licensed under the Apache-2.0 license
1172
1172
  // See LICENSE in the project root for license information.
@@ -33,7 +33,6 @@
33
33
  <auro-anchorlink fluid href="#noValidate" class="level2 body-xs">No Validation</auro-anchorlink>
34
34
  <auro-anchorlink fluid href="#placeholder" class="level2 body-xs">Placeholder</auro-anchorlink>
35
35
  <auro-anchorlink fluid href="#loading" class="level2 body-xs">Loading</auro-anchorlink>
36
- <auro-anchorlink fluid href="#nonUniqueValues" class="level2 body-xs">Non-Unique Option Values</auro-anchorlink>
37
36
  </auro-nav>
38
37
  </nav>
39
38
  <div class="mainContent">
@@ -1298,77 +1297,6 @@
1298
1297
  &lt;/auro-select&gt;</code></pre>
1299
1298
  <!-- AURO-GENERATED-CONTENT:END -->
1300
1299
  </auro-accordion>
1301
- <auro-header level="3" id="nonUniqueValues">Non-Unique Option Values</auro-header>
1302
- <p>Two or more <code>auro-menuoption</code> elements may share the same <code>value</code>. This is common when the <code>value</code> represents a coarser grouping than the option label &mdash; for example, several airports that all serve the same city. The component tracks the specific option a user selects, so the correct label is displayed even when the underlying <code>value</code> is duplicated.</p>
1303
- <div class="exampleWrapper">
1304
- <!-- AURO-GENERATED-CONTENT:START (FILE:src=./../apiExamples/duplicate-values.html) -->
1305
- <!-- The below content is automatically added from ./../apiExamples/duplicate-values.html -->
1306
- <auro-select>
1307
- <span slot="ariaLabel.bib.close">Close Popup</span>
1308
- <span slot="bib.fullscreen.headline">Choose an airport</span>
1309
- <span slot="label">Departure airport</span>
1310
- <auro-menu>
1311
- <auro-menuoption value="seattle">Seattle&ndash;Tacoma International (SEA)</auro-menuoption>
1312
- <auro-menuoption value="seattle">Seattle Paine Field (PAE)</auro-menuoption>
1313
- <auro-menuoption value="portland">Portland International (PDX)</auro-menuoption>
1314
- <auro-menuoption value="spokane">Spokane International (GEG)</auro-menuoption>
1315
- </auro-menu>
1316
- </auro-select>
1317
- <!-- AURO-GENERATED-CONTENT:END -->
1318
- </div>
1319
- <auro-accordion alignRight>
1320
- <span slot="trigger">See code</span>
1321
- <!-- AURO-GENERATED-CONTENT:START (CODE:src=./../apiExamples/duplicate-values.html) -->
1322
- <!-- The below code snippet is automatically added from ./../apiExamples/duplicate-values.html -->
1323
- <pre class="language-html"><code class="language-html">&lt;auro-select&gt;
1324
- &lt;span slot="ariaLabel.bib.close"&gt;Close Popup&lt;/span&gt;
1325
- &lt;span slot="bib.fullscreen.headline"&gt;Choose an airport&lt;/span&gt;
1326
- &lt;span slot="label"&gt;Departure airport&lt;/span&gt;
1327
- &lt;auro-menu&gt;
1328
- &lt;auro-menuoption value="seattle"&gt;Seattle&amp;ndash;Tacoma International (SEA)&lt;/auro-menuoption&gt;
1329
- &lt;auro-menuoption value="seattle"&gt;Seattle Paine Field (PAE)&lt;/auro-menuoption&gt;
1330
- &lt;auro-menuoption value="portland"&gt;Portland International (PDX)&lt;/auro-menuoption&gt;
1331
- &lt;auro-menuoption value="spokane"&gt;Spokane International (GEG)&lt;/auro-menuoption&gt;
1332
- &lt;/auro-menu&gt;
1333
- &lt;/auro-select&gt;</code></pre>
1334
- <!-- AURO-GENERATED-CONTENT:END -->
1335
- </auro-accordion>
1336
- <p>In <code>multiselect</code> mode, options that share a <code>value</code> are tracked independently, so each can be selected and removed on its own. Selections are stored in DOM order regardless of the order in which they were chosen.</p>
1337
- <div class="exampleWrapper">
1338
- <!-- AURO-GENERATED-CONTENT:START (FILE:src=./../apiExamples/duplicate-values-multiselect.html) -->
1339
- <!-- The below content is automatically added from ./../apiExamples/duplicate-values-multiselect.html -->
1340
- <auro-select multiselect>
1341
- <span slot="ariaLabel.bib.close">Close Popup</span>
1342
- <span slot="bib.fullscreen.headline">Choose airports</span>
1343
- <label slot="placeholder">Select one or more airports</label>
1344
- <span slot="label">Airports served</span>
1345
- <auro-menu>
1346
- <auro-menuoption value="seattle">Seattle&ndash;Tacoma International (SEA)</auro-menuoption>
1347
- <auro-menuoption value="seattle">Seattle Paine Field (PAE)</auro-menuoption>
1348
- <auro-menuoption value="portland">Portland International (PDX)</auro-menuoption>
1349
- <auro-menuoption value="spokane">Spokane International (GEG)</auro-menuoption>
1350
- </auro-menu>
1351
- </auro-select>
1352
- <!-- AURO-GENERATED-CONTENT:END -->
1353
- </div>
1354
- <auro-accordion alignRight>
1355
- <span slot="trigger">See code</span>
1356
- <!-- AURO-GENERATED-CONTENT:START (CODE:src=./../apiExamples/duplicate-values-multiselect.html) -->
1357
- <!-- The below code snippet is automatically added from ./../apiExamples/duplicate-values-multiselect.html -->
1358
- <pre class="language-html"><code class="language-html">&lt;auro-select multiselect&gt;
1359
- &lt;span slot="ariaLabel.bib.close"&gt;Close Popup&lt;/span&gt;
1360
- &lt;span slot="bib.fullscreen.headline"&gt;Choose airports&lt;/span&gt;
1361
- &lt;label slot="placeholder"&gt;Select one or more airports&lt;/label&gt;
1362
- &lt;span slot="label"&gt;Airports served&lt;/span&gt;
1363
- &lt;auro-menu&gt;
1364
- &lt;auro-menuoption value="seattle"&gt;Seattle&amp;ndash;Tacoma International (SEA)&lt;/auro-menuoption&gt;
1365
- &lt;auro-menuoption value="seattle"&gt;Seattle Paine Field (PAE)&lt;/auro-menuoption&gt;
1366
- &lt;auro-menuoption value="portland"&gt;Portland International (PDX)&lt;/auro-menuoption&gt;
1367
- &lt;auro-menuoption value="spokane"&gt;Spokane International (GEG)&lt;/auro-menuoption&gt;
1368
- &lt;/auro-menu&gt;
1369
- &lt;/auro-select&gt;</code></pre>
1370
- <!-- AURO-GENERATED-CONTENT:END -->
1371
- </auro-accordion>
1372
1300
  </section>
1373
1301
  </div>
1374
1302
  </div>