@aurodesignsystem-dev/auro-formkit 0.0.0-pr1431.3 → 0.0.0-pr1433.1

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 (43) hide show
  1. package/components/checkbox/demo/api.min.js +1 -1
  2. package/components/checkbox/demo/index.min.js +1 -1
  3. package/components/checkbox/dist/index.js +1 -1
  4. package/components/checkbox/dist/registered.js +1 -1
  5. package/components/combobox/demo/api.min.js +230 -44
  6. package/components/combobox/demo/index.min.js +230 -44
  7. package/components/combobox/dist/auro-combobox copy.d.ts +578 -0
  8. package/components/combobox/dist/auro-combobox.d.ts +4 -0
  9. package/components/combobox/dist/index.js +142 -22
  10. package/components/combobox/dist/registered.js +142 -22
  11. package/components/counter/demo/api.min.js +30 -2
  12. package/components/counter/demo/index.min.js +30 -2
  13. package/components/counter/dist/index.js +30 -2
  14. package/components/counter/dist/registered.js +30 -2
  15. package/components/datepicker/demo/api.min.js +33 -3
  16. package/components/datepicker/demo/index.min.js +33 -3
  17. package/components/datepicker/dist/index.js +33 -3
  18. package/components/datepicker/dist/registered.js +33 -3
  19. package/components/dropdown/demo/api.min.js +29 -1
  20. package/components/dropdown/demo/index.min.js +29 -1
  21. package/components/dropdown/dist/index.js +29 -1
  22. package/components/dropdown/dist/keyboardUtils.d.ts +18 -0
  23. package/components/dropdown/dist/registered.js +29 -1
  24. package/components/form/demo/api.min.js +326 -54
  25. package/components/form/demo/index.min.js +326 -54
  26. package/components/input/demo/api.min.js +1 -1
  27. package/components/input/demo/index.min.js +1 -1
  28. package/components/input/dist/index.js +1 -1
  29. package/components/input/dist/registered.js +1 -1
  30. package/components/menu/demo/api.min.js +88 -22
  31. package/components/menu/demo/index.min.js +88 -22
  32. package/components/menu/dist/index.js +88 -22
  33. package/components/menu/dist/registered.js +88 -22
  34. package/components/radio/demo/api.min.js +1 -1
  35. package/components/radio/demo/index.min.js +1 -1
  36. package/components/radio/dist/index.js +1 -1
  37. package/components/radio/dist/registered.js +1 -1
  38. package/components/select/demo/api.min.js +118 -24
  39. package/components/select/demo/index.min.js +118 -24
  40. package/components/select/dist/index.js +30 -2
  41. package/components/select/dist/registered.js +30 -2
  42. package/custom-elements.json +1906 -1897
  43. package/package.json +3 -3
@@ -1687,7 +1687,7 @@ class AuroHelpText extends i$2 {
1687
1687
  }
1688
1688
  }
1689
1689
 
1690
- var formkitVersion = '202604091453';
1690
+ var formkitVersion = '202604101700';
1691
1691
 
1692
1692
  // Copyright (c) 2026 Alaska Airlines. All rights reserved. Licensed under the Apache-2.0 license
1693
1693
  // See LICENSE in the project root for license information.
@@ -1679,7 +1679,7 @@ class AuroHelpText extends i$2 {
1679
1679
  }
1680
1680
  }
1681
1681
 
1682
- var formkitVersion = '202604091453';
1682
+ var formkitVersion = '202604101700';
1683
1683
 
1684
1684
  // Copyright (c) 2026 Alaska Airlines. All rights reserved. Licensed under the Apache-2.0 license
1685
1685
  // See LICENSE in the project root for license information.
@@ -1632,7 +1632,7 @@ class AuroHelpText extends LitElement {
1632
1632
  }
1633
1633
  }
1634
1634
 
1635
- var formkitVersion = '202604091453';
1635
+ var formkitVersion = '202604101700';
1636
1636
 
1637
1637
  // Copyright (c) 2026 Alaska Airlines. All rights reserved. Licensed under the Apache-2.0 license
1638
1638
  // See LICENSE in the project root for license information.
@@ -1632,7 +1632,7 @@ class AuroHelpText extends LitElement {
1632
1632
  }
1633
1633
  }
1634
1634
 
1635
- var formkitVersion = '202604091453';
1635
+ var formkitVersion = '202604101700';
1636
1636
 
1637
1637
  // Copyright (c) 2026 Alaska Airlines. All rights reserved. Licensed under the Apache-2.0 license
1638
1638
  // See LICENSE in the project root for license information.
@@ -3294,6 +3294,7 @@ class AuroFloatingUI {
3294
3294
  this.focusHandler = null;
3295
3295
  this.clickHandler = null;
3296
3296
  this.keyDownHandler = null;
3297
+ this.touchHandler = null;
3297
3298
 
3298
3299
  /**
3299
3300
  * @private
@@ -3711,6 +3712,28 @@ class AuroFloatingUI {
3711
3712
  setTimeout(() => {
3712
3713
  window.addEventListener("click", this.clickHandler);
3713
3714
  }, 0);
3715
+
3716
+ // iOS Safari does not fire `click` on non-interactive elements, so
3717
+ // tapping an inert backdrop never reaches the click handler above.
3718
+ // Mirror the same outside-tap logic with a passive touchstart listener.
3719
+ this.touchHandler = (evt) => {
3720
+ const element = this.element;
3721
+ if (!element?.bib) {
3722
+ return;
3723
+ }
3724
+
3725
+ // fullscreen (modal) dialog handles its own dismissal
3726
+ if (element.bib.hasAttribute("isfullscreen")) {
3727
+ return;
3728
+ }
3729
+
3730
+ const path = evt.composedPath();
3731
+ if (!path.includes(element.trigger) && !path.includes(element.bib)) {
3732
+ this.hideBib("click");
3733
+ }
3734
+ };
3735
+
3736
+ window.addEventListener("touchstart", this.touchHandler, { passive: true });
3714
3737
  }
3715
3738
 
3716
3739
  cleanupHideHandlers() {
@@ -3726,6 +3749,11 @@ class AuroFloatingUI {
3726
3749
  this.clickHandler = null;
3727
3750
  }
3728
3751
 
3752
+ if (this.touchHandler) {
3753
+ window.removeEventListener("touchstart", this.touchHandler);
3754
+ this.touchHandler = null;
3755
+ }
3756
+
3729
3757
  if (this.keyDownHandler) {
3730
3758
  document.removeEventListener("keydown", this.keyDownHandler);
3731
3759
  this.keyDownHandler = null;
@@ -5200,7 +5228,7 @@ let AuroHelpText$2 = class AuroHelpText extends i$4 {
5200
5228
  }
5201
5229
  };
5202
5230
 
5203
- var formkitVersion$2 = '202604091453';
5231
+ var formkitVersion$2 = '202604101700';
5204
5232
 
5205
5233
  let AuroElement$2 = class AuroElement extends i$4 {
5206
5234
  static get properties() {
@@ -12964,7 +12992,7 @@ let AuroHelpText$1 = class AuroHelpText extends i$4 {
12964
12992
  }
12965
12993
  };
12966
12994
 
12967
- var formkitVersion$1 = '202604091453';
12995
+ var formkitVersion$1 = '202604101700';
12968
12996
 
12969
12997
  // Copyright (c) 2025 Alaska Airlines. All right reserved. Licensed under the Apache-2.0 license
12970
12998
  // See LICENSE in the project root for license information.
@@ -14029,11 +14057,11 @@ class AuroBibtemplate extends i$4 {
14029
14057
  }
14030
14058
  }
14031
14059
 
14032
- var formkitVersion = '202604091453';
14060
+ var formkitVersion = '202604101700';
14033
14061
 
14034
14062
  var styleCss$3 = i$7`.util_displayInline{display:inline}.util_displayInlineBlock{display:inline-block}.util_displayBlock{display:block}.util_displayFlex{display:flex}.util_displayHidden{display:none}.util_displayHiddenVisually{position:absolute;overflow:hidden;clip:rect(1px, 1px, 1px, 1px);width:1px;height:1px;padding:0;border:0}:host{display:block;text-align:left}:host [auro-dropdown]{--ds-auro-dropdown-trigger-background-color: transparent}:host #inputInBib::part(wrapper){box-shadow:none}:host #inputInBib::part(accent-left){display:none}:host([layout*=classic]) [auro-input]{width:100%}:host([layout*=classic]) [auro-input]::part(helpText){display:none}:host([layout*=classic]) #slotHolder{display:none}`;
14035
14063
 
14036
- var styleEmphasizedCss = i$7`:host([layout*=emphasized][shape*=pill]) [auro-input]{--ds-auro-input-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843));--ds-auro-input-container-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout*=emphasized][shape*=pill]) [auro-input]:hover{--ds-auro-input-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843));--ds-auro-input-container-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout*=emphasized][shape*=pill]) [auro-input]{width:100%}:host([layout*=emphasized][shape*=pill]) [auro-input]::part(inputHelpText){display:none}:host([layout=emphasized]) [auro-dropdown]{--ds-auro-dropdown-trigger-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout=emphasized]) [auro-dropdown]:hover{--ds-auro-dropdown-trigger-hover-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout=emphasized]) [auro-dropdown][layout*=emphasized]::part(wrapper){--ds-auro-dropdown-trigger-background-color: transparent}`;
14064
+ var styleEmphasizedCss = i$7`:host([layout*=emphasized][shape*=pill]) [auro-input][slot=trigger]{--ds-auro-input-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843));--ds-auro-input-container-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout*=emphasized][shape*=pill]) [auro-input][slot=trigger]:hover{--ds-auro-input-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843));--ds-auro-input-container-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout*=emphasized][shape*=pill]) [auro-input][slot=trigger]{width:100%}:host([layout*=emphasized][shape*=pill]) [auro-input][slot=trigger]::part(inputHelpText){display:none}:host([layout=emphasized]) [auro-dropdown]{--ds-auro-dropdown-trigger-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout=emphasized]) [auro-dropdown]:hover{--ds-auro-dropdown-trigger-hover-background-color: var(--ds-advanced-color-dropdown-emphasized-background, rgba(0, 39, 74, 0.1019607843))}:host([layout=emphasized]) [auro-dropdown][layout*=emphasized]::part(wrapper){--ds-auro-dropdown-trigger-background-color: transparent}`;
14037
14065
 
14038
14066
  var styleSnowflakeCss = i$7`:host([layout*=snowflake][shape*=snowflake]) [auro-input]{width:100%}:host([layout*=snowflake][shape*=snowflake]) [auro-input]::part(inputHelpText){display:none}:host([layout*=snowflake][shape*=snowflake])::part(helpText){text-align:center}`;
14039
14067
 
@@ -14991,14 +15019,18 @@ class AuroCombobox extends AuroElement {
14991
15019
  /**
14992
15020
  * Update displayValue or input.value, it's called when making a selection.
14993
15021
  * @param {string} label - The label of the selected option.
15022
+ * @param {object} [options={}] - Optional display update settings.
15023
+ * @param {boolean} [options.force=false] - Force display sync while focused.
14994
15024
  * @private
14995
15025
  */
14996
- updateTriggerTextDisplay(label) {
15026
+ updateTriggerTextDisplay(label, options = {}) {
15027
+ const { force = false } = options;
15028
+
14997
15029
  // update the input content if persistInput is false
14998
15030
  // in suggestion mode, do not override input value if no selection has been made and the input currently has focus
14999
15031
  const isInputFocusedWithNoSelection = !this.menu.value && (this.input.matches(':focus-within') || (this.inputInBib && this.inputInBib.matches(':focus-within')));
15000
15032
 
15001
- if (!this.persistInput && !(this.behavior === 'suggestion' && isInputFocusedWithNoSelection)) {
15033
+ if (!this.persistInput && (force || !(this.behavior === 'suggestion' && isInputFocusedWithNoSelection))) {
15002
15034
  this.input.value = label || this.value;
15003
15035
  }
15004
15036
 
@@ -15075,6 +15107,13 @@ class AuroCombobox extends AuroElement {
15075
15107
  * @returns {void}
15076
15108
  */
15077
15109
  showBib() {
15110
+ // Do not auto-open from programmatic value/option updates when the
15111
+ // combobox is not focused. User-driven interactions still open normally
15112
+ // once focus enters the component.
15113
+ // if (!this.componentHasFocus && !this.dropdown.isPopoverVisible) {
15114
+ // return;
15115
+ // }
15116
+
15078
15117
  if (!this.input.value && !this.dropdown.isBibFullscreen) {
15079
15118
  this.dropdown.hide();
15080
15119
  return;
@@ -15363,6 +15402,25 @@ class AuroCombobox extends AuroElement {
15363
15402
 
15364
15403
  // Handle menu option selection like select does
15365
15404
  this.menu.addEventListener('auroMenu-selectedOption', (event) => {
15405
+ const hasMatchingOptionForValue =
15406
+ typeof this.value === 'string' &&
15407
+ this.value.length > 0 &&
15408
+ this.menu && Array.isArray(this.menu.options) &&
15409
+ this.menu.options.some((opt) => opt.value === this.value);
15410
+
15411
+ const isInitNoMatch = event.detail && event.detail.reason === 'no-match' &&
15412
+ this.menu && this.menu.options && this.menu.options.length === 0 &&
15413
+ typeof this.value === 'string' &&
15414
+ this.value.length > 0;
15415
+
15416
+ const isTransientProgrammaticNoMatch = event.detail && event.detail.reason === 'no-match' &&
15417
+ this._suppressNextEmptyInputClear &&
15418
+ hasMatchingOptionForValue;
15419
+
15420
+ if (isInitNoMatch || isTransientProgrammaticNoMatch) {
15421
+ return;
15422
+ }
15423
+
15366
15424
  // Update the optionSelected from the event details, not manually
15367
15425
  [this.optionSelected] = event.detail.options;
15368
15426
 
@@ -15538,7 +15596,18 @@ class AuroCombobox extends AuroElement {
15538
15596
  }
15539
15597
 
15540
15598
  if (!this.input.value) {
15541
- this.clear();
15599
+ const hasCommittedValue = typeof this.value === 'string' && this.value.length > 0;
15600
+ const hasCommittedSelection = Boolean(this.menu && this.menu.optionSelected);
15601
+ const isBlurSideEffect = !this.componentHasFocus && !this.dropdownOpen;
15602
+ const isTransientEmptyInputEvent = this._suppressNextEmptyInputClear && (!event || !event.detail || event.detail.value === null || event.detail.value === undefined);
15603
+
15604
+ // Preserve a committed value when an empty input event is emitted as a
15605
+ // side effect of focus leaving the combobox (e.g., clicking a swap
15606
+ // control between two comboboxes). User-driven empty input while focused
15607
+ // should still clear as before.
15608
+ if (!(isTransientEmptyInputEvent || (isBlurSideEffect && hasCommittedValue && hasCommittedSelection))) {
15609
+ this.clear();
15610
+ }
15542
15611
  }
15543
15612
  this.handleMenuOptions();
15544
15613
 
@@ -15721,6 +15790,19 @@ class AuroCombobox extends AuroElement {
15721
15790
  }
15722
15791
 
15723
15792
  updated(changedProperties) {
15793
+ if (changedProperties.has('typedValue')) {
15794
+ const nextTypedValue = this.typedValue === null || this.typedValue === undefined ? '' : this.typedValue;
15795
+ if (this.input && this.input.value !== nextTypedValue) {
15796
+ this.input.value = nextTypedValue;
15797
+ }
15798
+ if (this.inputInBib && this.inputInBib.value !== nextTypedValue) {
15799
+ this.inputInBib.value = nextTypedValue;
15800
+ }
15801
+ if (this.menu) {
15802
+ this.menu.matchWord = normalizeFilterValue(nextTypedValue);
15803
+ }
15804
+ }
15805
+
15724
15806
  // After the component is ready, send direct value changes to auro-menu.
15725
15807
  if (changedProperties.has('value')) {
15726
15808
  if (this.value && this.value.length > 0) {
@@ -15748,6 +15830,19 @@ class AuroCombobox extends AuroElement {
15748
15830
  this.clear();
15749
15831
  }
15750
15832
  }
15833
+
15834
+ // Keep trigger text synced after value/menu state has settled. Force the
15835
+ // update so external programmatic swaps reflect immediately in the UI
15836
+ // even if the input still technically holds focus during the same tick.
15837
+ if (this.value) {
15838
+ const selectedOption = this.menu && this.menu.optionSelected;
15839
+ const hasMatchingSelectedOption = selectedOption && selectedOption.value === this.value;
15840
+ const selectedOptionLabel = (selectedOption && selectedOption.getAttribute('label')) || (selectedOption && selectedOption.textContent ? selectedOption.textContent.trim() : undefined);
15841
+ const nextDisplayLabel = hasMatchingSelectedOption ? (selectedOptionLabel || this.value) : this.value;
15842
+
15843
+ this.updateTriggerTextDisplay(nextDisplayLabel, { force: true });
15844
+ }
15845
+
15751
15846
  if (this.value && !this.componentHasFocus) {
15752
15847
  // If the value got set programmatically make sure we hide the bib
15753
15848
  // when input is not taking the focus (input can be in dropdown.trigger or in bibtemplate)
@@ -15759,22 +15854,47 @@ class AuroCombobox extends AuroElement {
15759
15854
  this.menu.matchWord = normalizeFilterValue(this.input.value);
15760
15855
  }
15761
15856
 
15762
- this.dispatchEvent(new CustomEvent('input', {
15763
- bubbles: true,
15764
- cancelable: false,
15765
- composed: true,
15766
- detail: {
15767
- optionSelected: this.menu.optionSelected,
15768
- value: this.menu.value
15769
- }
15770
- }));
15857
+ // Only dispatch 'input' when the value transition is meaningful — at least one
15858
+ // of old/new must be a non-empty string. Skipping the event when both are
15859
+ // empty/undefined prevents a feedback loop during SPA navigation where Lit's
15860
+ // initial update cycle fires before the parent framework (e.g. Svelte) has
15861
+ // had a chance to set the preselected value as a property. Without this
15862
+ // guard the event arrives with el.value === undefined, the surrounding
15863
+ // framework reads it as '' and writes that back, permanently obscuring the
15864
+ // intended preselected value.
15865
+ const _oldValue = changedProperties.get('value');
15866
+ const _oldIsNonEmpty = typeof _oldValue === 'string' && _oldValue.length > 0;
15867
+ const _newIsNonEmpty = typeof this.value === 'string' && this.value.length > 0;
15868
+
15869
+ if (_newIsNonEmpty && this.menu && Array.isArray(this.menu.options) && this.menu.options.some((opt) => opt.value === this.value)) {
15870
+ this._suppressNextEmptyInputClear = true;
15871
+ clearTimeout(this._suppressNextEmptyInputClearTimeout);
15872
+ const suppressNextEmptyInputClearDelay = 300;
15873
+ this._suppressNextEmptyInputClearTimeout = setTimeout(() => {
15874
+ this._suppressNextEmptyInputClear = false;
15875
+ }, suppressNextEmptyInputClearDelay);
15876
+ } else {
15877
+ this._suppressNextEmptyInputClear = false;
15878
+ }
15771
15879
 
15772
- // Deprecated, need to be removed.
15773
- this.dispatchEvent(new CustomEvent('auroCombobox-valueSet', {
15774
- bubbles: true,
15775
- cancelable: false,
15776
- composed: true,
15777
- }));
15880
+ if (_oldIsNonEmpty || _newIsNonEmpty) {
15881
+ this.dispatchEvent(new CustomEvent('input', {
15882
+ bubbles: true,
15883
+ cancelable: false,
15884
+ composed: true,
15885
+ detail: {
15886
+ optionSelected: this.menu.optionSelected,
15887
+ value: this.menu.value
15888
+ }
15889
+ }));
15890
+
15891
+ // Deprecated, need to be removed.
15892
+ this.dispatchEvent(new CustomEvent('auroCombobox-valueSet', {
15893
+ bubbles: true,
15894
+ cancelable: false,
15895
+ composed: true,
15896
+ }));
15897
+ }
15778
15898
  }
15779
15899
 
15780
15900
  if (changedProperties.has('availableOptions')) {
@@ -16353,7 +16473,7 @@ class AuroMenuOption extends AuroElement {
16353
16473
  this.setAttribute('aria-selected', this.selected.toString());
16354
16474
 
16355
16475
  // Update menu service selection state if this isn't an internal update
16356
- if (this.internalUpdateInProgress !== true) {
16476
+ if (this.internalUpdateInProgress !== true && this.menuService) {
16357
16477
  this.menuService[this.selected ? 'selectOption' : 'deselectOption'](this);
16358
16478
  }
16359
16479
  }
@@ -16388,9 +16508,10 @@ class AuroMenuOption extends AuroElement {
16388
16508
  }
16389
16509
 
16390
16510
  disconnectedCallback() {
16391
- if (this.menuService) {
16392
- this.menuService.unsubscribe(this.handleMenuChange);
16393
- this.menuService.removeMenuOption(this);
16511
+ const { menuService } = this;
16512
+ if (menuService) {
16513
+ menuService.unsubscribe(this.handleMenuChange);
16514
+ menuService.removeMenuOption(this);
16394
16515
  }
16395
16516
  }
16396
16517
 
@@ -16559,9 +16680,11 @@ class AuroMenuOption extends AuroElement {
16559
16680
  * @private
16560
16681
  */
16561
16682
  handleMouseEnter() {
16562
- if (!this.disabled) {
16563
- this.menuService.setHighlightedOption(this);
16683
+ const { menuService } = this;
16684
+ if (!menuService || this.disabled) {
16685
+ return;
16564
16686
  }
16687
+ menuService.setHighlightedOption(this);
16565
16688
  }
16566
16689
 
16567
16690
  /**
@@ -16965,10 +17088,15 @@ class MenuService {
16965
17088
  return;
16966
17089
  }
16967
17090
 
17091
+ const before = this.selectedOptions || [];
16968
17092
  const optionsSet = new Set(optionsToDeselect);
16969
- this.selectedOptions = (this.selectedOptions || [])
16970
- .filter(opt => !optionsSet.has(opt));
17093
+ const after = before.filter(opt => !optionsSet.has(opt));
17094
+
17095
+ if (this.optionsArraysMatch(after, before)) {
17096
+ return;
17097
+ }
16971
17098
 
17099
+ this.selectedOptions = after;
16972
17100
  this.stageUpdate();
16973
17101
  }
16974
17102
 
@@ -17064,6 +17192,16 @@ class MenuService {
17064
17192
  return;
17065
17193
  }
17066
17194
 
17195
+ const hostValue = this.host && this.host.value;
17196
+ const hostHasValue = hostValue !== undefined &&
17197
+ hostValue !== null &&
17198
+ (!Array.isArray(hostValue) || hostValue.length > 0) &&
17199
+ (typeof hostValue !== 'string' || hostValue.trim() !== '');
17200
+
17201
+ if (hostHasValue && this._pendingValue != null) {
17202
+ return;
17203
+ }
17204
+
17067
17205
  this.clearPendingValue();
17068
17206
 
17069
17207
  if (this.selectedOptions.length > 0) {
@@ -17244,6 +17382,9 @@ class MenuService {
17244
17382
  this.notify({ type: 'optionsChange', options: this._menuOptions });
17245
17383
 
17246
17384
  if (this._pendingValue != null) {
17385
+ // Reset the retry count so a new option registration gives a fresh
17386
+ // budget — the initial retries fired before delayed options arrived.
17387
+ this._pendingRetryCount = 0;
17247
17388
  this.queuePendingValue(this._pendingValue);
17248
17389
  }
17249
17390
  }
@@ -17588,7 +17729,11 @@ class AuroMenu extends AuroElement {
17588
17729
  * @returns {string} - Returns the label of the currently selected option(s).
17589
17730
  */
17590
17731
  get currentLabel() {
17591
- return this.menuService.currentLabel;
17732
+ const { menuService } = this;
17733
+ if (!menuService) {
17734
+ return '';
17735
+ }
17736
+ return menuService.currentLabel;
17592
17737
  };
17593
17738
 
17594
17739
  /**
@@ -17611,7 +17756,12 @@ class AuroMenu extends AuroElement {
17611
17756
  * @param {number} value - Sets the index of the currently active option.
17612
17757
  */
17613
17758
  set index(value) {
17614
- this.menuService.setHighlightedIndex(value);
17759
+ const { menuService } = this;
17760
+ if (!menuService) {
17761
+ return;
17762
+ }
17763
+
17764
+ menuService.setHighlightedIndex(value);
17615
17765
  }
17616
17766
 
17617
17767
  /**
@@ -17633,7 +17783,11 @@ class AuroMenu extends AuroElement {
17633
17783
  * @returns {String|Array<String>}
17634
17784
  */
17635
17785
  get formattedValue() {
17636
- return this.menuService.currentValue;
17786
+ const { menuService } = this;
17787
+ if (!menuService) {
17788
+ return '';
17789
+ }
17790
+ return menuService.currentValue;
17637
17791
  }
17638
17792
 
17639
17793
  /**
@@ -17677,7 +17831,11 @@ class AuroMenu extends AuroElement {
17677
17831
  * @param {HTMLElement} option - The option to set as active.
17678
17832
  */
17679
17833
  updateActiveOption(option) {
17680
- this.menuService.setHighlightedOption(option);
17834
+ const { menuService } = this;
17835
+ if (!menuService) {
17836
+ return;
17837
+ }
17838
+ menuService.setHighlightedOption(option);
17681
17839
  }
17682
17840
 
17683
17841
  /**
@@ -17705,7 +17863,8 @@ class AuroMenu extends AuroElement {
17705
17863
  if (event.type === 'valueChange') {
17706
17864
 
17707
17865
  // New option is array value or first option with fallback to undefined for empty array in all cases
17708
- const newOption = this.multiSelect && event.options.length ? event.options : event.options[0] || undefined;
17866
+ const options = event.options || [];
17867
+ const newOption = this.multiSelect && options.length ? options : options[0] || undefined;
17709
17868
  const newValue = event.stringValue;
17710
17869
 
17711
17870
  // Check if the option or value has actually changed
@@ -17714,8 +17873,11 @@ class AuroMenu extends AuroElement {
17714
17873
  this.setInternalValue(newValue);
17715
17874
  }
17716
17875
 
17717
- // Notify components of selection change
17718
- this.notifySelectionChange(event);
17876
+ // Notify components of selection change (pass normalized options to avoid undefined iterability errors)
17877
+ this.notifySelectionChange({
17878
+ ...event,
17879
+ options
17880
+ });
17719
17881
  }
17720
17882
 
17721
17883
  if (event.type === 'highlightChange') {
@@ -17738,7 +17900,11 @@ class AuroMenu extends AuroElement {
17738
17900
  * @returns {Array<HTMLElement>}
17739
17901
  */
17740
17902
  get selectedOptions() {
17741
- return this.menuService ? this.menuService.selectedOptions : [];
17903
+ const { menuService } = this;
17904
+ if (!menuService) {
17905
+ return [];
17906
+ }
17907
+ return menuService.selectedOptions;
17742
17908
  }
17743
17909
 
17744
17910
  /**
@@ -17746,7 +17912,11 @@ class AuroMenu extends AuroElement {
17746
17912
  * @returns {HTMLElement|null}
17747
17913
  */
17748
17914
  get selectedOption() {
17749
- return this.menuService ? this.menuService.selectedOptions[0] : null;
17915
+ const { menuService } = this;
17916
+ if (!menuService) {
17917
+ return null;
17918
+ }
17919
+ return menuService.selectedOptions[0] || null;
17750
17920
  }
17751
17921
 
17752
17922
  // Lifecycle Methods
@@ -17790,7 +17960,11 @@ class AuroMenu extends AuroElement {
17790
17960
  // keys are not yet resolved (framework mount-order race), selectByValue
17791
17961
  // queues a bounded retry automatically via queuePendingValue.
17792
17962
  if (changedProperties.has('value') && !this.internalUpdateInProgress) {
17793
- this.menuService.selectByValue(this.value);
17963
+ const { menuService } = this;
17964
+ if (!menuService) {
17965
+ return;
17966
+ }
17967
+ menuService.selectByValue(this.value);
17794
17968
  }
17795
17969
 
17796
17970
  // Handle loading state changes
@@ -17855,7 +18029,11 @@ class AuroMenu extends AuroElement {
17855
18029
  * @protected
17856
18030
  */
17857
18031
  makeSelection() {
17858
- this.menuService.selectHighlightedOption();
18032
+ const { menuService } = this;
18033
+ if (!menuService) {
18034
+ return;
18035
+ }
18036
+ menuService.selectHighlightedOption();
17859
18037
  }
17860
18038
 
17861
18039
  /**
@@ -17874,7 +18052,11 @@ class AuroMenu extends AuroElement {
17874
18052
  * @public
17875
18053
  */
17876
18054
  reset() {
17877
- this.menuService.reset();
18055
+ const { menuService } = this;
18056
+ if (!menuService) {
18057
+ return;
18058
+ }
18059
+ menuService.reset();
17878
18060
 
17879
18061
  // Dispatch reset event
17880
18062
  dispatchMenuEvent(this, 'auroMenu-selectValueReset');
@@ -17909,10 +18091,14 @@ class AuroMenu extends AuroElement {
17909
18091
  * @protected
17910
18092
  */
17911
18093
  navigateOptions(direction) {
18094
+ const { menuService } = this;
18095
+ if (!menuService) {
18096
+ return;
18097
+ }
17912
18098
  if (direction === 'up') {
17913
- this.menuService.highlightPrevious();
18099
+ menuService.highlightPrevious();
17914
18100
  } else if (direction === 'down') {
17915
- this.menuService.highlightNext();
18101
+ menuService.highlightNext();
17916
18102
  }
17917
18103
  }
17918
18104