@ni/ok-components 1.2.1 → 1.3.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 (98) hide show
  1. package/dist/all-components-bundle.js +3044 -530
  2. package/dist/all-components-bundle.js.map +1 -1
  3. package/dist/all-components-bundle.min.js +6788 -5229
  4. package/dist/all-components-bundle.min.js.map +1 -1
  5. package/dist/custom-elements.json +1423 -63
  6. package/dist/custom-elements.md +246 -13
  7. package/dist/esm/fv/accordion-item/index.d.ts +1 -0
  8. package/dist/esm/fv/accordion-item/index.js +1 -0
  9. package/dist/esm/fv/accordion-item/index.js.map +1 -1
  10. package/dist/esm/fv/accordion-item/testing/fv-accordion-item.pageobject.js +5 -0
  11. package/dist/esm/fv/accordion-item/testing/fv-accordion-item.pageobject.js.map +1 -1
  12. package/dist/esm/fv/all-fv.d.ts +7 -0
  13. package/dist/esm/fv/all-fv.js +7 -0
  14. package/dist/esm/fv/all-fv.js.map +1 -1
  15. package/dist/esm/fv/card/index.d.ts +59 -0
  16. package/dist/esm/fv/card/index.js +144 -0
  17. package/dist/esm/fv/card/index.js.map +1 -0
  18. package/dist/esm/fv/card/styles.d.ts +1 -0
  19. package/dist/esm/fv/card/styles.js +231 -0
  20. package/dist/esm/fv/card/styles.js.map +1 -0
  21. package/dist/esm/fv/card/template.d.ts +2 -0
  22. package/dist/esm/fv/card/template.js +126 -0
  23. package/dist/esm/fv/card/template.js.map +1 -0
  24. package/dist/esm/fv/card/types.d.ts +10 -0
  25. package/dist/esm/fv/card/types.js +9 -0
  26. package/dist/esm/fv/card/types.js.map +1 -0
  27. package/dist/esm/fv/chip-selector/index.d.ts +104 -0
  28. package/dist/esm/fv/chip-selector/index.js +367 -0
  29. package/dist/esm/fv/chip-selector/index.js.map +1 -0
  30. package/dist/esm/fv/chip-selector/styles.d.ts +1 -0
  31. package/dist/esm/fv/chip-selector/styles.js +251 -0
  32. package/dist/esm/fv/chip-selector/styles.js.map +1 -0
  33. package/dist/esm/fv/chip-selector/template.d.ts +2 -0
  34. package/dist/esm/fv/chip-selector/template.js +147 -0
  35. package/dist/esm/fv/chip-selector/template.js.map +1 -0
  36. package/dist/esm/fv/context-help/index.d.ts +22 -0
  37. package/dist/esm/fv/context-help/index.js +41 -0
  38. package/dist/esm/fv/context-help/index.js.map +1 -0
  39. package/dist/esm/fv/context-help/styles.d.ts +1 -0
  40. package/dist/esm/fv/context-help/styles.js +55 -0
  41. package/dist/esm/fv/context-help/styles.js.map +1 -0
  42. package/dist/esm/fv/context-help/template.d.ts +2 -0
  43. package/dist/esm/fv/context-help/template.js +24 -0
  44. package/dist/esm/fv/context-help/template.js.map +1 -0
  45. package/dist/esm/fv/context-help/types.d.ts +1 -0
  46. package/dist/esm/fv/context-help/types.js +2 -0
  47. package/dist/esm/fv/context-help/types.js.map +1 -0
  48. package/dist/esm/fv/search-input/index.d.ts +2 -0
  49. package/dist/esm/fv/search-input/index.js +2 -0
  50. package/dist/esm/fv/search-input/index.js.map +1 -1
  51. package/dist/esm/fv/search-input/styles.js +14 -14
  52. package/dist/esm/fv/search-input/styles.js.map +1 -1
  53. package/dist/esm/fv/split-button/index.d.ts +43 -0
  54. package/dist/esm/fv/split-button/index.js +130 -0
  55. package/dist/esm/fv/split-button/index.js.map +1 -0
  56. package/dist/esm/fv/split-button/styles.d.ts +1 -0
  57. package/dist/esm/fv/split-button/styles.js +220 -0
  58. package/dist/esm/fv/split-button/styles.js.map +1 -0
  59. package/dist/esm/fv/split-button/template.d.ts +2 -0
  60. package/dist/esm/fv/split-button/template.js +52 -0
  61. package/dist/esm/fv/split-button/template.js.map +1 -0
  62. package/dist/esm/fv/split-button/types.d.ts +12 -0
  63. package/dist/esm/fv/split-button/types.js +11 -0
  64. package/dist/esm/fv/split-button/types.js.map +1 -0
  65. package/dist/esm/fv/split-button-anchor/index.d.ts +47 -0
  66. package/dist/esm/fv/split-button-anchor/index.js +146 -0
  67. package/dist/esm/fv/split-button-anchor/index.js.map +1 -0
  68. package/dist/esm/fv/split-button-anchor/styles.d.ts +1 -0
  69. package/dist/esm/fv/split-button-anchor/styles.js +228 -0
  70. package/dist/esm/fv/split-button-anchor/styles.js.map +1 -0
  71. package/dist/esm/fv/split-button-anchor/template.d.ts +2 -0
  72. package/dist/esm/fv/split-button-anchor/template.js +64 -0
  73. package/dist/esm/fv/split-button-anchor/template.js.map +1 -0
  74. package/dist/esm/fv/split-button-anchor/types.d.ts +12 -0
  75. package/dist/esm/fv/split-button-anchor/types.js +11 -0
  76. package/dist/esm/fv/split-button-anchor/types.js.map +1 -0
  77. package/dist/esm/fv/summary-panel/index.d.ts +26 -0
  78. package/dist/esm/fv/summary-panel/index.js +70 -0
  79. package/dist/esm/fv/summary-panel/index.js.map +1 -0
  80. package/dist/esm/fv/summary-panel/styles.d.ts +1 -0
  81. package/dist/esm/fv/summary-panel/styles.js +49 -0
  82. package/dist/esm/fv/summary-panel/styles.js.map +1 -0
  83. package/dist/esm/fv/summary-panel/template.d.ts +2 -0
  84. package/dist/esm/fv/summary-panel/template.js +29 -0
  85. package/dist/esm/fv/summary-panel/template.js.map +1 -0
  86. package/dist/esm/fv/summary-panel-tile/index.d.ts +23 -0
  87. package/dist/esm/fv/summary-panel-tile/index.js +59 -0
  88. package/dist/esm/fv/summary-panel-tile/index.js.map +1 -0
  89. package/dist/esm/fv/summary-panel-tile/styles.d.ts +1 -0
  90. package/dist/esm/fv/summary-panel-tile/styles.js +138 -0
  91. package/dist/esm/fv/summary-panel-tile/styles.js.map +1 -0
  92. package/dist/esm/fv/summary-panel-tile/template.d.ts +2 -0
  93. package/dist/esm/fv/summary-panel-tile/template.js +14 -0
  94. package/dist/esm/fv/summary-panel-tile/template.js.map +1 -0
  95. package/dist/esm/fv/summary-panel-tile/types.d.ts +5 -0
  96. package/dist/esm/fv/summary-panel-tile/types.js +5 -0
  97. package/dist/esm/fv/summary-panel-tile/types.js.map +1 -0
  98. package/package.json +1 -1
@@ -0,0 +1,367 @@
1
+ import { __decorate } from "tslib";
2
+ import { attr, observable } from '@ni/fast-element';
3
+ import { DesignSystem, FoundationElement } from '@ni/fast-foundation';
4
+ import { uniqueId } from '@ni/fast-web-utilities';
5
+ import { chipTag } from '@ni/nimble-components/dist/esm/chip';
6
+ import { diacriticInsensitiveStringNormalizer } from '@ni/nimble-components/dist/esm/utilities/models/string-normalizers';
7
+ import { styles } from './styles';
8
+ import { template } from './template';
9
+ /**
10
+ * A chip picker with inline text entry, removable chips, and a dropdown option list.
11
+ */
12
+ export class FvChipSelector extends FoundationElement {
13
+ constructor() {
14
+ super(...arguments);
15
+ this.disabled = false;
16
+ this.open = false;
17
+ this.label = '';
18
+ this.selectedValues = '';
19
+ this.options = '';
20
+ this.placeholder = 'Select values';
21
+ this.allowCustomValues = false;
22
+ /** @internal */
23
+ this.filterText = '';
24
+ /** @internal */
25
+ this.activeOptionIndex = -1;
26
+ /** @internal */
27
+ this.activeOptionId = null;
28
+ /** @internal */
29
+ this.inputId = uniqueId('ok-fv-chip-selector-input');
30
+ /** @internal */
31
+ this.labelId = uniqueId('ok-fv-chip-selector-label');
32
+ /** @internal */
33
+ this.menuId = uniqueId('ok-fv-chip-selector-menu');
34
+ this.inputElement = null;
35
+ this.menuButtonElement = null;
36
+ this.documentClickHandler = (event) => {
37
+ if (this.open && !event.composedPath().includes(this)) {
38
+ this.setOpen(false);
39
+ }
40
+ };
41
+ }
42
+ /** @internal */
43
+ disabledChanged() {
44
+ if (this.disabled) {
45
+ this.filterText = '';
46
+ this.open = false;
47
+ }
48
+ }
49
+ /** @internal */
50
+ openChanged() {
51
+ this.syncMenuButtonState();
52
+ if (!this.open) {
53
+ this.activeOptionIndex = -1;
54
+ }
55
+ }
56
+ /** @internal */
57
+ activeOptionIndexChanged() {
58
+ this.syncActiveOption();
59
+ }
60
+ /** @internal */
61
+ filterTextChanged() {
62
+ this.activeOptionIndex = -1;
63
+ }
64
+ /** @internal */
65
+ optionsChanged() { }
66
+ /** @internal */
67
+ allowCustomValuesChanged() { }
68
+ /** @internal */
69
+ selectedValuesChanged() { }
70
+ /** @internal */
71
+ connectedCallback() {
72
+ super.connectedCallback();
73
+ document.addEventListener('click', this.documentClickHandler);
74
+ }
75
+ /** @internal */
76
+ disconnectedCallback() {
77
+ document.removeEventListener('click', this.documentClickHandler);
78
+ super.disconnectedCallback();
79
+ }
80
+ /** @internal */
81
+ captureInputRef(input) {
82
+ this.inputElement = input;
83
+ }
84
+ /** @internal */
85
+ captureMenuButtonRef(menuButton) {
86
+ this.menuButtonElement = menuButton;
87
+ this.syncMenuButtonState();
88
+ }
89
+ /** @internal */
90
+ regionChanged(_prev, _next) {
91
+ if (this.region && this.field) {
92
+ this.region.anchorElement = this.field;
93
+ }
94
+ }
95
+ /** @internal */
96
+ fieldChanged(_prev, _next) {
97
+ if (this.region) {
98
+ this.region.anchorElement = this.field ?? null;
99
+ }
100
+ }
101
+ /** @internal */
102
+ get selectedValueList() {
103
+ return Array.from(new Set(this.selectedValues
104
+ .split(',')
105
+ .map(value => value.trim())
106
+ .filter(value => value.length > 0)));
107
+ }
108
+ /** @internal */
109
+ get optionList() {
110
+ return Array.from(new Set(this.options
111
+ .split(',')
112
+ .map(option => option.trim())
113
+ .filter(option => option.length > 0)));
114
+ }
115
+ /** @internal */
116
+ get visibleOptionList() {
117
+ const selectedValues = new Set(this.selectedValueList);
118
+ const normalizedFilter = diacriticInsensitiveStringNormalizer(this.filterText.trim());
119
+ return this.optionList.filter(option => {
120
+ if (selectedValues.has(option)) {
121
+ return false;
122
+ }
123
+ return normalizedFilter.length === 0
124
+ || diacriticInsensitiveStringNormalizer(option).includes(normalizedFilter);
125
+ });
126
+ }
127
+ /** @internal */
128
+ get customValueCandidate() {
129
+ const trimmedFilterText = this.filterText.trim();
130
+ if (!this.allowCustomValues || trimmedFilterText.length === 0 || trimmedFilterText.includes(',')) {
131
+ return '';
132
+ }
133
+ if (this.optionList.includes(trimmedFilterText) || this.selectedValueList.includes(trimmedFilterText)) {
134
+ return '';
135
+ }
136
+ return trimmedFilterText;
137
+ }
138
+ /** @internal */
139
+ get createOptionLabel() {
140
+ return `Add '${this.customValueCandidate}'`;
141
+ }
142
+ /** @internal */
143
+ get showEmptyState() {
144
+ return this.visibleOptionList.length === 0 && this.customValueCandidate.length === 0;
145
+ }
146
+ /** @internal */
147
+ handleFieldClick(event) {
148
+ if (this.disabled) {
149
+ return;
150
+ }
151
+ const target = event.target;
152
+ if (target?.closest(chipTag) || target?.closest('.chip-selector-menu-button')) {
153
+ return;
154
+ }
155
+ this.setOpen(true);
156
+ this.inputElement?.focus();
157
+ }
158
+ /** @internal */
159
+ handleMenuButtonClick(event) {
160
+ event.stopPropagation();
161
+ event.preventDefault();
162
+ if (this.disabled) {
163
+ return;
164
+ }
165
+ this.setOpen(!this.open);
166
+ this.inputElement?.focus();
167
+ }
168
+ /** @internal */
169
+ handleMenuButtonChange(event) {
170
+ // Prevent internal toggle-button change events from surfacing as chip-selector selection changes.
171
+ event.stopPropagation();
172
+ this.syncMenuButtonState();
173
+ }
174
+ /** @internal */
175
+ handleInput(event) {
176
+ const input = event.target;
177
+ this.filterText = input.value;
178
+ this.setOpen(true);
179
+ }
180
+ /** @internal */
181
+ handleInputFocus() {
182
+ if (!this.disabled) {
183
+ this.setOpen(true);
184
+ }
185
+ }
186
+ /** @internal */
187
+ handleInputKeydown(event) {
188
+ if (this.disabled) {
189
+ return true;
190
+ }
191
+ if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {
192
+ event.preventDefault();
193
+ if (!this.open) {
194
+ this.setOpen(true);
195
+ }
196
+ const maxIndex = this.visibleOptionList.length + (this.customValueCandidate ? 1 : 0) - 1;
197
+ if (maxIndex < 0) {
198
+ return false;
199
+ }
200
+ if (event.key === 'ArrowDown') {
201
+ this.activeOptionIndex = Math.min(this.activeOptionIndex + 1, maxIndex);
202
+ }
203
+ else {
204
+ this.activeOptionIndex = Math.max(this.activeOptionIndex - 1, 0);
205
+ }
206
+ return false;
207
+ }
208
+ if (event.key === 'Enter') {
209
+ if (this.open && this.activeOptionIndex >= 0) {
210
+ event.preventDefault();
211
+ this.commitActiveOption();
212
+ return false;
213
+ }
214
+ return true;
215
+ }
216
+ if (event.key === 'Escape') {
217
+ event.preventDefault();
218
+ this.filterText = '';
219
+ this.setOpen(false);
220
+ return false;
221
+ }
222
+ if (event.key === 'Backspace' && this.filterText.length === 0) {
223
+ const selectedValues = this.selectedValueList;
224
+ const lastValue = selectedValues[selectedValues.length - 1];
225
+ if (lastValue) {
226
+ event.preventDefault();
227
+ this.removeValue(lastValue);
228
+ }
229
+ return false;
230
+ }
231
+ return true;
232
+ }
233
+ /** @internal */
234
+ handleChipRemove(event) {
235
+ const chip = event.composedPath().find(element => element instanceof HTMLElement && element.tagName.toLowerCase() === chipTag);
236
+ const value = chip?.getAttribute('data-chip-value')?.trim();
237
+ if (value) {
238
+ this.removeValue(value);
239
+ }
240
+ }
241
+ /** @internal */
242
+ handleMenuClick(event) {
243
+ const optionEl = event.composedPath().find(el => el instanceof HTMLElement && el.hasAttribute('data-option-value'));
244
+ const value = optionEl?.getAttribute('data-option-value')?.trim();
245
+ if (value) {
246
+ this.addValue(value);
247
+ }
248
+ }
249
+ /** @internal */
250
+ handleMenuItemChange(event) {
251
+ event.stopPropagation();
252
+ const menuItem = event.composedPath().find(pathItem => pathItem instanceof HTMLElement && pathItem.hasAttribute('data-option-value'));
253
+ const value = menuItem?.getAttribute('data-option-value')?.trim();
254
+ if (value) {
255
+ this.addValue(value);
256
+ }
257
+ }
258
+ syncActiveOption() {
259
+ const options = Array.from(this.shadowRoot?.querySelectorAll('.chip-selector-option') ?? []);
260
+ options.forEach((option, index) => {
261
+ option.setAttribute('aria-selected', String(index === this.activeOptionIndex));
262
+ });
263
+ if (this.activeOptionIndex < 0) {
264
+ this.activeOptionId = null;
265
+ }
266
+ else if (this.customValueCandidate.length > 0
267
+ && this.activeOptionIndex === this.visibleOptionList.length) {
268
+ this.activeOptionId = `${this.menuId}-option-create`;
269
+ }
270
+ else {
271
+ this.activeOptionId = `${this.menuId}-option-${this.activeOptionIndex}`;
272
+ }
273
+ }
274
+ commitActiveOption() {
275
+ const allOptions = [
276
+ ...this.visibleOptionList,
277
+ ...(this.customValueCandidate ? [this.customValueCandidate] : [])
278
+ ];
279
+ const value = allOptions[this.activeOptionIndex];
280
+ if (value !== undefined) {
281
+ this.addValue(value);
282
+ }
283
+ }
284
+ addValue(value) {
285
+ if (this.disabled) {
286
+ return;
287
+ }
288
+ const nextValues = this.selectedValueList;
289
+ if (nextValues.includes(value)) {
290
+ return;
291
+ }
292
+ nextValues.push(value);
293
+ this.commitSelection(nextValues);
294
+ this.filterText = '';
295
+ this.setOpen(true);
296
+ this.inputElement?.focus();
297
+ }
298
+ removeValue(value) {
299
+ if (this.disabled) {
300
+ return;
301
+ }
302
+ const nextValues = this.selectedValueList.filter(selectedValue => selectedValue !== value);
303
+ this.commitSelection(nextValues);
304
+ this.inputElement?.focus();
305
+ }
306
+ commitSelection(nextValues) {
307
+ this.selectedValues = nextValues.join(',');
308
+ this.dispatchEvent(new CustomEvent('change', {
309
+ bubbles: true,
310
+ composed: true,
311
+ detail: { selectedValues: nextValues }
312
+ }));
313
+ }
314
+ setOpen(nextOpen) {
315
+ this.open = this.disabled ? false : nextOpen;
316
+ this.syncMenuButtonState();
317
+ }
318
+ syncMenuButtonState() {
319
+ if (this.menuButtonElement) {
320
+ this.menuButtonElement.checked = this.open;
321
+ }
322
+ }
323
+ }
324
+ __decorate([
325
+ attr({ mode: 'boolean' })
326
+ ], FvChipSelector.prototype, "disabled", void 0);
327
+ __decorate([
328
+ attr({ mode: 'boolean' })
329
+ ], FvChipSelector.prototype, "open", void 0);
330
+ __decorate([
331
+ attr
332
+ ], FvChipSelector.prototype, "label", void 0);
333
+ __decorate([
334
+ attr({ attribute: 'selected-values' })
335
+ ], FvChipSelector.prototype, "selectedValues", void 0);
336
+ __decorate([
337
+ attr
338
+ ], FvChipSelector.prototype, "options", void 0);
339
+ __decorate([
340
+ attr
341
+ ], FvChipSelector.prototype, "placeholder", void 0);
342
+ __decorate([
343
+ attr({ attribute: 'allow-custom-values', mode: 'boolean' })
344
+ ], FvChipSelector.prototype, "allowCustomValues", void 0);
345
+ __decorate([
346
+ observable
347
+ ], FvChipSelector.prototype, "filterText", void 0);
348
+ __decorate([
349
+ observable
350
+ ], FvChipSelector.prototype, "activeOptionIndex", void 0);
351
+ __decorate([
352
+ observable
353
+ ], FvChipSelector.prototype, "activeOptionId", void 0);
354
+ __decorate([
355
+ observable
356
+ ], FvChipSelector.prototype, "region", void 0);
357
+ __decorate([
358
+ observable
359
+ ], FvChipSelector.prototype, "field", void 0);
360
+ const okFvChipSelector = FvChipSelector.compose({
361
+ baseName: 'fv-chip-selector',
362
+ template,
363
+ styles
364
+ });
365
+ DesignSystem.getOrCreate().withPrefix('ok').register(okFvChipSelector());
366
+ export const fvChipSelectorTag = 'ok-fv-chip-selector';
367
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/fv/chip-selector/index.ts"],"names":[],"mappings":"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","sourcesContent":["import { attr, observable } from '@ni/fast-element';\nimport { DesignSystem, FoundationElement } from '@ni/fast-foundation';\nimport { uniqueId } from '@ni/fast-web-utilities';\nimport type { AnchoredRegion } from '@ni/nimble-components/dist/esm/anchored-region';\nimport { chipTag } from '@ni/nimble-components/dist/esm/chip';\nimport { diacriticInsensitiveStringNormalizer } from '@ni/nimble-components/dist/esm/utilities/models/string-normalizers';\nimport { styles } from './styles';\nimport { template } from './template';\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'ok-fv-chip-selector': FvChipSelector;\n }\n}\n\n/**\n * A chip picker with inline text entry, removable chips, and a dropdown option list.\n */\nexport class FvChipSelector extends FoundationElement {\n @attr({ mode: 'boolean' })\n public disabled = false;\n\n @attr({ mode: 'boolean' })\n public open = false;\n\n @attr\n public label = '';\n\n @attr({ attribute: 'selected-values' })\n public selectedValues = '';\n\n @attr\n public options = '';\n\n @attr\n public placeholder = 'Select values';\n\n @attr({ attribute: 'allow-custom-values', mode: 'boolean' })\n public allowCustomValues = false;\n\n /** @internal */\n @observable\n public filterText = '';\n\n /** @internal */\n @observable\n public activeOptionIndex = -1;\n\n /** @internal */\n @observable\n public activeOptionId: string | null = null;\n\n /** @internal */\n public readonly inputId = uniqueId('ok-fv-chip-selector-input');\n\n /** @internal */\n public readonly labelId = uniqueId('ok-fv-chip-selector-label');\n\n /** @internal */\n public readonly menuId = uniqueId('ok-fv-chip-selector-menu');\n\n /** @internal */\n @observable\n public readonly region?: AnchoredRegion;\n\n /** @internal */\n @observable\n public readonly field?: HTMLElement;\n\n private inputElement: HTMLInputElement | null = null;\n\n private menuButtonElement: (HTMLElement & { checked?: boolean }) | null = null;\n\n /** @internal */\n public disabledChanged(): void {\n if (this.disabled) {\n this.filterText = '';\n this.open = false;\n }\n }\n\n /** @internal */\n public openChanged(): void {\n this.syncMenuButtonState();\n if (!this.open) {\n this.activeOptionIndex = -1;\n }\n }\n\n /** @internal */\n public activeOptionIndexChanged(): void {\n this.syncActiveOption();\n }\n\n /** @internal */\n public filterTextChanged(): void {\n this.activeOptionIndex = -1;\n }\n\n /** @internal */\n public optionsChanged(): void {}\n\n /** @internal */\n public allowCustomValuesChanged(): void {}\n\n /** @internal */\n public selectedValuesChanged(): void {}\n\n /** @internal */\n public override connectedCallback(): void {\n super.connectedCallback();\n document.addEventListener('click', this.documentClickHandler);\n }\n\n /** @internal */\n public override disconnectedCallback(): void {\n document.removeEventListener('click', this.documentClickHandler);\n super.disconnectedCallback();\n }\n\n /** @internal */\n public captureInputRef(input: HTMLInputElement | null): void {\n this.inputElement = input;\n }\n\n /** @internal */\n public captureMenuButtonRef(menuButton: (HTMLElement & { checked?: boolean }) | null): void {\n this.menuButtonElement = menuButton;\n this.syncMenuButtonState();\n }\n\n /** @internal */\n public regionChanged(\n _prev: AnchoredRegion | undefined,\n _next: AnchoredRegion | undefined\n ): void {\n if (this.region && this.field) {\n this.region.anchorElement = this.field;\n }\n }\n\n /** @internal */\n public fieldChanged(\n _prev: HTMLElement | undefined,\n _next: HTMLElement | undefined\n ): void {\n if (this.region) {\n this.region.anchorElement = this.field ?? null;\n }\n }\n\n /** @internal */\n public get selectedValueList(): string[] {\n return Array.from(new Set(\n this.selectedValues\n .split(',')\n .map(value => value.trim())\n .filter(value => value.length > 0)\n ));\n }\n\n /** @internal */\n public get optionList(): string[] {\n return Array.from(new Set(\n this.options\n .split(',')\n .map(option => option.trim())\n .filter(option => option.length > 0)\n ));\n }\n\n /** @internal */\n public get visibleOptionList(): string[] {\n const selectedValues = new Set(this.selectedValueList);\n const normalizedFilter = diacriticInsensitiveStringNormalizer(this.filterText.trim());\n\n return this.optionList.filter(option => {\n if (selectedValues.has(option)) {\n return false;\n }\n\n return normalizedFilter.length === 0\n || diacriticInsensitiveStringNormalizer(option).includes(normalizedFilter);\n });\n }\n\n /** @internal */\n public get customValueCandidate(): string {\n const trimmedFilterText = this.filterText.trim();\n\n if (!this.allowCustomValues || trimmedFilterText.length === 0 || trimmedFilterText.includes(',')) {\n return '';\n }\n\n if (this.optionList.includes(trimmedFilterText) || this.selectedValueList.includes(trimmedFilterText)) {\n return '';\n }\n\n return trimmedFilterText;\n }\n\n /** @internal */\n public get createOptionLabel(): string {\n return `Add '${this.customValueCandidate}'`;\n }\n\n /** @internal */\n public get showEmptyState(): boolean {\n return this.visibleOptionList.length === 0 && this.customValueCandidate.length === 0;\n }\n\n /** @internal */\n public handleFieldClick(event: Event): void {\n if (this.disabled) {\n return;\n }\n\n const target = event.target as HTMLElement | null;\n if (target?.closest(chipTag) || target?.closest('.chip-selector-menu-button')) {\n return;\n }\n\n this.setOpen(true);\n this.inputElement?.focus();\n }\n\n /** @internal */\n public handleMenuButtonClick(event: Event): void {\n event.stopPropagation();\n event.preventDefault();\n\n if (this.disabled) {\n return;\n }\n\n this.setOpen(!this.open);\n this.inputElement?.focus();\n }\n\n /** @internal */\n public handleMenuButtonChange(event: Event): void {\n // Prevent internal toggle-button change events from surfacing as chip-selector selection changes.\n event.stopPropagation();\n this.syncMenuButtonState();\n }\n\n /** @internal */\n public handleInput(event: Event): void {\n const input = event.target as HTMLInputElement;\n this.filterText = input.value;\n this.setOpen(true);\n }\n\n /** @internal */\n public handleInputFocus(): void {\n if (!this.disabled) {\n this.setOpen(true);\n }\n }\n\n /** @internal */\n public handleInputKeydown(event: KeyboardEvent): boolean {\n if (this.disabled) {\n return true;\n }\n\n if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {\n event.preventDefault();\n if (!this.open) {\n this.setOpen(true);\n }\n const maxIndex = this.visibleOptionList.length + (this.customValueCandidate ? 1 : 0) - 1;\n if (maxIndex < 0) {\n return false;\n }\n if (event.key === 'ArrowDown') {\n this.activeOptionIndex = Math.min(this.activeOptionIndex + 1, maxIndex);\n } else {\n this.activeOptionIndex = Math.max(this.activeOptionIndex - 1, 0);\n }\n return false;\n }\n\n if (event.key === 'Enter') {\n if (this.open && this.activeOptionIndex >= 0) {\n event.preventDefault();\n this.commitActiveOption();\n return false;\n }\n return true;\n }\n\n if (event.key === 'Escape') {\n event.preventDefault();\n this.filterText = '';\n this.setOpen(false);\n return false;\n }\n\n if (event.key === 'Backspace' && this.filterText.length === 0) {\n const selectedValues = this.selectedValueList;\n const lastValue = selectedValues[selectedValues.length - 1];\n if (lastValue) {\n event.preventDefault();\n this.removeValue(lastValue);\n }\n return false;\n }\n\n return true;\n }\n\n /** @internal */\n public handleChipRemove(event: Event): void {\n const chip = event.composedPath().find(\n element => element instanceof HTMLElement && element.tagName.toLowerCase() === chipTag\n ) as HTMLElement | undefined;\n\n const value = chip?.getAttribute('data-chip-value')?.trim();\n if (value) {\n this.removeValue(value);\n }\n }\n\n /** @internal */\n public handleMenuClick(event: Event): void {\n const optionEl = event.composedPath().find(\n el => el instanceof HTMLElement && el.hasAttribute('data-option-value')\n ) as HTMLElement | undefined;\n const value = optionEl?.getAttribute('data-option-value')?.trim();\n if (value) {\n this.addValue(value);\n }\n }\n\n /** @internal */\n public handleMenuItemChange(event: Event): void {\n event.stopPropagation();\n const menuItem = event.composedPath().find(\n pathItem => pathItem instanceof HTMLElement && pathItem.hasAttribute('data-option-value')\n ) as HTMLElement | undefined;\n const value = menuItem?.getAttribute('data-option-value')?.trim();\n if (value) {\n this.addValue(value);\n }\n }\n\n private readonly documentClickHandler = (event: Event): void => {\n if (this.open && !event.composedPath().includes(this)) {\n this.setOpen(false);\n }\n };\n\n private syncActiveOption(): void {\n const options = Array.from(\n this.shadowRoot?.querySelectorAll<HTMLElement>('.chip-selector-option') ?? []\n );\n options.forEach((option, index) => {\n option.setAttribute('aria-selected', String(index === this.activeOptionIndex));\n });\n\n if (this.activeOptionIndex < 0) {\n this.activeOptionId = null;\n } else if (\n this.customValueCandidate.length > 0\n && this.activeOptionIndex === this.visibleOptionList.length\n ) {\n this.activeOptionId = `${this.menuId}-option-create`;\n } else {\n this.activeOptionId = `${this.menuId}-option-${this.activeOptionIndex}`;\n }\n }\n\n private commitActiveOption(): void {\n const allOptions = [\n ...this.visibleOptionList,\n ...(this.customValueCandidate ? [this.customValueCandidate] : [])\n ];\n const value = allOptions[this.activeOptionIndex];\n if (value !== undefined) {\n this.addValue(value);\n }\n }\n\n private addValue(value: string): void {\n if (this.disabled) {\n return;\n }\n\n const nextValues = this.selectedValueList;\n if (nextValues.includes(value)) {\n return;\n }\n\n nextValues.push(value);\n this.commitSelection(nextValues);\n this.filterText = '';\n this.setOpen(true);\n this.inputElement?.focus();\n }\n\n private removeValue(value: string): void {\n if (this.disabled) {\n return;\n }\n\n const nextValues = this.selectedValueList.filter(selectedValue => selectedValue !== value);\n this.commitSelection(nextValues);\n this.inputElement?.focus();\n }\n\n private commitSelection(nextValues: string[]): void {\n this.selectedValues = nextValues.join(',');\n this.dispatchEvent(new CustomEvent('change', {\n bubbles: true,\n composed: true,\n detail: { selectedValues: nextValues }\n }));\n }\n\n private setOpen(nextOpen: boolean): void {\n this.open = this.disabled ? false : nextOpen;\n this.syncMenuButtonState();\n }\n\n private syncMenuButtonState(): void {\n if (this.menuButtonElement) {\n this.menuButtonElement.checked = this.open;\n }\n }\n}\n\nconst okFvChipSelector = FvChipSelector.compose({\n baseName: 'fv-chip-selector',\n template,\n styles\n});\n\nDesignSystem.getOrCreate().withPrefix('ok').register(okFvChipSelector());\nexport const fvChipSelectorTag = 'ok-fv-chip-selector';"]}
@@ -0,0 +1 @@
1
+ export declare const styles: import("@ni/fast-element").ElementStyles;
@@ -0,0 +1,251 @@
1
+ import { css } from '@ni/fast-element';
2
+ import { applicationBackgroundColor, bodyDisabledFontColor, bodyFont, bodyFontColor, borderHoverColor, borderRgbPartialColor, borderWidth, controlHeight, controlLabelDisabledFontColor, controlLabelFont, controlLabelFontColor, elevation2BoxShadow, fillHoverColor, fillHoverSelectedColor, fillSelectedColor, iconColor, placeholderFontColor, popupBorderColor, smallDelay, smallPadding, standardPadding } from '@ni/nimble-components/dist/esm/theme-provider/design-tokens';
3
+ import { display } from '../../utilities/style/display';
4
+ export const styles = css `
5
+ @layer base, hover, focusVisible, active, disabled, top;
6
+
7
+ @layer base {
8
+ ${display('inline-block')}
9
+
10
+ :host {
11
+ width: 300px;
12
+ max-width: 100%;
13
+ box-sizing: border-box;
14
+ font: ${bodyFont};
15
+ color: ${bodyFontColor};
16
+ }
17
+
18
+ .chip-selector {
19
+ position: relative;
20
+ width: 100%;
21
+ }
22
+
23
+ .label {
24
+ display: flex;
25
+ margin-block-end: ${smallPadding};
26
+ color: ${controlLabelFontColor};
27
+ font: ${controlLabelFont};
28
+ }
29
+
30
+ .chip-selector-field {
31
+ position: relative;
32
+ display: flex;
33
+ align-items: stretch;
34
+ min-height: ${controlHeight};
35
+ border: ${borderWidth} solid rgba(${borderRgbPartialColor}, 0.3);
36
+ background: transparent;
37
+ transition:
38
+ border-color ${smallDelay} ease-in-out;
39
+ }
40
+
41
+ .chip-selector-field::before {
42
+ content: '';
43
+ position: absolute;
44
+ inset-inline: 0;
45
+ inset-block-end: -1px;
46
+ height: 1px;
47
+ background: transparent;
48
+ pointer-events: none;
49
+ transition: background-color ${smallDelay} ease-in-out;
50
+ }
51
+
52
+ .chip-selector-field::after {
53
+ content: '';
54
+ position: absolute;
55
+ inset-inline: 0;
56
+ inset-block-end: -1px;
57
+ height: 2px;
58
+ background: transparent;
59
+ pointer-events: none;
60
+ transition:
61
+ background-color ${smallDelay} ease-in-out;
62
+ }
63
+
64
+ .chip-selector-selection-area {
65
+ position: relative;
66
+ display: flex;
67
+ flex: 1 1 auto;
68
+ flex-wrap: wrap;
69
+ align-items: center;
70
+ gap: ${smallPadding};
71
+ min-width: 0;
72
+ padding: ${smallPadding} ${standardPadding} ${smallPadding} ${smallPadding};
73
+ box-sizing: border-box;
74
+ }
75
+
76
+ .chip-selector-selection-area::after {
77
+ content: '';
78
+ position: absolute;
79
+ inset-block: ${smallPadding};
80
+ inset-inline-end: 0;
81
+ width: 2px;
82
+ background: rgba(${borderRgbPartialColor}, 0.2);
83
+ }
84
+
85
+ /* Target only the picker's internal chips, not slotted client content. */
86
+ .chip-selector-selection-area > nimble-chip {
87
+ ${controlHeight.cssCustomProperty}: 24px;
88
+ min-width: 0;
89
+ max-width: calc(100% - ${smallPadding});
90
+ }
91
+
92
+ .chip-selector-input {
93
+ -webkit-appearance: none;
94
+ appearance: none;
95
+ flex: 1 1 0;
96
+ min-width: 0;
97
+ width: 0;
98
+ padding: 0;
99
+ border: none;
100
+ background: transparent;
101
+ color: inherit;
102
+ font: inherit;
103
+ outline: none;
104
+ }
105
+
106
+ .chip-selector-input::placeholder {
107
+ color: ${placeholderFontColor};
108
+ }
109
+
110
+ .chip-selector-menu-button {
111
+ ${controlHeight.cssCustomProperty}: 24px;
112
+ align-self: flex-start;
113
+ margin-block: ${smallPadding};
114
+ margin-inline: ${smallPadding};
115
+ }
116
+
117
+ .chip-selector-menu-icon {
118
+ ${iconColor.cssCustomProperty}: currentColor;
119
+ }
120
+
121
+ .chip-selector-menu {
122
+ width: 100%;
123
+ box-sizing: border-box;
124
+ margin-block-start: ${smallPadding};
125
+ display: flex;
126
+ flex-direction: column;
127
+ max-height: 192px;
128
+ overflow-y: auto;
129
+ border: ${borderWidth} solid ${popupBorderColor};
130
+ background: ${applicationBackgroundColor};
131
+ box-shadow: ${elevation2BoxShadow};
132
+ border-radius: 4px;
133
+ }
134
+
135
+ .chip-selector-menu[hidden] {
136
+ display: none;
137
+ }
138
+
139
+ .chip-selector-option {
140
+ -webkit-appearance: none;
141
+ appearance: none;
142
+ display: flex;
143
+ align-items: center;
144
+ width: 100%;
145
+ min-width: 0;
146
+ min-height: ${controlHeight};
147
+ padding: 0 ${standardPadding};
148
+ border: none;
149
+ background: transparent;
150
+ color: inherit;
151
+ font: inherit;
152
+ text-align: left;
153
+ overflow: hidden;
154
+ text-overflow: ellipsis;
155
+ white-space: nowrap;
156
+ cursor: pointer;
157
+ }
158
+
159
+ .chip-selector-create-option {
160
+ border-top: ${borderWidth} solid rgba(${borderRgbPartialColor}, 0.12);
161
+ }
162
+
163
+ .chip-selector-empty {
164
+ padding: ${smallPadding} ${standardPadding};
165
+ color: ${placeholderFontColor};
166
+ }
167
+ }
168
+
169
+ @layer hover {
170
+ .chip-selector-field:hover::after {
171
+ background: ${borderHoverColor};
172
+ }
173
+
174
+ .chip-selector-option:hover,
175
+ .chip-selector-option.active {
176
+ background: ${fillHoverColor};
177
+ }
178
+ }
179
+
180
+ @layer focusVisible {
181
+ .chip-selector-field:focus-within::before {
182
+ background: ${borderHoverColor};
183
+ }
184
+
185
+ .chip-selector-field:focus-within {
186
+ border-bottom-color: transparent;
187
+ }
188
+
189
+ .chip-selector-field:focus-within::after {
190
+ background: transparent;
191
+ }
192
+
193
+ .chip-selector-option:focus-visible {
194
+ outline: ${borderWidth} solid ${borderHoverColor};
195
+ outline-offset: -1px;
196
+ }
197
+ }
198
+
199
+ @layer active {
200
+ :host([open]) .chip-selector-field::before {
201
+ background: ${borderHoverColor};
202
+ }
203
+
204
+ :host([open]) .chip-selector-field {
205
+ border-bottom-color: transparent;
206
+ }
207
+
208
+ :host([open]) .chip-selector-field::after {
209
+ background: transparent;
210
+ }
211
+
212
+ .chip-selector-option[aria-selected='true'] {
213
+ background: ${fillSelectedColor};
214
+ }
215
+
216
+ .chip-selector-option[aria-selected='true']:hover {
217
+ background: ${fillHoverSelectedColor};
218
+ }
219
+
220
+ .chip-selector-option:active {
221
+ background: ${fillSelectedColor};
222
+ }
223
+ }
224
+
225
+ @layer disabled {
226
+ :host([disabled]) {
227
+ color: ${bodyDisabledFontColor};
228
+ }
229
+
230
+ :host([disabled]) .label {
231
+ color: ${controlLabelDisabledFontColor};
232
+ }
233
+
234
+ :host([disabled]) .chip-selector-field {
235
+ border-color: rgba(${borderRgbPartialColor}, 0.1);
236
+ background: rgba(${borderRgbPartialColor}, 0.07);
237
+ }
238
+
239
+ :host([disabled]) .chip-selector-field::after {
240
+ background: transparent;
241
+ }
242
+
243
+ :host([disabled]) .chip-selector-menu-button,
244
+ :host([disabled]) .chip-selector-input {
245
+ cursor: not-allowed;
246
+ }
247
+ }
248
+
249
+ @layer top {}
250
+ `;
251
+ //# sourceMappingURL=styles.js.map