@ni/nimble-components 21.4.0 → 21.5.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.
- package/dist/all-components-bundle.js +864 -73
- package/dist/all-components-bundle.js.map +1 -1
- package/dist/all-components-bundle.min.js +3598 -3450
- package/dist/all-components-bundle.min.js.map +1 -1
- package/dist/esm/anchored-region/styles.js +6 -1
- package/dist/esm/anchored-region/styles.js.map +1 -1
- package/dist/esm/label-provider/core/index.d.ts +6 -0
- package/dist/esm/label-provider/core/index.js +10 -2
- package/dist/esm/label-provider/core/index.js.map +1 -1
- package/dist/esm/label-provider/core/label-token-defaults.js +3 -1
- package/dist/esm/label-provider/core/label-token-defaults.js.map +1 -1
- package/dist/esm/label-provider/core/label-tokens.d.ts +2 -0
- package/dist/esm/label-provider/core/label-tokens.js +8 -0
- package/dist/esm/label-provider/core/label-tokens.js.map +1 -1
- package/dist/esm/patterns/dropdown/styles.js +0 -4
- package/dist/esm/patterns/dropdown/styles.js.map +1 -1
- package/dist/esm/select/index.d.ts +251 -7
- package/dist/esm/select/index.js +653 -19
- package/dist/esm/select/index.js.map +1 -1
- package/dist/esm/select/models/select-form-associated.d.ts +16 -0
- package/dist/esm/select/models/select-form-associated.js +19 -0
- package/dist/esm/select/models/select-form-associated.js.map +1 -0
- package/dist/esm/select/styles.js +89 -1
- package/dist/esm/select/styles.js.map +1 -1
- package/dist/esm/select/template.js +71 -37
- package/dist/esm/select/template.js.map +1 -1
- package/dist/esm/select/testing/select.pageobject.d.ts +32 -0
- package/dist/esm/select/testing/select.pageobject.js +128 -0
- package/dist/esm/select/testing/select.pageobject.js.map +1 -0
- package/dist/esm/select/types.d.ts +9 -0
- package/dist/esm/select/types.js +8 -0
- package/dist/esm/select/types.js.map +1 -1
- package/package.json +4 -1
|
@@ -12570,12 +12570,12 @@
|
|
|
12570
12570
|
*
|
|
12571
12571
|
* @internal
|
|
12572
12572
|
*/
|
|
12573
|
-
class FormAssociatedSelect extends FormAssociated(_Select) {
|
|
12573
|
+
let FormAssociatedSelect$1 = class FormAssociatedSelect extends FormAssociated(_Select) {
|
|
12574
12574
|
constructor() {
|
|
12575
12575
|
super(...arguments);
|
|
12576
12576
|
this.proxy = document.createElement("select");
|
|
12577
12577
|
}
|
|
12578
|
-
}
|
|
12578
|
+
};
|
|
12579
12579
|
|
|
12580
12580
|
/**
|
|
12581
12581
|
* A Select Custom HTML Element.
|
|
@@ -12596,7 +12596,7 @@
|
|
|
12596
12596
|
*
|
|
12597
12597
|
* @public
|
|
12598
12598
|
*/
|
|
12599
|
-
let Select$
|
|
12599
|
+
let Select$2 = class Select extends FormAssociatedSelect$1 {
|
|
12600
12600
|
constructor() {
|
|
12601
12601
|
super(...arguments);
|
|
12602
12602
|
/**
|
|
@@ -13031,22 +13031,22 @@
|
|
|
13031
13031
|
};
|
|
13032
13032
|
__decorate([
|
|
13033
13033
|
attr({ attribute: "open", mode: "boolean" })
|
|
13034
|
-
], Select$
|
|
13034
|
+
], Select$2.prototype, "open", void 0);
|
|
13035
13035
|
__decorate([
|
|
13036
13036
|
volatile
|
|
13037
|
-
], Select$
|
|
13037
|
+
], Select$2.prototype, "collapsible", null);
|
|
13038
13038
|
__decorate([
|
|
13039
13039
|
observable
|
|
13040
|
-
], Select$
|
|
13040
|
+
], Select$2.prototype, "control", void 0);
|
|
13041
13041
|
__decorate([
|
|
13042
13042
|
attr({ attribute: "position" })
|
|
13043
|
-
], Select$
|
|
13043
|
+
], Select$2.prototype, "positionAttribute", void 0);
|
|
13044
13044
|
__decorate([
|
|
13045
13045
|
observable
|
|
13046
|
-
], Select$
|
|
13046
|
+
], Select$2.prototype, "position", void 0);
|
|
13047
13047
|
__decorate([
|
|
13048
13048
|
observable
|
|
13049
|
-
], Select$
|
|
13049
|
+
], Select$2.prototype, "maxHeight", void 0);
|
|
13050
13050
|
/**
|
|
13051
13051
|
* Includes ARIA states and properties relating to the ARIA select role.
|
|
13052
13052
|
*
|
|
@@ -13058,7 +13058,7 @@
|
|
|
13058
13058
|
observable
|
|
13059
13059
|
], DelegatesARIASelect.prototype, "ariaControls", void 0);
|
|
13060
13060
|
applyMixins(DelegatesARIASelect, DelegatesARIAListbox);
|
|
13061
|
-
applyMixins(Select$
|
|
13061
|
+
applyMixins(Select$2, StartEnd, DelegatesARIASelect);
|
|
13062
13062
|
|
|
13063
13063
|
class _Switch extends FoundationElement {
|
|
13064
13064
|
}
|
|
@@ -16301,7 +16301,7 @@
|
|
|
16301
16301
|
|
|
16302
16302
|
/**
|
|
16303
16303
|
* Do not edit directly
|
|
16304
|
-
* Generated on
|
|
16304
|
+
* Generated on Thu, 15 Feb 2024 20:33:21 GMT
|
|
16305
16305
|
*/
|
|
16306
16306
|
|
|
16307
16307
|
const Information100DarkUi = "#a46eff";
|
|
@@ -18576,10 +18576,15 @@
|
|
|
18576
18576
|
|
|
18577
18577
|
const styles$P = css `
|
|
18578
18578
|
:host {
|
|
18579
|
-
|
|
18579
|
+
/* Avoid using the 'display' helper to customize hidden behavior */
|
|
18580
18580
|
display: block;
|
|
18581
|
+
contain: layout;
|
|
18581
18582
|
z-index: ${ZIndexLevels.zIndex1000};
|
|
18582
18583
|
}
|
|
18584
|
+
|
|
18585
|
+
:host([hidden]) {
|
|
18586
|
+
visibility: hidden;
|
|
18587
|
+
}
|
|
18583
18588
|
`;
|
|
18584
18589
|
|
|
18585
18590
|
// When the anchor element changes position on the page, it is the client's responsibility to update the position
|
|
@@ -19730,7 +19735,9 @@
|
|
|
19730
19735
|
numericDecrementLabel: 'Decrement',
|
|
19731
19736
|
errorIconLabel: 'Error',
|
|
19732
19737
|
warningIconLabel: 'Warning',
|
|
19733
|
-
informationIconLabel: 'Information'
|
|
19738
|
+
informationIconLabel: 'Information',
|
|
19739
|
+
filterSearchLabel: 'Search',
|
|
19740
|
+
filterNoResultsLabel: 'No items found'
|
|
19734
19741
|
};
|
|
19735
19742
|
|
|
19736
19743
|
const popupDismissLabel = DesignToken.create({
|
|
@@ -19757,6 +19764,14 @@
|
|
|
19757
19764
|
name: 'information-icon-label',
|
|
19758
19765
|
cssCustomPropertyName: null
|
|
19759
19766
|
}).withDefault(coreLabelDefaults.informationIconLabel);
|
|
19767
|
+
const filterSearchLabel = DesignToken.create({
|
|
19768
|
+
name: 'filter-search-label',
|
|
19769
|
+
cssCustomPropertyName: null
|
|
19770
|
+
}).withDefault(coreLabelDefaults.filterSearchLabel);
|
|
19771
|
+
const filterNoResultsLabel = DesignToken.create({
|
|
19772
|
+
name: 'filter-no-results-label',
|
|
19773
|
+
cssCustomPropertyName: null
|
|
19774
|
+
}).withDefault(coreLabelDefaults.filterNoResultsLabel);
|
|
19760
19775
|
|
|
19761
19776
|
// prettier-ignore
|
|
19762
19777
|
const template$x = html `
|
|
@@ -20643,10 +20658,6 @@
|
|
|
20643
20658
|
border-bottom-color: ${failColor};
|
|
20644
20659
|
}
|
|
20645
20660
|
|
|
20646
|
-
.anchored-region[hidden] {
|
|
20647
|
-
visibility: hidden;
|
|
20648
|
-
}
|
|
20649
|
-
|
|
20650
20661
|
.listbox {
|
|
20651
20662
|
box-sizing: border-box;
|
|
20652
20663
|
display: inline-flex;
|
|
@@ -20793,6 +20804,19 @@
|
|
|
20793
20804
|
}
|
|
20794
20805
|
`;
|
|
20795
20806
|
|
|
20807
|
+
/**
|
|
20808
|
+
* Types of dropdown appearance.
|
|
20809
|
+
* @public
|
|
20810
|
+
*/
|
|
20811
|
+
/**
|
|
20812
|
+
* Types of select filter mode.
|
|
20813
|
+
* @public
|
|
20814
|
+
*/
|
|
20815
|
+
const FilterMode = {
|
|
20816
|
+
none: undefined,
|
|
20817
|
+
standard: 'standard'
|
|
20818
|
+
};
|
|
20819
|
+
|
|
20796
20820
|
const styles$D = css `
|
|
20797
20821
|
${styles$F}
|
|
20798
20822
|
${styles$E}
|
|
@@ -23135,6 +23159,7 @@
|
|
|
23135
23159
|
}
|
|
23136
23160
|
}
|
|
23137
23161
|
registerIcon('icon-magnifying-glass', IconMagnifyingGlass);
|
|
23162
|
+
const iconMagnifyingGlassTag = 'nimble-icon-magnifying-glass';
|
|
23138
23163
|
|
|
23139
23164
|
// AUTO-GENERATED FILE - DO NOT EDIT DIRECTLY
|
|
23140
23165
|
// See generation source in nimble-components/build/generate-icons
|
|
@@ -23920,7 +23945,9 @@
|
|
|
23920
23945
|
numericIncrement: numericIncrementLabel,
|
|
23921
23946
|
errorIcon: errorIconLabel,
|
|
23922
23947
|
warningIcon: warningIconLabel,
|
|
23923
|
-
informationIcon: informationIconLabel
|
|
23948
|
+
informationIcon: informationIconLabel,
|
|
23949
|
+
filterSearch: filterSearchLabel,
|
|
23950
|
+
filterNoResults: filterNoResultsLabel
|
|
23924
23951
|
};
|
|
23925
23952
|
/**
|
|
23926
23953
|
* Core label provider for Nimble
|
|
@@ -23949,6 +23976,12 @@
|
|
|
23949
23976
|
__decorate$1([
|
|
23950
23977
|
attr({ attribute: 'information-icon' })
|
|
23951
23978
|
], LabelProviderCore.prototype, "informationIcon", void 0);
|
|
23979
|
+
__decorate$1([
|
|
23980
|
+
attr({ attribute: 'filter-search' })
|
|
23981
|
+
], LabelProviderCore.prototype, "filterSearch", void 0);
|
|
23982
|
+
__decorate$1([
|
|
23983
|
+
attr({ attribute: 'filter-no-results' })
|
|
23984
|
+
], LabelProviderCore.prototype, "filterNoResults", void 0);
|
|
23952
23985
|
const nimbleLabelProviderCore = LabelProviderCore.compose({
|
|
23953
23986
|
baseName: 'label-provider-core'
|
|
23954
23987
|
});
|
|
@@ -57724,13 +57757,97 @@ img.ProseMirror-separator {
|
|
|
57724
57757
|
[part='end'] {
|
|
57725
57758
|
display: contents;
|
|
57726
57759
|
}
|
|
57760
|
+
|
|
57761
|
+
.listbox {
|
|
57762
|
+
overflow-x: clip;
|
|
57763
|
+
}
|
|
57764
|
+
|
|
57765
|
+
.listbox.empty slot {
|
|
57766
|
+
display: none;
|
|
57767
|
+
}
|
|
57768
|
+
|
|
57769
|
+
.listbox.above {
|
|
57770
|
+
flex-flow: column-reverse;
|
|
57771
|
+
}
|
|
57772
|
+
|
|
57773
|
+
.filter-field {
|
|
57774
|
+
display: flex;
|
|
57775
|
+
flex-direction: row;
|
|
57776
|
+
align-items: center;
|
|
57777
|
+
height: ${controlHeight};
|
|
57778
|
+
background: transparent;
|
|
57779
|
+
}
|
|
57780
|
+
|
|
57781
|
+
.filter-field::before {
|
|
57782
|
+
content: '';
|
|
57783
|
+
position: absolute;
|
|
57784
|
+
height: 0px;
|
|
57785
|
+
border-bottom: rgba(${borderRgbPartialColor}, 0.1) 2px solid;
|
|
57786
|
+
bottom: calc(${controlHeight} + ${smallPadding} - ${borderWidth});
|
|
57787
|
+
}
|
|
57788
|
+
|
|
57789
|
+
.filter-field.above::before {
|
|
57790
|
+
width: calc(100% - (2 * ${borderWidth}));
|
|
57791
|
+
}
|
|
57792
|
+
|
|
57793
|
+
.filter-field::after {
|
|
57794
|
+
content: '';
|
|
57795
|
+
position: absolute;
|
|
57796
|
+
height: 0px;
|
|
57797
|
+
border-bottom: rgba(${borderRgbPartialColor}, 0.1) 2px solid;
|
|
57798
|
+
top: calc(${controlHeight} + ${smallPadding} - ${borderWidth});
|
|
57799
|
+
}
|
|
57800
|
+
|
|
57801
|
+
.filter-field:not(.above)::after {
|
|
57802
|
+
width: calc(100% - (2 * ${borderWidth}));
|
|
57803
|
+
}
|
|
57804
|
+
|
|
57805
|
+
.filter-icon {
|
|
57806
|
+
padding-left: ${smallPadding};
|
|
57807
|
+
}
|
|
57808
|
+
|
|
57809
|
+
.filter-input {
|
|
57810
|
+
background: transparent;
|
|
57811
|
+
border: none;
|
|
57812
|
+
color: inherit;
|
|
57813
|
+
font: inherit;
|
|
57814
|
+
height: var(--ni-nimble-control-height);
|
|
57815
|
+
padding: 0 ${smallPadding} 0 ${mediumPadding};
|
|
57816
|
+
width: 100%;
|
|
57817
|
+
}
|
|
57818
|
+
|
|
57819
|
+
.filter-input::placeholder {
|
|
57820
|
+
color: ${placeholderFontColor};
|
|
57821
|
+
}
|
|
57822
|
+
|
|
57823
|
+
.filter-input${focusVisible} {
|
|
57824
|
+
outline: 0px;
|
|
57825
|
+
}
|
|
57826
|
+
|
|
57827
|
+
.scrollable-region {
|
|
57828
|
+
overflow: auto;
|
|
57829
|
+
}
|
|
57830
|
+
|
|
57831
|
+
.no-results-label {
|
|
57832
|
+
color: ${placeholderFontColor};
|
|
57833
|
+
height: ${controlHeight};
|
|
57834
|
+
display: inline-flex;
|
|
57835
|
+
align-items: center;
|
|
57836
|
+
padding: ${smallPadding} ${mediumPadding};
|
|
57837
|
+
}
|
|
57727
57838
|
`.withBehaviors(appearanceBehavior(DropdownAppearance.block, css `
|
|
57728
57839
|
:host([error-visible]) .control {
|
|
57729
57840
|
border-bottom-width: ${borderWidth};
|
|
57730
57841
|
padding-bottom: 0;
|
|
57731
57842
|
}
|
|
57843
|
+
`), themeBehavior(Theme.color, css `
|
|
57844
|
+
.filter-field,
|
|
57845
|
+
.no-results-label {
|
|
57846
|
+
background: ${hexToRgbaCssColor(White, 0.15)};
|
|
57847
|
+
}
|
|
57732
57848
|
`));
|
|
57733
57849
|
|
|
57850
|
+
/* eslint-disable @typescript-eslint/indent */
|
|
57734
57851
|
// prettier-ignore
|
|
57735
57852
|
const template$l = (context, definition) => html `
|
|
57736
57853
|
<template
|
|
@@ -57739,11 +57856,9 @@ img.ProseMirror-separator {
|
|
|
57739
57856
|
x.collapsible && x.open && 'open',
|
|
57740
57857
|
x.disabled && 'disabled',
|
|
57741
57858
|
x.collapsible && x.position,
|
|
57742
|
-
]
|
|
57743
|
-
|
|
57744
|
-
|
|
57745
|
-
aria-activedescendant="${x => x.ariaActiveDescendant}"
|
|
57746
|
-
aria-controls="${x => x.ariaControls}"
|
|
57859
|
+
].filter(Boolean).join(' ')}"
|
|
57860
|
+
aria-activedescendant="${x => (x.filterMode === FilterMode.none ? x.ariaActiveDescendant : null)}"
|
|
57861
|
+
aria-controls="${x => (x.filterMode === FilterMode.none ? x.ariaControls : null)}"
|
|
57747
57862
|
aria-disabled="${x => x.ariaDisabled}"
|
|
57748
57863
|
aria-expanded="${x => x.ariaExpanded}"
|
|
57749
57864
|
aria-haspopup="${x => (x.collapsible ? 'listbox' : null)}"
|
|
@@ -57752,34 +57867,36 @@ img.ProseMirror-separator {
|
|
|
57752
57867
|
role="combobox"
|
|
57753
57868
|
tabindex="${x => (!x.disabled ? '0' : null)}"
|
|
57754
57869
|
@click="${(x, c) => x.clickHandler(c.event)}"
|
|
57870
|
+
@change="${x => x.changeValueHandler()}"
|
|
57871
|
+
@contentchange="${x => x.updateDisplayValue()}"
|
|
57755
57872
|
@focusin="${(x, c) => x.focusinHandler(c.event)}"
|
|
57756
57873
|
@focusout="${(x, c) => x.focusoutHandler(c.event)}"
|
|
57757
57874
|
@keydown="${(x, c) => x.keydownHandler(c.event)}"
|
|
57758
57875
|
@mousedown="${(x, c) => x.mousedownHandler(c.event)}"
|
|
57759
57876
|
>
|
|
57760
57877
|
${when(x => x.collapsible, html `
|
|
57761
|
-
|
|
57762
|
-
|
|
57763
|
-
|
|
57764
|
-
|
|
57765
|
-
|
|
57766
|
-
|
|
57767
|
-
|
|
57768
|
-
|
|
57769
|
-
|
|
57770
|
-
|
|
57771
|
-
|
|
57772
|
-
|
|
57773
|
-
|
|
57774
|
-
|
|
57775
|
-
|
|
57776
|
-
|
|
57777
|
-
|
|
57778
|
-
|
|
57779
|
-
|
|
57780
|
-
|
|
57878
|
+
<div
|
|
57879
|
+
class="control"
|
|
57880
|
+
part="control"
|
|
57881
|
+
?disabled="${x => x.disabled}"
|
|
57882
|
+
${ref('control')}
|
|
57883
|
+
>
|
|
57884
|
+
${startSlotTemplate(context, definition)}
|
|
57885
|
+
<slot name="button-container">
|
|
57886
|
+
<div class="selected-value" part="selected-value" ${overflow('hasOverflow')} title=${x => (x.hasOverflow && x.displayValue ? x.displayValue : null)}>
|
|
57887
|
+
<slot name="selected-value">${x => x.displayValue}</slot>
|
|
57888
|
+
</div>
|
|
57889
|
+
<div aria-hidden="true" class="indicator" part="indicator">
|
|
57890
|
+
<slot name="indicator">
|
|
57891
|
+
${definition.indicator || ''}
|
|
57892
|
+
</slot>
|
|
57893
|
+
</div>
|
|
57894
|
+
</slot>
|
|
57895
|
+
${endSlotTemplate(context, definition)}
|
|
57896
|
+
</div>
|
|
57897
|
+
`)}
|
|
57781
57898
|
<${anchoredRegionTag}
|
|
57782
|
-
${ref('
|
|
57899
|
+
${ref('anchoredRegion')}
|
|
57783
57900
|
class="anchored-region"
|
|
57784
57901
|
fixed-placement
|
|
57785
57902
|
auto-update-mode="auto"
|
|
@@ -57788,93 +57905,766 @@ img.ProseMirror-separator {
|
|
|
57788
57905
|
horizontal-default-position="center"
|
|
57789
57906
|
horizontal-positioning-mode="locktodefault"
|
|
57790
57907
|
horizontal-scaling="anchor"
|
|
57908
|
+
@loaded="${x => x.regionLoadedHandler()}"
|
|
57791
57909
|
?hidden="${x => (x.collapsible ? !x.open : false)}">
|
|
57792
|
-
<div
|
|
57793
|
-
|
|
57794
|
-
|
|
57795
|
-
|
|
57796
|
-
|
|
57797
|
-
|
|
57798
|
-
|
|
57799
|
-
|
|
57800
|
-
|
|
57801
|
-
|
|
57910
|
+
<div class="listbox-background">
|
|
57911
|
+
<div
|
|
57912
|
+
class="
|
|
57913
|
+
listbox
|
|
57914
|
+
${x => (x.filteredOptions.length === 0 ? 'empty' : '')}
|
|
57915
|
+
${x => x.positionAttribute}
|
|
57916
|
+
"
|
|
57917
|
+
id="${x => x.listboxId}"
|
|
57918
|
+
part="listbox"
|
|
57919
|
+
role="listbox"
|
|
57920
|
+
?disabled="${x => x.disabled}"
|
|
57921
|
+
${ref('listbox')}
|
|
57922
|
+
>
|
|
57923
|
+
${when(x => x.filterMode !== FilterMode.none, html `
|
|
57924
|
+
<div class="filter-field ${x => x.positionAttribute}">
|
|
57925
|
+
<${iconMagnifyingGlassTag} class="filter-icon"></${iconMagnifyingGlassTag}>
|
|
57926
|
+
<input
|
|
57927
|
+
${ref('filterInput')}
|
|
57928
|
+
class="filter-input"
|
|
57929
|
+
aria-controls="${x => x.ariaControls}"
|
|
57930
|
+
aria-activedescendant="${x => x.ariaActiveDescendant}"
|
|
57931
|
+
@input="${(x, c) => x.inputHandler(c.event)}"
|
|
57932
|
+
@click="${(x, c) => x.inputClickHandler(c.event)}"
|
|
57933
|
+
placeholder="${x => filterSearchLabel.getValueFor(x)}"
|
|
57934
|
+
value="${x => x.filter}"
|
|
57935
|
+
/>
|
|
57936
|
+
</div>
|
|
57937
|
+
`)}
|
|
57938
|
+
<div ${ref('scrollableRegion')}
|
|
57939
|
+
class="scrollable-region">
|
|
57940
|
+
<slot
|
|
57941
|
+
${slotted({
|
|
57802
57942
|
filter: (n) => n instanceof HTMLElement && Listbox$1.slottedOptionFilter(n),
|
|
57803
57943
|
flatten: true,
|
|
57804
57944
|
property: 'slottedOptions',
|
|
57805
57945
|
})}
|
|
57806
|
-
|
|
57946
|
+
></slot>
|
|
57947
|
+
</div>
|
|
57948
|
+
${when(x => (x.filterMode !== FilterMode.none && x.filteredOptions.length === 0), html `
|
|
57949
|
+
<span class="no-results-label ${x => x.positionAttribute}">
|
|
57950
|
+
${x => filterNoResultsLabel.getValueFor(x)}
|
|
57951
|
+
</span>
|
|
57952
|
+
`)}
|
|
57953
|
+
</div>
|
|
57807
57954
|
</div>
|
|
57808
57955
|
</${anchoredRegionTag}>
|
|
57809
57956
|
</template>
|
|
57810
57957
|
`;
|
|
57811
57958
|
|
|
57959
|
+
// Based on: https://github.com/microsoft/fast/blob/%40microsoft/fast-foundation_v2.49.5/packages/web-components/fast-foundation/src/select/select.form-associated.ts
|
|
57960
|
+
/* eslint-disable max-classes-per-file */
|
|
57961
|
+
// eslint-disable-next-line jsdoc/require-jsdoc
|
|
57962
|
+
let Select$1 = class Select extends ListboxElement {
|
|
57963
|
+
};
|
|
57964
|
+
/**
|
|
57965
|
+
* A form-associated base class for the Select component. This was copied from the
|
|
57966
|
+
* FAST FormAssociatedSelect (which is not exported by fast-foundation)
|
|
57967
|
+
*
|
|
57968
|
+
* @internal
|
|
57969
|
+
*/
|
|
57970
|
+
class FormAssociatedSelect extends FormAssociated(Select$1) {
|
|
57971
|
+
constructor() {
|
|
57972
|
+
super(...arguments);
|
|
57973
|
+
this.proxy = document.createElement('select');
|
|
57974
|
+
}
|
|
57975
|
+
}
|
|
57976
|
+
|
|
57812
57977
|
/**
|
|
57813
|
-
* A nimble-styled HTML select
|
|
57978
|
+
* A nimble-styled HTML select.
|
|
57814
57979
|
*/
|
|
57815
|
-
class Select extends
|
|
57980
|
+
class Select extends FormAssociatedSelect {
|
|
57816
57981
|
constructor() {
|
|
57817
57982
|
super(...arguments);
|
|
57818
57983
|
this.appearance = DropdownAppearance.underline;
|
|
57819
57984
|
this.errorVisible = false;
|
|
57985
|
+
this.filterMode = FilterMode.none;
|
|
57986
|
+
/**
|
|
57987
|
+
* @internal
|
|
57988
|
+
*/
|
|
57989
|
+
this.open = false;
|
|
57990
|
+
/**
|
|
57991
|
+
* The unique id for the internal listbox element.
|
|
57992
|
+
*
|
|
57993
|
+
* @internal
|
|
57994
|
+
*/
|
|
57995
|
+
this.listboxId = uniqueId('listbox-');
|
|
57820
57996
|
/** @internal */
|
|
57821
57997
|
this.hasOverflow = false;
|
|
57998
|
+
/**
|
|
57999
|
+
* @internal
|
|
58000
|
+
*/
|
|
58001
|
+
this.filteredOptions = [];
|
|
58002
|
+
/**
|
|
58003
|
+
* @internal
|
|
58004
|
+
*/
|
|
58005
|
+
this.filter = '';
|
|
58006
|
+
/**
|
|
58007
|
+
* @internal
|
|
58008
|
+
*/
|
|
58009
|
+
this.committedSelectedOption = undefined;
|
|
58010
|
+
/**
|
|
58011
|
+
* The max height for the listbox when opened.
|
|
58012
|
+
*
|
|
58013
|
+
* @internal
|
|
58014
|
+
*/
|
|
58015
|
+
this.maxHeight = 0;
|
|
58016
|
+
this._value = '';
|
|
58017
|
+
this.forcedPosition = false;
|
|
58018
|
+
}
|
|
58019
|
+
/**
|
|
58020
|
+
* The component is collapsible when in single-selection mode with no size attribute.
|
|
58021
|
+
*
|
|
58022
|
+
* @internal
|
|
58023
|
+
*/
|
|
58024
|
+
get collapsible() {
|
|
58025
|
+
return !(this.multiple || typeof this.size === 'number');
|
|
58026
|
+
}
|
|
58027
|
+
/**
|
|
58028
|
+
* @internal
|
|
58029
|
+
*/
|
|
58030
|
+
connectedCallback() {
|
|
58031
|
+
super.connectedCallback();
|
|
58032
|
+
this.forcedPosition = !!this.positionAttribute;
|
|
58033
|
+
this.initializeOpenState();
|
|
58034
|
+
}
|
|
58035
|
+
/**
|
|
58036
|
+
* The list of options. This mirrors FAST's override implementation for this
|
|
58037
|
+
* member for the Combobox to support a filtered list in the dropdown.
|
|
58038
|
+
*
|
|
58039
|
+
* @public
|
|
58040
|
+
* @remarks
|
|
58041
|
+
* Overrides `Listbox.options`.
|
|
58042
|
+
*/
|
|
58043
|
+
get options() {
|
|
58044
|
+
Observable.track(this, 'options');
|
|
58045
|
+
return this.filteredOptions?.length
|
|
58046
|
+
? this.filteredOptions
|
|
58047
|
+
: this._options;
|
|
58048
|
+
}
|
|
58049
|
+
set options(value) {
|
|
58050
|
+
this._options = value;
|
|
58051
|
+
Observable.notify(this, 'options');
|
|
58052
|
+
}
|
|
58053
|
+
get value() {
|
|
58054
|
+
Observable.track(this, 'value');
|
|
58055
|
+
return this._value;
|
|
58056
|
+
}
|
|
58057
|
+
set value(next) {
|
|
58058
|
+
const prev = this._value;
|
|
58059
|
+
let newValue = next;
|
|
58060
|
+
// use 'options' here instead of '_options' as 'selectedIndex' may be relative
|
|
58061
|
+
// to filtered set
|
|
58062
|
+
if (this.options?.length) {
|
|
58063
|
+
const newValueIndex = this.options.findIndex(el => el.value === newValue);
|
|
58064
|
+
const prevSelectedValue = this.options[this.selectedIndex]?.value ?? null;
|
|
58065
|
+
const nextSelectedValue = this.options[newValueIndex]?.value ?? null;
|
|
58066
|
+
if (newValueIndex === -1
|
|
58067
|
+
|| prevSelectedValue !== nextSelectedValue) {
|
|
58068
|
+
newValue = '';
|
|
58069
|
+
this.selectedIndex = newValueIndex;
|
|
58070
|
+
}
|
|
58071
|
+
newValue = this.firstSelectedOption?.value ?? newValue;
|
|
58072
|
+
}
|
|
58073
|
+
if (prev !== newValue && !(this.open && this.selectedIndex < 0)) {
|
|
58074
|
+
this._value = newValue;
|
|
58075
|
+
super.valueChanged(prev, newValue);
|
|
58076
|
+
if (!this.open) {
|
|
58077
|
+
this.committedSelectedOption = this._options.find(o => o.value === newValue);
|
|
58078
|
+
}
|
|
58079
|
+
Observable.notify(this, 'value');
|
|
58080
|
+
if (this.collapsible) {
|
|
58081
|
+
Observable.notify(this, 'displayValue');
|
|
58082
|
+
}
|
|
58083
|
+
}
|
|
58084
|
+
}
|
|
58085
|
+
/**
|
|
58086
|
+
* @internal
|
|
58087
|
+
*/
|
|
58088
|
+
get displayValue() {
|
|
58089
|
+
Observable.track(this, 'displayValue');
|
|
58090
|
+
return this.committedSelectedOption?.text ?? '';
|
|
58091
|
+
}
|
|
58092
|
+
/**
|
|
58093
|
+
* @internal
|
|
58094
|
+
*/
|
|
58095
|
+
anchoredRegionChanged(_prev, _next) {
|
|
58096
|
+
if (this.anchoredRegion && this.control) {
|
|
58097
|
+
this.anchoredRegion.anchorElement = this.control;
|
|
58098
|
+
}
|
|
58099
|
+
}
|
|
58100
|
+
/**
|
|
58101
|
+
* @internal
|
|
58102
|
+
*/
|
|
58103
|
+
controlChanged(_prev, _next) {
|
|
58104
|
+
if (this.anchoredRegion && this.control) {
|
|
58105
|
+
this.anchoredRegion.anchorElement = this.control;
|
|
58106
|
+
}
|
|
58107
|
+
}
|
|
58108
|
+
/**
|
|
58109
|
+
* @internal
|
|
58110
|
+
*/
|
|
58111
|
+
slottedOptionsChanged(prev, next) {
|
|
58112
|
+
const value = this.value;
|
|
58113
|
+
this._options.forEach(o => {
|
|
58114
|
+
const notifier = Observable.getNotifier(o);
|
|
58115
|
+
notifier.unsubscribe(this, 'value');
|
|
58116
|
+
});
|
|
58117
|
+
super.slottedOptionsChanged(prev, next);
|
|
58118
|
+
this._options.forEach(o => {
|
|
58119
|
+
const notifier = Observable.getNotifier(o);
|
|
58120
|
+
notifier.subscribe(this, 'value');
|
|
58121
|
+
});
|
|
58122
|
+
this.setProxyOptions();
|
|
58123
|
+
this.updateValue();
|
|
58124
|
+
// We need to force an update to the filteredOptions observable
|
|
58125
|
+
// (by calling 'filterOptions()) so that the template correctly updates.
|
|
58126
|
+
this.filterOptions();
|
|
58127
|
+
if (value) {
|
|
58128
|
+
this.value = value;
|
|
58129
|
+
}
|
|
58130
|
+
this.committedSelectedOption = this.options[this.selectedIndex];
|
|
58131
|
+
}
|
|
58132
|
+
/**
|
|
58133
|
+
* @internal
|
|
58134
|
+
*/
|
|
58135
|
+
clickHandler(e) {
|
|
58136
|
+
// do nothing if the select is disabled
|
|
58137
|
+
if (this.disabled) {
|
|
58138
|
+
return;
|
|
58139
|
+
}
|
|
58140
|
+
if (this.open) {
|
|
58141
|
+
const captured = e.target.closest('option,[role=option]');
|
|
58142
|
+
if (!captured?.disabled) {
|
|
58143
|
+
this.updateSelectedIndexFromFilteredSet();
|
|
58144
|
+
}
|
|
58145
|
+
if (captured?.disabled) {
|
|
58146
|
+
return;
|
|
58147
|
+
}
|
|
58148
|
+
}
|
|
58149
|
+
super.clickHandler(e);
|
|
58150
|
+
this.open = this.collapsible && !this.open;
|
|
58151
|
+
if (!this.open && this.indexWhenOpened !== this.selectedIndex) {
|
|
58152
|
+
this.updateValue(true);
|
|
58153
|
+
}
|
|
58154
|
+
}
|
|
58155
|
+
/**
|
|
58156
|
+
* Updates the value when an option's value changes.
|
|
58157
|
+
*
|
|
58158
|
+
* @param source - the source object
|
|
58159
|
+
* @param propertyName - the property to evaluate
|
|
58160
|
+
*
|
|
58161
|
+
* @internal
|
|
58162
|
+
* @override
|
|
58163
|
+
*/
|
|
58164
|
+
handleChange(source, propertyName) {
|
|
58165
|
+
super.handleChange(source, propertyName);
|
|
58166
|
+
if (propertyName === 'value') {
|
|
58167
|
+
this.updateValue();
|
|
58168
|
+
}
|
|
58169
|
+
}
|
|
58170
|
+
/**
|
|
58171
|
+
* Prevents focus when size is set and a scrollbar is clicked.
|
|
58172
|
+
*
|
|
58173
|
+
* @param e - the mouse event object
|
|
58174
|
+
*
|
|
58175
|
+
* @override
|
|
58176
|
+
* @internal
|
|
58177
|
+
*/
|
|
58178
|
+
mousedownHandler(e) {
|
|
58179
|
+
if (e.offsetX >= 0 && e.offsetX <= this.listbox?.scrollWidth) {
|
|
58180
|
+
return super.mousedownHandler(e);
|
|
58181
|
+
}
|
|
58182
|
+
return this.collapsible;
|
|
58183
|
+
}
|
|
58184
|
+
/**
|
|
58185
|
+
* @internal
|
|
58186
|
+
*/
|
|
58187
|
+
regionLoadedHandler() {
|
|
58188
|
+
this.focusAndScrollOptionIntoView();
|
|
58189
|
+
}
|
|
58190
|
+
/**
|
|
58191
|
+
* Sets the multiple property on the proxy element.
|
|
58192
|
+
*
|
|
58193
|
+
* @param prev - the previous multiple value
|
|
58194
|
+
* @param next - the current multiple value
|
|
58195
|
+
*/
|
|
58196
|
+
multipleChanged(prev, next) {
|
|
58197
|
+
super.multipleChanged(prev, next);
|
|
58198
|
+
if (this.proxy) {
|
|
58199
|
+
this.proxy.multiple = next;
|
|
58200
|
+
}
|
|
58201
|
+
}
|
|
58202
|
+
/**
|
|
58203
|
+
* @internal
|
|
58204
|
+
*/
|
|
58205
|
+
inputClickHandler(e) {
|
|
58206
|
+
e.stopPropagation(); // clicking in filter input shouldn't close dropdown
|
|
58207
|
+
}
|
|
58208
|
+
/**
|
|
58209
|
+
* @internal
|
|
58210
|
+
*/
|
|
58211
|
+
changeValueHandler() {
|
|
58212
|
+
this.committedSelectedOption = this.options.find(option => option.selected);
|
|
58213
|
+
}
|
|
58214
|
+
/**
|
|
58215
|
+
* @internal
|
|
58216
|
+
*/
|
|
58217
|
+
updateDisplayValue() {
|
|
58218
|
+
if (this.collapsible) {
|
|
58219
|
+
Observable.notify(this, 'displayValue');
|
|
58220
|
+
}
|
|
58221
|
+
}
|
|
58222
|
+
/**
|
|
58223
|
+
* Handle content changes on the control input.
|
|
58224
|
+
*
|
|
58225
|
+
* @param e - the input event
|
|
58226
|
+
* @internal
|
|
58227
|
+
*/
|
|
58228
|
+
inputHandler(e) {
|
|
58229
|
+
this.filter = this.filterInput?.value ?? '';
|
|
58230
|
+
if (!this.committedSelectedOption) {
|
|
58231
|
+
this.committedSelectedOption = this._options.find(option => option.selected);
|
|
58232
|
+
}
|
|
58233
|
+
this.clearSelection();
|
|
58234
|
+
this.filterOptions();
|
|
58235
|
+
if (this.filteredOptions.length > 0
|
|
58236
|
+
&& this.committedSelectedOption
|
|
58237
|
+
&& !this.filteredOptions.includes(this.committedSelectedOption)) {
|
|
58238
|
+
const enabledOptions = this.filteredOptions.filter(o => !o.disabled);
|
|
58239
|
+
if (enabledOptions.length > 0) {
|
|
58240
|
+
enabledOptions[0].selected = true;
|
|
58241
|
+
}
|
|
58242
|
+
else {
|
|
58243
|
+
// only filtered option is disabled
|
|
58244
|
+
this.selectedOptions = [];
|
|
58245
|
+
this.selectedIndex = -1;
|
|
58246
|
+
}
|
|
58247
|
+
}
|
|
58248
|
+
else if (this.committedSelectedOption) {
|
|
58249
|
+
this.committedSelectedOption.selected = true;
|
|
58250
|
+
}
|
|
58251
|
+
if (e.inputType.includes('deleteContent') || !this.filter.length) {
|
|
58252
|
+
return true;
|
|
58253
|
+
}
|
|
58254
|
+
e.stopPropagation();
|
|
58255
|
+
return true;
|
|
58256
|
+
}
|
|
58257
|
+
/**
|
|
58258
|
+
* @internal
|
|
58259
|
+
*/
|
|
58260
|
+
focusoutHandler(e) {
|
|
58261
|
+
this.updateSelectedIndexFromFilteredSet();
|
|
58262
|
+
super.focusoutHandler(e);
|
|
58263
|
+
if (!this.open) {
|
|
58264
|
+
return true;
|
|
58265
|
+
}
|
|
58266
|
+
const focusTarget = e.relatedTarget;
|
|
58267
|
+
if (this.isSameNode(focusTarget)) {
|
|
58268
|
+
this.focus();
|
|
58269
|
+
return true;
|
|
58270
|
+
}
|
|
58271
|
+
if (!this.options?.includes(focusTarget)) {
|
|
58272
|
+
this.open = false;
|
|
58273
|
+
if (this.indexWhenOpened !== this.selectedIndex) {
|
|
58274
|
+
this.updateValue(true);
|
|
58275
|
+
}
|
|
58276
|
+
}
|
|
58277
|
+
return true;
|
|
58278
|
+
}
|
|
58279
|
+
/**
|
|
58280
|
+
* @internal
|
|
58281
|
+
*/
|
|
58282
|
+
keydownHandler(e) {
|
|
58283
|
+
super.keydownHandler(e);
|
|
58284
|
+
const key = e.key;
|
|
58285
|
+
if (e.ctrlKey || e.shiftKey) {
|
|
58286
|
+
return true;
|
|
58287
|
+
}
|
|
58288
|
+
switch (key) {
|
|
58289
|
+
case keySpace: {
|
|
58290
|
+
// when dropdown is open allow user to enter a space for filter text
|
|
58291
|
+
if (this.open && this.filterMode !== FilterMode.none) {
|
|
58292
|
+
break;
|
|
58293
|
+
}
|
|
58294
|
+
e.preventDefault();
|
|
58295
|
+
if (this.collapsible && this.typeAheadExpired) {
|
|
58296
|
+
this.open = !this.open;
|
|
58297
|
+
}
|
|
58298
|
+
if (!this.open) {
|
|
58299
|
+
this.focus();
|
|
58300
|
+
}
|
|
58301
|
+
break;
|
|
58302
|
+
}
|
|
58303
|
+
case keyHome:
|
|
58304
|
+
case keyEnd: {
|
|
58305
|
+
e.preventDefault();
|
|
58306
|
+
break;
|
|
58307
|
+
}
|
|
58308
|
+
case keyEnter: {
|
|
58309
|
+
e.preventDefault();
|
|
58310
|
+
if (this.filteredOptions.length === 0
|
|
58311
|
+
|| this.filteredOptions.every(o => o.disabled)) {
|
|
58312
|
+
return false;
|
|
58313
|
+
}
|
|
58314
|
+
this.updateSelectedIndexFromFilteredSet();
|
|
58315
|
+
this.open = !this.open;
|
|
58316
|
+
if (!this.open) {
|
|
58317
|
+
this.focus();
|
|
58318
|
+
}
|
|
58319
|
+
break;
|
|
58320
|
+
}
|
|
58321
|
+
case keyEscape: {
|
|
58322
|
+
// clear filter as update to "selectedIndex" will result in processing
|
|
58323
|
+
// "options" and not "_options"
|
|
58324
|
+
this.filter = '';
|
|
58325
|
+
if (this.committedSelectedOption) {
|
|
58326
|
+
this.clearSelection();
|
|
58327
|
+
this.selectedIndex = this._options.indexOf(this.committedSelectedOption);
|
|
58328
|
+
}
|
|
58329
|
+
if (this.collapsible && this.open) {
|
|
58330
|
+
e.preventDefault();
|
|
58331
|
+
this.open = false;
|
|
58332
|
+
}
|
|
58333
|
+
// reset 'selected' state otherwise the selected state doesn't stick.
|
|
58334
|
+
const selectedOption = this._options[this.selectedIndex];
|
|
58335
|
+
if (selectedOption) {
|
|
58336
|
+
selectedOption.selected = true;
|
|
58337
|
+
}
|
|
58338
|
+
this.focus();
|
|
58339
|
+
break;
|
|
58340
|
+
}
|
|
58341
|
+
case keyTab: {
|
|
58342
|
+
if (this.collapsible && this.open) {
|
|
58343
|
+
e.preventDefault();
|
|
58344
|
+
this.open = false;
|
|
58345
|
+
}
|
|
58346
|
+
return true;
|
|
58347
|
+
}
|
|
58348
|
+
}
|
|
58349
|
+
if (!this.open && this.indexWhenOpened !== this.selectedIndex) {
|
|
58350
|
+
this.updateValue(true);
|
|
58351
|
+
this.indexWhenOpened = this.selectedIndex;
|
|
58352
|
+
}
|
|
58353
|
+
return !(key === keyArrowDown || key === keyArrowUp);
|
|
58354
|
+
}
|
|
58355
|
+
/**
|
|
58356
|
+
* Updates the proxy value when the selected index changes.
|
|
58357
|
+
*
|
|
58358
|
+
* @param prev - the previous selected index
|
|
58359
|
+
* @param next - the next selected index
|
|
58360
|
+
*
|
|
58361
|
+
* @internal
|
|
58362
|
+
*/
|
|
58363
|
+
selectedIndexChanged(prev, next) {
|
|
58364
|
+
super.selectedIndexChanged(prev, next);
|
|
58365
|
+
this.updateValue();
|
|
58366
|
+
}
|
|
58367
|
+
/**
|
|
58368
|
+
* Synchronize the `aria-disabled` property when the `disabled` property changes.
|
|
58369
|
+
*
|
|
58370
|
+
* @param prev - The previous disabled value
|
|
58371
|
+
* @param next - The next disabled value
|
|
58372
|
+
*
|
|
58373
|
+
* @internal
|
|
58374
|
+
*/
|
|
58375
|
+
disabledChanged(prev, next) {
|
|
58376
|
+
if (super.disabledChanged) {
|
|
58377
|
+
super.disabledChanged(prev, next);
|
|
58378
|
+
}
|
|
58379
|
+
this.ariaDisabled = this.disabled ? 'true' : 'false';
|
|
58380
|
+
}
|
|
58381
|
+
/**
|
|
58382
|
+
* Reset the element to its first selectable option when its parent form is reset.
|
|
58383
|
+
*
|
|
58384
|
+
* @internal
|
|
58385
|
+
*/
|
|
58386
|
+
formResetCallback() {
|
|
58387
|
+
this.setProxyOptions();
|
|
58388
|
+
// Call the base class's implementation setDefaultSelectedOption instead of the select's
|
|
58389
|
+
// override, in order to reset the selectedIndex without using the value property.
|
|
58390
|
+
super.setDefaultSelectedOption();
|
|
58391
|
+
if (this.selectedIndex === -1) {
|
|
58392
|
+
this.selectedIndex = 0;
|
|
58393
|
+
}
|
|
58394
|
+
}
|
|
58395
|
+
// Prevents parent classes from resetting selectedIndex to a positive
|
|
58396
|
+
// value while filtering, which can result in a disabled option being
|
|
58397
|
+
// selected.
|
|
58398
|
+
setSelectedOptions() {
|
|
58399
|
+
if (this.open && this.selectedIndex === -1) {
|
|
58400
|
+
return;
|
|
58401
|
+
}
|
|
58402
|
+
super.setSelectedOptions();
|
|
58403
|
+
}
|
|
58404
|
+
focusAndScrollOptionIntoView() {
|
|
58405
|
+
super.focusAndScrollOptionIntoView();
|
|
58406
|
+
if (this.open) {
|
|
58407
|
+
window.requestAnimationFrame(() => {
|
|
58408
|
+
this.filterInput?.focus();
|
|
58409
|
+
});
|
|
58410
|
+
}
|
|
58411
|
+
}
|
|
58412
|
+
positionChanged(_, next) {
|
|
58413
|
+
this.positionAttribute = next;
|
|
58414
|
+
this.setPositioning();
|
|
58415
|
+
}
|
|
58416
|
+
/**
|
|
58417
|
+
* Updates the proxy's size property when the size attribute changes.
|
|
58418
|
+
*
|
|
58419
|
+
* @param prev - the previous size
|
|
58420
|
+
* @param next - the current size
|
|
58421
|
+
*
|
|
58422
|
+
* @override
|
|
58423
|
+
* @internal
|
|
58424
|
+
*/
|
|
58425
|
+
sizeChanged(prev, next) {
|
|
58426
|
+
super.sizeChanged(prev, next);
|
|
58427
|
+
if (this.proxy) {
|
|
58428
|
+
this.proxy.size = next;
|
|
58429
|
+
}
|
|
58430
|
+
}
|
|
58431
|
+
openChanged() {
|
|
58432
|
+
if (!this.collapsible) {
|
|
58433
|
+
return;
|
|
58434
|
+
}
|
|
58435
|
+
if (this.open) {
|
|
58436
|
+
this.initializeOpenState();
|
|
58437
|
+
this.indexWhenOpened = this.selectedIndex;
|
|
58438
|
+
return;
|
|
58439
|
+
}
|
|
58440
|
+
this.filter = '';
|
|
58441
|
+
if (this.filterInput) {
|
|
58442
|
+
this.filterInput.value = '';
|
|
58443
|
+
}
|
|
58444
|
+
this.ariaControls = '';
|
|
58445
|
+
this.ariaExpanded = 'false';
|
|
58446
|
+
}
|
|
58447
|
+
/**
|
|
58448
|
+
* Updates the selectedness of each option when the list of selected options changes.
|
|
58449
|
+
*
|
|
58450
|
+
* @param prev - the previous list of selected options
|
|
58451
|
+
* @param next - the current list of selected options
|
|
58452
|
+
*
|
|
58453
|
+
* @override
|
|
58454
|
+
* @internal
|
|
58455
|
+
*/
|
|
58456
|
+
selectedOptionsChanged(prev, next) {
|
|
58457
|
+
super.selectedOptionsChanged(prev, next);
|
|
58458
|
+
this.options?.forEach((o, i) => {
|
|
58459
|
+
const proxyOption = this.proxy?.options.item(i);
|
|
58460
|
+
if (proxyOption) {
|
|
58461
|
+
proxyOption.selected = o.selected;
|
|
58462
|
+
}
|
|
58463
|
+
});
|
|
58464
|
+
}
|
|
58465
|
+
/**
|
|
58466
|
+
* Sets the selected index to match the first option with the selected attribute, or
|
|
58467
|
+
* the first selectable option.
|
|
58468
|
+
*
|
|
58469
|
+
* @override
|
|
58470
|
+
* @internal
|
|
58471
|
+
*/
|
|
58472
|
+
setDefaultSelectedOption() {
|
|
58473
|
+
const options = this.options
|
|
58474
|
+
?? Array.from(this.children).filter(o => Listbox$1.slottedOptionFilter(o));
|
|
58475
|
+
const selectedIndex = options?.findIndex(el => el.hasAttribute('selected')
|
|
58476
|
+
|| el.selected
|
|
58477
|
+
|| el.value === this.value);
|
|
58478
|
+
if (selectedIndex !== -1) {
|
|
58479
|
+
this.selectedIndex = selectedIndex;
|
|
58480
|
+
return;
|
|
58481
|
+
}
|
|
58482
|
+
this.selectedIndex = 0;
|
|
57822
58483
|
}
|
|
57823
|
-
// Workaround for https://github.com/microsoft/fast/issues/5123
|
|
57824
58484
|
setPositioning() {
|
|
57825
58485
|
if (!this.$fastController.isConnected) {
|
|
57826
58486
|
// Don't call setPositioning() until we're connected,
|
|
57827
58487
|
// since this.forcedPosition isn't initialized yet.
|
|
57828
58488
|
return;
|
|
57829
58489
|
}
|
|
57830
|
-
|
|
58490
|
+
const currentBox = this.getBoundingClientRect();
|
|
58491
|
+
const viewportHeight = window.innerHeight;
|
|
58492
|
+
const availableBottom = viewportHeight - currentBox.bottom;
|
|
58493
|
+
if (this.forcedPosition) {
|
|
58494
|
+
this.position = this.positionAttribute;
|
|
58495
|
+
}
|
|
58496
|
+
else if (currentBox.top > availableBottom) {
|
|
58497
|
+
this.position = SelectPosition.above;
|
|
58498
|
+
}
|
|
58499
|
+
else {
|
|
58500
|
+
this.position = SelectPosition.below;
|
|
58501
|
+
}
|
|
58502
|
+
this.positionAttribute = this.forcedPosition
|
|
58503
|
+
? this.positionAttribute
|
|
58504
|
+
: this.position;
|
|
58505
|
+
this.maxHeight = this.position === SelectPosition.above
|
|
58506
|
+
? Math.trunc(currentBox.top)
|
|
58507
|
+
: Math.trunc(availableBottom);
|
|
57831
58508
|
this.updateListboxMaxHeightCssVariable();
|
|
57832
58509
|
}
|
|
57833
|
-
|
|
57834
|
-
|
|
57835
|
-
|
|
57836
|
-
|
|
57837
|
-
|
|
57838
|
-
|
|
58510
|
+
/**
|
|
58511
|
+
* Filter available options by text value.
|
|
58512
|
+
*
|
|
58513
|
+
* @public
|
|
58514
|
+
*/
|
|
58515
|
+
filterOptions() {
|
|
58516
|
+
const filter = this.filter.toLowerCase();
|
|
58517
|
+
if (filter) {
|
|
58518
|
+
this.filteredOptions = this._options.filter(option => {
|
|
58519
|
+
return diacriticInsensitiveStringNormalizer(option.text).includes(diacriticInsensitiveStringNormalizer(filter));
|
|
58520
|
+
});
|
|
58521
|
+
}
|
|
58522
|
+
else {
|
|
58523
|
+
this.filteredOptions = this._options;
|
|
57839
58524
|
}
|
|
58525
|
+
this._options.forEach(o => {
|
|
58526
|
+
o.hidden = !this.filteredOptions.includes(o);
|
|
58527
|
+
});
|
|
57840
58528
|
}
|
|
57841
|
-
|
|
57842
|
-
|
|
57843
|
-
|
|
58529
|
+
/**
|
|
58530
|
+
* Sets the value and display value to match the first selected option.
|
|
58531
|
+
*
|
|
58532
|
+
* @param shouldEmit - if true, the input and change events will be emitted
|
|
58533
|
+
*
|
|
58534
|
+
* @internal
|
|
58535
|
+
*/
|
|
58536
|
+
updateValue(shouldEmit) {
|
|
58537
|
+
if (this.$fastController.isConnected) {
|
|
58538
|
+
this.value = this.firstSelectedOption?.value ?? '';
|
|
58539
|
+
}
|
|
58540
|
+
if (shouldEmit) {
|
|
58541
|
+
this.$emit('input');
|
|
58542
|
+
this.$emit('change', this, {
|
|
58543
|
+
bubbles: true,
|
|
58544
|
+
composed: undefined
|
|
58545
|
+
});
|
|
57844
58546
|
}
|
|
57845
58547
|
}
|
|
57846
|
-
|
|
57847
|
-
|
|
57848
|
-
|
|
58548
|
+
/**
|
|
58549
|
+
* Resets and fills the proxy to match the component's options.
|
|
58550
|
+
*
|
|
58551
|
+
* @internal
|
|
58552
|
+
*/
|
|
58553
|
+
setProxyOptions() {
|
|
58554
|
+
if (this.proxy instanceof HTMLSelectElement && this.options) {
|
|
58555
|
+
this.proxy.options.length = 0;
|
|
58556
|
+
this.options.forEach(option => {
|
|
58557
|
+
const proxyOption = option.proxy
|
|
58558
|
+
|| (option instanceof HTMLOptionElement
|
|
58559
|
+
? option.cloneNode()
|
|
58560
|
+
: null);
|
|
58561
|
+
if (proxyOption) {
|
|
58562
|
+
this.proxy.options.add(proxyOption);
|
|
58563
|
+
}
|
|
58564
|
+
});
|
|
57849
58565
|
}
|
|
57850
58566
|
}
|
|
58567
|
+
clearSelection() {
|
|
58568
|
+
this.options.forEach(option => {
|
|
58569
|
+
option.selected = false;
|
|
58570
|
+
});
|
|
58571
|
+
}
|
|
58572
|
+
filterChanged() {
|
|
58573
|
+
this.filterOptions();
|
|
58574
|
+
}
|
|
57851
58575
|
maxHeightChanged() {
|
|
57852
58576
|
this.updateListboxMaxHeightCssVariable();
|
|
57853
58577
|
}
|
|
58578
|
+
initializeOpenState() {
|
|
58579
|
+
if (!this.open) {
|
|
58580
|
+
this.ariaExpanded = 'false';
|
|
58581
|
+
this.ariaControls = '';
|
|
58582
|
+
return;
|
|
58583
|
+
}
|
|
58584
|
+
this.committedSelectedOption = this._options[this.selectedIndex];
|
|
58585
|
+
this.ariaControls = this.listboxId;
|
|
58586
|
+
this.ariaExpanded = 'true';
|
|
58587
|
+
this.setPositioning();
|
|
58588
|
+
this.focusAndScrollOptionIntoView();
|
|
58589
|
+
}
|
|
57854
58590
|
updateListboxMaxHeightCssVariable() {
|
|
57855
58591
|
if (this.listbox) {
|
|
57856
58592
|
this.listbox.style.setProperty('--ni-private-select-max-height', `${this.maxHeight}px`);
|
|
57857
58593
|
}
|
|
57858
58594
|
}
|
|
58595
|
+
updateSelectedIndexFromFilteredSet() {
|
|
58596
|
+
const selectedItem = this.filteredOptions.length > 0
|
|
58597
|
+
? this.options[this.selectedIndex]
|
|
58598
|
+
?? this.committedSelectedOption
|
|
58599
|
+
: this.committedSelectedOption;
|
|
58600
|
+
if (!selectedItem) {
|
|
58601
|
+
return;
|
|
58602
|
+
}
|
|
58603
|
+
// Clear filter so any logic resolving against 'this.options' resolves against all options,
|
|
58604
|
+
// since selectedIndex should be relative to entire set.
|
|
58605
|
+
this.filter = '';
|
|
58606
|
+
// translate selectedIndex for filtered list to selectedIndex for all items
|
|
58607
|
+
this.selectedIndex = this._options.indexOf(selectedItem);
|
|
58608
|
+
// force selected to true again if the selection hasn't actually changed
|
|
58609
|
+
if (selectedItem === this.committedSelectedOption) {
|
|
58610
|
+
selectedItem.selected = true;
|
|
58611
|
+
}
|
|
58612
|
+
}
|
|
57859
58613
|
}
|
|
57860
58614
|
__decorate$1([
|
|
57861
58615
|
attr
|
|
57862
58616
|
], Select.prototype, "appearance", void 0);
|
|
58617
|
+
__decorate$1([
|
|
58618
|
+
attr({ attribute: 'position' })
|
|
58619
|
+
], Select.prototype, "positionAttribute", void 0);
|
|
57863
58620
|
__decorate$1([
|
|
57864
58621
|
attr({ attribute: 'error-text' })
|
|
57865
58622
|
], Select.prototype, "errorText", void 0);
|
|
57866
58623
|
__decorate$1([
|
|
57867
58624
|
attr({ attribute: 'error-visible', mode: 'boolean' })
|
|
57868
58625
|
], Select.prototype, "errorVisible", void 0);
|
|
58626
|
+
__decorate$1([
|
|
58627
|
+
attr({ attribute: 'filter-mode' })
|
|
58628
|
+
], Select.prototype, "filterMode", void 0);
|
|
58629
|
+
__decorate$1([
|
|
58630
|
+
attr({ attribute: 'open', mode: 'boolean' })
|
|
58631
|
+
], Select.prototype, "open", void 0);
|
|
58632
|
+
__decorate$1([
|
|
58633
|
+
observable
|
|
58634
|
+
], Select.prototype, "position", void 0);
|
|
58635
|
+
__decorate$1([
|
|
58636
|
+
observable
|
|
58637
|
+
], Select.prototype, "control", void 0);
|
|
57869
58638
|
__decorate$1([
|
|
57870
58639
|
observable
|
|
57871
|
-
], Select.prototype, "
|
|
58640
|
+
], Select.prototype, "scrollableRegion", void 0);
|
|
58641
|
+
__decorate$1([
|
|
58642
|
+
observable
|
|
58643
|
+
], Select.prototype, "filterInput", void 0);
|
|
58644
|
+
__decorate$1([
|
|
58645
|
+
observable
|
|
58646
|
+
], Select.prototype, "anchoredRegion", void 0);
|
|
57872
58647
|
__decorate$1([
|
|
57873
58648
|
observable
|
|
57874
58649
|
], Select.prototype, "hasOverflow", void 0);
|
|
58650
|
+
__decorate$1([
|
|
58651
|
+
observable
|
|
58652
|
+
], Select.prototype, "filteredOptions", void 0);
|
|
58653
|
+
__decorate$1([
|
|
58654
|
+
observable
|
|
58655
|
+
], Select.prototype, "filter", void 0);
|
|
58656
|
+
__decorate$1([
|
|
58657
|
+
observable
|
|
58658
|
+
], Select.prototype, "committedSelectedOption", void 0);
|
|
58659
|
+
__decorate$1([
|
|
58660
|
+
observable
|
|
58661
|
+
], Select.prototype, "maxHeight", void 0);
|
|
58662
|
+
__decorate$1([
|
|
58663
|
+
volatile
|
|
58664
|
+
], Select.prototype, "collapsible", null);
|
|
57875
58665
|
const nimbleSelect = Select.compose({
|
|
57876
58666
|
baseName: 'select',
|
|
57877
|
-
baseClass: Select$
|
|
58667
|
+
baseClass: Select$2,
|
|
57878
58668
|
template: template$l,
|
|
57879
58669
|
styles: styles$o,
|
|
57880
58670
|
indicator: arrowExpanderDown16X16.data,
|
|
@@ -57886,6 +58676,7 @@ img.ProseMirror-separator {
|
|
|
57886
58676
|
${errorTextTemplate}
|
|
57887
58677
|
`
|
|
57888
58678
|
});
|
|
58679
|
+
applyMixins(Select, StartEnd, DelegatesARIASelect);
|
|
57889
58680
|
DesignSystem.getOrCreate().withPrefix('nimble').register(nimbleSelect());
|
|
57890
58681
|
|
|
57891
58682
|
const styles$n = css `
|