@dropi/ui 0.1.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 (117) hide show
  1. package/LICENSE +21 -0
  2. package/dist/cjs/dropi-badge.cjs.entry.js +37 -0
  3. package/dist/cjs/dropi-button.cjs.entry.js +81 -0
  4. package/dist/cjs/dropi-checkbox.cjs.entry.js +36 -0
  5. package/dist/cjs/dropi-icon.cjs.entry.js +50 -0
  6. package/dist/cjs/dropi-input.cjs.entry.js +210 -0
  7. package/dist/cjs/dropi-radio-button.cjs.entry.js +47 -0
  8. package/dist/cjs/dropi-select.cjs.entry.js +335 -0
  9. package/dist/cjs/dropi-switch.cjs.entry.js +30 -0
  10. package/dist/cjs/dropi-tag.cjs.entry.js +68 -0
  11. package/dist/cjs/dropi-text-area.cjs.entry.js +103 -0
  12. package/dist/cjs/dropi-ui.cjs.js +24 -0
  13. package/dist/cjs/index-CuGLZVqo.js +1743 -0
  14. package/dist/cjs/index.cjs.js +2 -0
  15. package/dist/cjs/loader.cjs.js +12 -0
  16. package/dist/collection/assets/icons/symbol/svg/sprite.css.svg +1 -0
  17. package/dist/collection/collection-manifest.json +22 -0
  18. package/dist/collection/components/dropi-badge/dropi-badge.css +41 -0
  19. package/dist/collection/components/dropi-badge/dropi-badge.js +72 -0
  20. package/dist/collection/components/dropi-button/dropi-button.css +169 -0
  21. package/dist/collection/components/dropi-button/dropi-button.js +277 -0
  22. package/dist/collection/components/dropi-checkbox/dropi-checkbox.css +47 -0
  23. package/dist/collection/components/dropi-checkbox/dropi-checkbox.js +103 -0
  24. package/dist/collection/components/dropi-icon/dropi-icon.css +19 -0
  25. package/dist/collection/components/dropi-icon/dropi-icon.js +142 -0
  26. package/dist/collection/components/dropi-input/dropi-input.css +168 -0
  27. package/dist/collection/components/dropi-input/dropi-input.js +735 -0
  28. package/dist/collection/components/dropi-radio-button/dropi-radio-button.css +59 -0
  29. package/dist/collection/components/dropi-radio-button/dropi-radio-button.js +181 -0
  30. package/dist/collection/components/dropi-select/dropi-select.css +364 -0
  31. package/dist/collection/components/dropi-select/dropi-select.js +932 -0
  32. package/dist/collection/components/dropi-select/select.types.js +1 -0
  33. package/dist/collection/components/dropi-switch/dropi-switch.css +57 -0
  34. package/dist/collection/components/dropi-switch/dropi-switch.js +96 -0
  35. package/dist/collection/components/dropi-tag/dropi-tag.css +40 -0
  36. package/dist/collection/components/dropi-tag/dropi-tag.js +190 -0
  37. package/dist/collection/components/dropi-text-area/dropi-text-area.css +97 -0
  38. package/dist/collection/components/dropi-text-area/dropi-text-area.js +457 -0
  39. package/dist/collection/index.js +1 -0
  40. package/dist/collection/utils/utils.js +3 -0
  41. package/dist/collection/utils/utils.unit.test.js +16 -0
  42. package/dist/components/dropi-badge.d.ts +11 -0
  43. package/dist/components/dropi-badge.js +1 -0
  44. package/dist/components/dropi-button.d.ts +11 -0
  45. package/dist/components/dropi-button.js +1 -0
  46. package/dist/components/dropi-checkbox.d.ts +11 -0
  47. package/dist/components/dropi-checkbox.js +1 -0
  48. package/dist/components/dropi-icon.d.ts +11 -0
  49. package/dist/components/dropi-icon.js +1 -0
  50. package/dist/components/dropi-input.d.ts +11 -0
  51. package/dist/components/dropi-input.js +1 -0
  52. package/dist/components/dropi-radio-button.d.ts +11 -0
  53. package/dist/components/dropi-radio-button.js +1 -0
  54. package/dist/components/dropi-select.d.ts +11 -0
  55. package/dist/components/dropi-select.js +1 -0
  56. package/dist/components/dropi-switch.d.ts +11 -0
  57. package/dist/components/dropi-switch.js +1 -0
  58. package/dist/components/dropi-tag.d.ts +11 -0
  59. package/dist/components/dropi-tag.js +1 -0
  60. package/dist/components/dropi-text-area.d.ts +11 -0
  61. package/dist/components/dropi-text-area.js +1 -0
  62. package/dist/components/index.d.ts +35 -0
  63. package/dist/components/index.js +1 -0
  64. package/dist/components/p-MNma8N1x.js +1 -0
  65. package/dist/dropi-ui/dropi-ui.css +1 -0
  66. package/dist/dropi-ui/dropi-ui.esm.js +1 -0
  67. package/dist/dropi-ui/index.esm.js +0 -0
  68. package/dist/dropi-ui/p-1a28b8f5.entry.js +1 -0
  69. package/dist/dropi-ui/p-21abf91a.entry.js +1 -0
  70. package/dist/dropi-ui/p-52291024.entry.js +1 -0
  71. package/dist/dropi-ui/p-54502c46.entry.js +1 -0
  72. package/dist/dropi-ui/p-6f0aa619.entry.js +1 -0
  73. package/dist/dropi-ui/p-9c7076d3.entry.js +1 -0
  74. package/dist/dropi-ui/p-DFz-gwFP.js +2 -0
  75. package/dist/dropi-ui/p-a1944f3d.entry.js +1 -0
  76. package/dist/dropi-ui/p-c7b9cbda.entry.js +1 -0
  77. package/dist/dropi-ui/p-dd089a60.entry.js +1 -0
  78. package/dist/dropi-ui/p-f785011f.entry.js +1 -0
  79. package/dist/esm/dropi-badge.entry.js +35 -0
  80. package/dist/esm/dropi-button.entry.js +79 -0
  81. package/dist/esm/dropi-checkbox.entry.js +34 -0
  82. package/dist/esm/dropi-icon.entry.js +48 -0
  83. package/dist/esm/dropi-input.entry.js +208 -0
  84. package/dist/esm/dropi-radio-button.entry.js +45 -0
  85. package/dist/esm/dropi-select.entry.js +333 -0
  86. package/dist/esm/dropi-switch.entry.js +28 -0
  87. package/dist/esm/dropi-tag.entry.js +66 -0
  88. package/dist/esm/dropi-text-area.entry.js +101 -0
  89. package/dist/esm/dropi-ui.js +20 -0
  90. package/dist/esm/index-DFz-gwFP.js +1734 -0
  91. package/dist/esm/index.js +1 -0
  92. package/dist/esm/loader.js +10 -0
  93. package/dist/index.cjs.js +1 -0
  94. package/dist/index.js +1 -0
  95. package/dist/types/components/dropi-badge/dropi-badge.d.ts +12 -0
  96. package/dist/types/components/dropi-button/dropi-button.d.ts +35 -0
  97. package/dist/types/components/dropi-checkbox/dropi-checkbox.d.ts +16 -0
  98. package/dist/types/components/dropi-icon/dropi-icon.d.ts +25 -0
  99. package/dist/types/components/dropi-input/dropi-input.d.ts +92 -0
  100. package/dist/types/components/dropi-radio-button/dropi-radio-button.d.ts +25 -0
  101. package/dist/types/components/dropi-select/dropi-select.d.ts +103 -0
  102. package/dist/types/components/dropi-select/select.types.d.ts +23 -0
  103. package/dist/types/components/dropi-switch/dropi-switch.d.ts +15 -0
  104. package/dist/types/components/dropi-tag/dropi-tag.d.ts +25 -0
  105. package/dist/types/components/dropi-text-area/dropi-text-area.d.ts +53 -0
  106. package/dist/types/components.d.ts +1549 -0
  107. package/dist/types/index.d.ts +7 -0
  108. package/dist/types/stencil-public-runtime.d.ts +1860 -0
  109. package/dist/types/utils/utils.d.ts +1 -0
  110. package/dist/types/utils/utils.unit.test.d.ts +1 -0
  111. package/loader/cdn.js +1 -0
  112. package/loader/index.cjs.js +1 -0
  113. package/loader/index.d.ts +24 -0
  114. package/loader/index.es2017.js +1 -0
  115. package/loader/index.js +2 -0
  116. package/package.json +50 -0
  117. package/readme.md +89 -0
@@ -0,0 +1,932 @@
1
+ import { h, } from "@stencil/core";
2
+ /**
3
+ * @component dropi-select
4
+ * Feature-rich select with support for:
5
+ * - Single / multi select
6
+ * - Grouped options
7
+ * - Search / filter
8
+ * - Country flags
9
+ * - Radio-style options with images
10
+ * - Inline (dropdownType) or bordered trigger
11
+ * - Native form association
12
+ *
13
+ * ## Usage
14
+ * Options must be set via JS property (not HTML attribute) for object arrays:
15
+ * ```js
16
+ * document.querySelector('dropi-select').options = [
17
+ * { id: 1, label: 'Option A' },
18
+ * { id: 2, label: 'Option B' },
19
+ * ];
20
+ * ```
21
+ */
22
+ export class DropiSelect {
23
+ el;
24
+ internals;
25
+ buttonRef;
26
+ scrollDebounce;
27
+ hasEmittedScrollEnd = false;
28
+ lastScrollTop = 0;
29
+ // ── Props ────────────────────────────────────────────────────
30
+ label = '';
31
+ placeholder = 'Seleccionar';
32
+ /** Array of SelectOption or SelectOptionGroup */
33
+ options = [];
34
+ name = '';
35
+ disabled = false;
36
+ invalid = false;
37
+ errorText = '';
38
+ helperText = '';
39
+ showObligatory = false;
40
+ /** Enables text search inside the dropdown */
41
+ searchEnabled = false;
42
+ /** Allows selecting multiple options */
43
+ multiSelect = false;
44
+ /** Renders trigger without border (inline/dropdown style) */
45
+ dropdownType = false;
46
+ /** Show country flags next to option labels */
47
+ showCountryFlags = false;
48
+ /** Renders options as radio buttons with optional image */
49
+ radioOptions = false;
50
+ /** Placeholder inside the search field */
51
+ placeHolderSearch = 'Buscar';
52
+ /** Icon name shown before the trigger label */
53
+ preIcon = '';
54
+ /** Pre-select an option by id */
55
+ defaultSelectedId = '';
56
+ /** Controlled selected option (single select) */
57
+ value = null;
58
+ // ── State ────────────────────────────────────────────────────
59
+ isOpen = false;
60
+ selectedOption = null;
61
+ multiSelected = [];
62
+ filteredOptions = [];
63
+ searchTerm = '';
64
+ dropdownStyle = {
65
+ top: '0px', left: '0px', width: '0px',
66
+ };
67
+ // ── Events ───────────────────────────────────────────────────
68
+ /** Emitted when an option is selected (single) or selection changes (multi) */
69
+ dropiChange;
70
+ /** Emitted when the selection is cleared */
71
+ dropiClear;
72
+ /** Emitted on search input */
73
+ dropiSearch;
74
+ /** Emitted when the list is scrolled to the end */
75
+ dropiScrollEnd;
76
+ /** Emitted on Enter key inside search */
77
+ dropiKeyEnter;
78
+ // ── Lifecycle ────────────────────────────────────────────────
79
+ componentWillLoad() {
80
+ this.normalizeOptions();
81
+ this.filteredOptions = [...this.options];
82
+ this.applyDefaultSelection();
83
+ }
84
+ optionsChanged() {
85
+ this.normalizeOptions();
86
+ this.filteredOptions = [...this.options];
87
+ this.applyDefaultSelection();
88
+ }
89
+ normalizeOptions() {
90
+ if (typeof this.options === 'string') {
91
+ try {
92
+ this.options = JSON.parse(this.options);
93
+ }
94
+ catch (_) {
95
+ this.options = [];
96
+ }
97
+ }
98
+ }
99
+ defaultChanged(newId) {
100
+ this.applyDefaultSelection(newId);
101
+ }
102
+ valueChanged(v) {
103
+ this.selectedOption = v;
104
+ this.internals.setFormValue(v ? String(v.id) : '');
105
+ }
106
+ // ── Public Methods ───────────────────────────────────────────
107
+ /** Select an option by its id */
108
+ async setById(id) {
109
+ const opt = this.options.find(o => o.id === id || String(o.id) === String(id));
110
+ if (opt)
111
+ this.selectOption(opt);
112
+ }
113
+ /** Select an option by its label */
114
+ async setByLabel(label) {
115
+ const opt = this.options.find(o => o.label === label);
116
+ if (opt)
117
+ this.selectOption(opt);
118
+ }
119
+ /** Clear the current selection */
120
+ async clearSelection() {
121
+ this.selectedOption = null;
122
+ this.multiSelected = [];
123
+ this.internals.setFormValue('');
124
+ this.dropiClear.emit();
125
+ }
126
+ /** Reset multi-select state and show a placeholder label */
127
+ async resetMultiSelect(_placeholder) {
128
+ this.multiSelected = [];
129
+ this.internals.setFormValue('');
130
+ }
131
+ // ── Click outside ────────────────────────────────────────────
132
+ handleOutsideClick(e) {
133
+ if (!this.el.contains(e.target)) {
134
+ this.closeDropdown();
135
+ }
136
+ }
137
+ // ── Helpers ──────────────────────────────────────────────────
138
+ applyDefaultSelection(id) {
139
+ const targetId = id ?? this.defaultSelectedId;
140
+ if (targetId === '' || targetId === undefined || targetId === null)
141
+ return;
142
+ const flat = this.flatOptions();
143
+ const found = flat.find(o => o.id === targetId || String(o.id) === String(targetId));
144
+ if (found) {
145
+ this.selectedOption = found;
146
+ this.internals.setFormValue(String(found.id));
147
+ }
148
+ }
149
+ flatOptions() {
150
+ if (!this.options?.length)
151
+ return [];
152
+ if ('category' in this.options[0]) {
153
+ return this.options.flatMap(g => g.options);
154
+ }
155
+ return this.options;
156
+ }
157
+ get isGrouped() {
158
+ return this.options?.length > 0 && 'category' in this.options[0];
159
+ }
160
+ get triggerLabel() {
161
+ if (this.multiSelect) {
162
+ return this.multiSelected.length
163
+ ? this.multiSelected.map(o => o.label).join(', ')
164
+ : this.placeholder;
165
+ }
166
+ if (this.selectedOption) {
167
+ return this.showCountryFlags && this.selectedOption.shortLabel
168
+ ? this.selectedOption.shortLabel
169
+ : this.selectedOption.label;
170
+ }
171
+ return this.placeholder;
172
+ }
173
+ // ── Dropdown positioning ─────────────────────────────────────
174
+ openDropdown() {
175
+ if (this.disabled)
176
+ return;
177
+ const rect = this.buttonRef.getBoundingClientRect();
178
+ const viewportHeight = window.innerHeight;
179
+ const dropdownHeight = 250;
180
+ const spaceBelow = viewportHeight - rect.bottom;
181
+ const top = spaceBelow >= dropdownHeight
182
+ ? rect.bottom + 4
183
+ : rect.top - dropdownHeight - 4;
184
+ this.dropdownStyle = {
185
+ top: `${top}px`,
186
+ left: `${rect.left}px`,
187
+ width: `${rect.width}px`,
188
+ };
189
+ this.isOpen = true;
190
+ if (this.searchEnabled) {
191
+ setTimeout(() => {
192
+ const searchInput = this.el.shadowRoot?.querySelector('.search-input');
193
+ searchInput?.focus();
194
+ }, 50);
195
+ }
196
+ }
197
+ closeDropdown() {
198
+ this.isOpen = false;
199
+ this.searchTerm = '';
200
+ this.filteredOptions = [...this.options];
201
+ }
202
+ toggleDropdown() {
203
+ this.isOpen ? this.closeDropdown() : this.openDropdown();
204
+ }
205
+ // ── Option selection ─────────────────────────────────────────
206
+ selectOption(option) {
207
+ if (option.disabled)
208
+ return;
209
+ if (this.multiSelect) {
210
+ const idx = this.multiSelected.findIndex(o => o.id === option.id);
211
+ if (idx >= 0) {
212
+ this.multiSelected = this.multiSelected.filter(o => o.id !== option.id);
213
+ }
214
+ else {
215
+ this.multiSelected = [...this.multiSelected, option];
216
+ }
217
+ this.internals.setFormValue(this.multiSelected.map(o => o.id).join(','));
218
+ this.dropiChange.emit([...this.multiSelected]);
219
+ }
220
+ else {
221
+ this.selectedOption = option;
222
+ this.internals.setFormValue(String(option.id));
223
+ this.dropiChange.emit(option);
224
+ this.closeDropdown();
225
+ }
226
+ }
227
+ isOptionChecked(option) {
228
+ return this.multiSelected.some(o => o.id === option.id);
229
+ }
230
+ // ── Search ───────────────────────────────────────────────────
231
+ handleSearch(term) {
232
+ this.searchTerm = term;
233
+ this.dropiSearch.emit(term);
234
+ const lower = term.toLowerCase().trim();
235
+ if (!lower) {
236
+ this.filteredOptions = [...this.options];
237
+ return;
238
+ }
239
+ if (this.isGrouped) {
240
+ this.filteredOptions = this.options
241
+ .map(g => ({ ...g, options: g.options.filter(o => o.label.toLowerCase().includes(lower)) }))
242
+ .filter(g => g.options.length > 0);
243
+ }
244
+ else {
245
+ this.filteredOptions = this.options.filter(o => o.label.toLowerCase().includes(lower));
246
+ }
247
+ }
248
+ // ── Scroll to end ─────────────────────────────────────────────
249
+ handleScroll(e) {
250
+ const el = e.target;
251
+ clearTimeout(this.scrollDebounce);
252
+ this.scrollDebounce = setTimeout(() => {
253
+ if (!el)
254
+ return;
255
+ const distFromBottom = el.scrollHeight - el.scrollTop - el.clientHeight;
256
+ const threshold = Math.min(50, el.clientHeight / 2);
257
+ if (el.scrollTop < this.lastScrollTop)
258
+ this.hasEmittedScrollEnd = false;
259
+ this.lastScrollTop = el.scrollTop;
260
+ if (distFromBottom <= threshold && !this.hasEmittedScrollEnd) {
261
+ this.dropiScrollEnd.emit();
262
+ this.hasEmittedScrollEnd = true;
263
+ setTimeout(() => { this.hasEmittedScrollEnd = false; }, 1000);
264
+ }
265
+ }, 100);
266
+ }
267
+ // ── Render helpers ───────────────────────────────────────────
268
+ renderTrigger() {
269
+ const isCompleted = this.multiSelect ? this.multiSelected.length > 0 : !!this.selectedOption;
270
+ const iconColor = this.disabled ? 'Gray-Gray-300' : this.dropdownType ? 'Gray-Gray-600' : 'Gray-Gray-400';
271
+ const iconSize = this.dropdownType ? '24px' : '20px';
272
+ return (h("button", { type: "button", class: {
273
+ 'select-button': true,
274
+ 'select-completed': isCompleted,
275
+ 'select-button-error': this.invalid,
276
+ 'no-border': this.dropdownType,
277
+ }, disabled: this.disabled, ref: el => (this.buttonRef = el), onClick: () => this.toggleDropdown() }, h("div", { class: {
278
+ 'button-content': true,
279
+ 'option-radio': this.radioOptions && !!this.selectedOption && !this.multiSelect,
280
+ } }, this.preIcon && (h("dropi-icon", { name: this.preIcon, width: "20px", height: "20px", color: "Gray-Gray-500" })), this.radioOptions && this.selectedOption && !this.multiSelect && [
281
+ this.selectedOption.imageUrl && !this.selectedOption.isFallback
282
+ ? h("img", { class: "option-image small-image", src: this.selectedOption.imageUrl, alt: "", onError: () => {
283
+ if (this.selectedOption)
284
+ this.selectedOption = { ...this.selectedOption, isFallback: true };
285
+ } })
286
+ : this.selectedOption.isFallback
287
+ ? h("span", { class: "option-image-fallback small-image" }, this.selectedOption.label.charAt(0).toUpperCase())
288
+ : null,
289
+ h("div", { class: "labels-container elipsis" }, h("span", null, this.selectedOption.label), this.selectedOption.secondLabel && h("span", { class: "option-second-label" }, this.selectedOption.secondLabel)),
290
+ ], !(this.radioOptions && this.selectedOption && !this.multiSelect) && (h("div", { class: "elipsis" }, this.triggerLabel))), h("dropi-icon", { name: this.isOpen ? 'Dropdown-up' : 'Dropdown-down', width: iconSize, height: iconSize, color: iconColor })));
291
+ }
292
+ renderOption(option) {
293
+ const isSelected = this.multiSelect
294
+ ? this.isOptionChecked(option)
295
+ : this.selectedOption?.id === option.id;
296
+ return (h("li", { key: option.id }, h("button", { type: "button", class: {
297
+ option: true,
298
+ 'option-radio': this.radioOptions,
299
+ 'option-with-flag': this.showCountryFlags && !!option.countryCode,
300
+ 'disabled-option': !!option.disabled,
301
+ 'selected-option': isSelected,
302
+ }, disabled: option.disabled, onClick: () => this.selectOption(option) }, this.multiSelect && (h("span", { class: { 'multi-checkbox': true, checked: isSelected } }, isSelected && (h("svg", { width: "10", height: "10", viewBox: "0 0 24 24", fill: "none" }, h("path", { d: "M20.6 5.7L9.1 17.2c-.2.2-.5.3-.8.3s-.6-.1-.8-.3L3 12.8c-.4-.4-.4-1 0-1.4.4-.4 1-.4 1.4 0l3.9 3.9L19.2 4.3c.4-.4 1-.4 1.4 0 .4.4.4 1 0 1.4z", fill: "white" }))))), this.radioOptions && (h("div", { class: { radio: true, selected: isSelected } }, isSelected && h("div", { class: "circle" }))), !this.radioOptions && option.preIcon && (h("dropi-icon", { name: option.preIcon, width: "20px", height: "20px", color: "Gray-Gray-500" })), this.radioOptions && option.imageUrl && !option.isFallback && (h("img", { class: "option-image", src: option.imageUrl, alt: "", onError: () => { option.isFallback = true; this.options = [...this.options]; } })), this.radioOptions && option.isFallback && (h("span", { class: "option-image-fallback" }, option.label.charAt(0).toUpperCase())), this.showCountryFlags && option.countryCode && (h("span", { class: "flag-placeholder" }, option.countryCode)), this.radioOptions
303
+ ? (h("div", { class: "labels-container" }, h("span", { class: "elipsis" }, option.label), option.secondLabel && h("span", { class: "option-second-label" }, option.secondLabel)))
304
+ : (h("span", { class: "elipsis" }, this.showCountryFlags && option.shortLabel ? option.shortLabel : option.label)))));
305
+ }
306
+ renderDropdown() {
307
+ if (!this.isOpen)
308
+ return null;
309
+ return (h("ul", { class: "select-dropdown-overlay", style: this.dropdownStyle, onScroll: (e) => this.handleScroll(e) }, this.searchEnabled && (h("li", { class: "sticky-search" }, h("div", { class: "search-wrapper" }, h("dropi-icon", { name: "Search", width: "16px", height: "16px", color: "Gray-Gray-400" }), h("input", { class: "search-input", type: "text", placeholder: this.placeHolderSearch, value: this.searchTerm, onInput: (e) => this.handleSearch(e.target.value), onKeyDown: (e) => {
310
+ if (e.key === 'Enter')
311
+ this.dropiKeyEnter.emit(e);
312
+ } }), this.searchTerm && (h("button", { type: "button", class: "search-clear", onClick: () => this.handleSearch('') }, h("dropi-icon", { name: "Close", width: "14px", height: "14px", color: "Gray-Gray-400" })))))), this.isGrouped && this.filteredOptions.map(group => [
313
+ h("li", { class: "option-group-title" }, group.category),
314
+ ...group.options.map(opt => (h("li", { key: opt.id }, h("button", { type: "button", class: { option: true, 'option-group': true, 'disabled-option': !!opt.disabled }, disabled: opt.disabled, onClick: () => this.selectOption(opt) }, opt.preIcon && h("dropi-icon", { name: opt.preIcon, width: "20px", height: "20px", color: "Gray-Gray-500" }), h("span", { class: "elipsis" }, opt.label))))),
315
+ ]), !this.isGrouped && this.filteredOptions.map(opt => this.renderOption(opt)), this.filteredOptions.length === 0 && (h("li", { class: "no-results" }, "Sin resultados"))));
316
+ }
317
+ render() {
318
+ return (h("div", { key: '94383b3267955dcb8d1a6c523730e291976157b2', class: "custom-select" }, !this.dropdownType && this.label && (h("label", { key: '4ff14d77b301a275f6c608d227361ff2829ac7a1', class: { 'disabled-label': this.disabled } }, this.label, this.showObligatory && !this.disabled && h("span", { key: '8345af7646d8cea8e66c996f0eb4abf210c9d211', class: "asterisk" }, " *"))), h("div", { key: '290a9521e39c2e1bdb1a8aacf35b2b22bf4966de', class: "dropdown-container" }, this.dropdownType && this.label && (h("div", { key: 'a9ad2741e23d31b3b0dc69a3aa89f54eaa291b04', class: "left-label" }, this.label)), this.renderTrigger()), this.helperText && !this.invalid && (h("div", { key: '8dd7cd895c1124b07020f396ac316390d4ee8cc8', class: "select-helper" }, h("span", { key: 'cdcaeb30b27baf4441d6ef87f6f553fd2b73e145' }, this.helperText))), this.invalid && this.errorText && (h("div", { key: '8e1a4da603de7b6c730a9946b63652fbe5e68321', class: "select-helper-error" }, h("dropi-icon", { key: 'f831c9f543c4f4be52d969f1d26f7d7e8816d08f', name: "Warning-circle", width: "12px", height: "12px", color: "Error-Error-500" }), h("span", { key: '1eefbade098b9743b23abee3e43836ed33ecbadb' }, this.errorText))), this.renderDropdown()));
319
+ }
320
+ static get is() { return "dropi-select"; }
321
+ static get encapsulation() { return "shadow"; }
322
+ static get formAssociated() { return true; }
323
+ static get originalStyleUrls() {
324
+ return {
325
+ "$": ["dropi-select.css"]
326
+ };
327
+ }
328
+ static get styleUrls() {
329
+ return {
330
+ "$": ["dropi-select.css"]
331
+ };
332
+ }
333
+ static get properties() {
334
+ return {
335
+ "label": {
336
+ "type": "string",
337
+ "mutable": false,
338
+ "complexType": {
339
+ "original": "string",
340
+ "resolved": "string",
341
+ "references": {}
342
+ },
343
+ "required": false,
344
+ "optional": false,
345
+ "docs": {
346
+ "tags": [],
347
+ "text": ""
348
+ },
349
+ "getter": false,
350
+ "setter": false,
351
+ "reflect": false,
352
+ "attribute": "label",
353
+ "defaultValue": "''"
354
+ },
355
+ "placeholder": {
356
+ "type": "string",
357
+ "mutable": false,
358
+ "complexType": {
359
+ "original": "string",
360
+ "resolved": "string",
361
+ "references": {}
362
+ },
363
+ "required": false,
364
+ "optional": false,
365
+ "docs": {
366
+ "tags": [],
367
+ "text": ""
368
+ },
369
+ "getter": false,
370
+ "setter": false,
371
+ "reflect": false,
372
+ "attribute": "placeholder",
373
+ "defaultValue": "'Seleccionar'"
374
+ },
375
+ "options": {
376
+ "type": "unknown",
377
+ "mutable": true,
378
+ "complexType": {
379
+ "original": "SelectOption[] | SelectOptionGroup[]",
380
+ "resolved": "SelectOptionGroup[] | SelectOption[]",
381
+ "references": {
382
+ "SelectOption": {
383
+ "location": "import",
384
+ "path": "./select.types",
385
+ "id": "src/components/dropi-select/select.types.ts::SelectOption",
386
+ "referenceLocation": "SelectOption"
387
+ },
388
+ "SelectOptionGroup": {
389
+ "location": "import",
390
+ "path": "./select.types",
391
+ "id": "src/components/dropi-select/select.types.ts::SelectOptionGroup",
392
+ "referenceLocation": "SelectOptionGroup"
393
+ }
394
+ }
395
+ },
396
+ "required": false,
397
+ "optional": false,
398
+ "docs": {
399
+ "tags": [],
400
+ "text": "Array of SelectOption or SelectOptionGroup"
401
+ },
402
+ "getter": false,
403
+ "setter": false,
404
+ "defaultValue": "[]"
405
+ },
406
+ "name": {
407
+ "type": "string",
408
+ "mutable": false,
409
+ "complexType": {
410
+ "original": "string",
411
+ "resolved": "string",
412
+ "references": {}
413
+ },
414
+ "required": false,
415
+ "optional": false,
416
+ "docs": {
417
+ "tags": [],
418
+ "text": ""
419
+ },
420
+ "getter": false,
421
+ "setter": false,
422
+ "reflect": false,
423
+ "attribute": "name",
424
+ "defaultValue": "''"
425
+ },
426
+ "disabled": {
427
+ "type": "boolean",
428
+ "mutable": false,
429
+ "complexType": {
430
+ "original": "boolean",
431
+ "resolved": "boolean",
432
+ "references": {}
433
+ },
434
+ "required": false,
435
+ "optional": false,
436
+ "docs": {
437
+ "tags": [],
438
+ "text": ""
439
+ },
440
+ "getter": false,
441
+ "setter": false,
442
+ "reflect": true,
443
+ "attribute": "disabled",
444
+ "defaultValue": "false"
445
+ },
446
+ "invalid": {
447
+ "type": "boolean",
448
+ "mutable": false,
449
+ "complexType": {
450
+ "original": "boolean",
451
+ "resolved": "boolean",
452
+ "references": {}
453
+ },
454
+ "required": false,
455
+ "optional": false,
456
+ "docs": {
457
+ "tags": [],
458
+ "text": ""
459
+ },
460
+ "getter": false,
461
+ "setter": false,
462
+ "reflect": false,
463
+ "attribute": "invalid",
464
+ "defaultValue": "false"
465
+ },
466
+ "errorText": {
467
+ "type": "string",
468
+ "mutable": false,
469
+ "complexType": {
470
+ "original": "string",
471
+ "resolved": "string",
472
+ "references": {}
473
+ },
474
+ "required": false,
475
+ "optional": false,
476
+ "docs": {
477
+ "tags": [],
478
+ "text": ""
479
+ },
480
+ "getter": false,
481
+ "setter": false,
482
+ "reflect": false,
483
+ "attribute": "error-text",
484
+ "defaultValue": "''"
485
+ },
486
+ "helperText": {
487
+ "type": "string",
488
+ "mutable": false,
489
+ "complexType": {
490
+ "original": "string",
491
+ "resolved": "string",
492
+ "references": {}
493
+ },
494
+ "required": false,
495
+ "optional": false,
496
+ "docs": {
497
+ "tags": [],
498
+ "text": ""
499
+ },
500
+ "getter": false,
501
+ "setter": false,
502
+ "reflect": false,
503
+ "attribute": "helper-text",
504
+ "defaultValue": "''"
505
+ },
506
+ "showObligatory": {
507
+ "type": "boolean",
508
+ "mutable": false,
509
+ "complexType": {
510
+ "original": "boolean",
511
+ "resolved": "boolean",
512
+ "references": {}
513
+ },
514
+ "required": false,
515
+ "optional": false,
516
+ "docs": {
517
+ "tags": [],
518
+ "text": ""
519
+ },
520
+ "getter": false,
521
+ "setter": false,
522
+ "reflect": false,
523
+ "attribute": "show-obligatory",
524
+ "defaultValue": "false"
525
+ },
526
+ "searchEnabled": {
527
+ "type": "boolean",
528
+ "mutable": false,
529
+ "complexType": {
530
+ "original": "boolean",
531
+ "resolved": "boolean",
532
+ "references": {}
533
+ },
534
+ "required": false,
535
+ "optional": false,
536
+ "docs": {
537
+ "tags": [],
538
+ "text": "Enables text search inside the dropdown"
539
+ },
540
+ "getter": false,
541
+ "setter": false,
542
+ "reflect": false,
543
+ "attribute": "search-enabled",
544
+ "defaultValue": "false"
545
+ },
546
+ "multiSelect": {
547
+ "type": "boolean",
548
+ "mutable": false,
549
+ "complexType": {
550
+ "original": "boolean",
551
+ "resolved": "boolean",
552
+ "references": {}
553
+ },
554
+ "required": false,
555
+ "optional": false,
556
+ "docs": {
557
+ "tags": [],
558
+ "text": "Allows selecting multiple options"
559
+ },
560
+ "getter": false,
561
+ "setter": false,
562
+ "reflect": false,
563
+ "attribute": "multi-select",
564
+ "defaultValue": "false"
565
+ },
566
+ "dropdownType": {
567
+ "type": "boolean",
568
+ "mutable": false,
569
+ "complexType": {
570
+ "original": "boolean",
571
+ "resolved": "boolean",
572
+ "references": {}
573
+ },
574
+ "required": false,
575
+ "optional": false,
576
+ "docs": {
577
+ "tags": [],
578
+ "text": "Renders trigger without border (inline/dropdown style)"
579
+ },
580
+ "getter": false,
581
+ "setter": false,
582
+ "reflect": false,
583
+ "attribute": "dropdown-type",
584
+ "defaultValue": "false"
585
+ },
586
+ "showCountryFlags": {
587
+ "type": "boolean",
588
+ "mutable": false,
589
+ "complexType": {
590
+ "original": "boolean",
591
+ "resolved": "boolean",
592
+ "references": {}
593
+ },
594
+ "required": false,
595
+ "optional": false,
596
+ "docs": {
597
+ "tags": [],
598
+ "text": "Show country flags next to option labels"
599
+ },
600
+ "getter": false,
601
+ "setter": false,
602
+ "reflect": false,
603
+ "attribute": "show-country-flags",
604
+ "defaultValue": "false"
605
+ },
606
+ "radioOptions": {
607
+ "type": "boolean",
608
+ "mutable": false,
609
+ "complexType": {
610
+ "original": "boolean",
611
+ "resolved": "boolean",
612
+ "references": {}
613
+ },
614
+ "required": false,
615
+ "optional": false,
616
+ "docs": {
617
+ "tags": [],
618
+ "text": "Renders options as radio buttons with optional image"
619
+ },
620
+ "getter": false,
621
+ "setter": false,
622
+ "reflect": false,
623
+ "attribute": "radio-options",
624
+ "defaultValue": "false"
625
+ },
626
+ "placeHolderSearch": {
627
+ "type": "string",
628
+ "mutable": false,
629
+ "complexType": {
630
+ "original": "string",
631
+ "resolved": "string",
632
+ "references": {}
633
+ },
634
+ "required": false,
635
+ "optional": false,
636
+ "docs": {
637
+ "tags": [],
638
+ "text": "Placeholder inside the search field"
639
+ },
640
+ "getter": false,
641
+ "setter": false,
642
+ "reflect": false,
643
+ "attribute": "place-holder-search",
644
+ "defaultValue": "'Buscar'"
645
+ },
646
+ "preIcon": {
647
+ "type": "string",
648
+ "mutable": false,
649
+ "complexType": {
650
+ "original": "string",
651
+ "resolved": "string",
652
+ "references": {}
653
+ },
654
+ "required": false,
655
+ "optional": false,
656
+ "docs": {
657
+ "tags": [],
658
+ "text": "Icon name shown before the trigger label"
659
+ },
660
+ "getter": false,
661
+ "setter": false,
662
+ "reflect": false,
663
+ "attribute": "pre-icon",
664
+ "defaultValue": "''"
665
+ },
666
+ "defaultSelectedId": {
667
+ "type": "any",
668
+ "mutable": true,
669
+ "complexType": {
670
+ "original": "string | number",
671
+ "resolved": "number | string",
672
+ "references": {}
673
+ },
674
+ "required": false,
675
+ "optional": false,
676
+ "docs": {
677
+ "tags": [],
678
+ "text": "Pre-select an option by id"
679
+ },
680
+ "getter": false,
681
+ "setter": false,
682
+ "reflect": false,
683
+ "attribute": "default-selected-id",
684
+ "defaultValue": "''"
685
+ },
686
+ "value": {
687
+ "type": "unknown",
688
+ "mutable": true,
689
+ "complexType": {
690
+ "original": "SelectOption | null",
691
+ "resolved": "SelectOption",
692
+ "references": {
693
+ "SelectOption": {
694
+ "location": "import",
695
+ "path": "./select.types",
696
+ "id": "src/components/dropi-select/select.types.ts::SelectOption",
697
+ "referenceLocation": "SelectOption"
698
+ }
699
+ }
700
+ },
701
+ "required": false,
702
+ "optional": false,
703
+ "docs": {
704
+ "tags": [],
705
+ "text": "Controlled selected option (single select)"
706
+ },
707
+ "getter": false,
708
+ "setter": false,
709
+ "defaultValue": "null"
710
+ }
711
+ };
712
+ }
713
+ static get states() {
714
+ return {
715
+ "isOpen": {},
716
+ "selectedOption": {},
717
+ "multiSelected": {},
718
+ "filteredOptions": {},
719
+ "searchTerm": {},
720
+ "dropdownStyle": {}
721
+ };
722
+ }
723
+ static get events() {
724
+ return [{
725
+ "method": "dropiChange",
726
+ "name": "dropiChange",
727
+ "bubbles": true,
728
+ "cancelable": true,
729
+ "composed": true,
730
+ "docs": {
731
+ "tags": [],
732
+ "text": "Emitted when an option is selected (single) or selection changes (multi)"
733
+ },
734
+ "complexType": {
735
+ "original": "SelectOption | SelectOption[]",
736
+ "resolved": "SelectOption | SelectOption[]",
737
+ "references": {
738
+ "SelectOption": {
739
+ "location": "import",
740
+ "path": "./select.types",
741
+ "id": "src/components/dropi-select/select.types.ts::SelectOption",
742
+ "referenceLocation": "SelectOption"
743
+ }
744
+ }
745
+ }
746
+ }, {
747
+ "method": "dropiClear",
748
+ "name": "dropiClear",
749
+ "bubbles": true,
750
+ "cancelable": true,
751
+ "composed": true,
752
+ "docs": {
753
+ "tags": [],
754
+ "text": "Emitted when the selection is cleared"
755
+ },
756
+ "complexType": {
757
+ "original": "void",
758
+ "resolved": "void",
759
+ "references": {}
760
+ }
761
+ }, {
762
+ "method": "dropiSearch",
763
+ "name": "dropiSearch",
764
+ "bubbles": true,
765
+ "cancelable": true,
766
+ "composed": true,
767
+ "docs": {
768
+ "tags": [],
769
+ "text": "Emitted on search input"
770
+ },
771
+ "complexType": {
772
+ "original": "string",
773
+ "resolved": "string",
774
+ "references": {}
775
+ }
776
+ }, {
777
+ "method": "dropiScrollEnd",
778
+ "name": "dropiScrollEnd",
779
+ "bubbles": true,
780
+ "cancelable": true,
781
+ "composed": true,
782
+ "docs": {
783
+ "tags": [],
784
+ "text": "Emitted when the list is scrolled to the end"
785
+ },
786
+ "complexType": {
787
+ "original": "void",
788
+ "resolved": "void",
789
+ "references": {}
790
+ }
791
+ }, {
792
+ "method": "dropiKeyEnter",
793
+ "name": "dropiKeyEnter",
794
+ "bubbles": true,
795
+ "cancelable": true,
796
+ "composed": true,
797
+ "docs": {
798
+ "tags": [],
799
+ "text": "Emitted on Enter key inside search"
800
+ },
801
+ "complexType": {
802
+ "original": "KeyboardEvent",
803
+ "resolved": "KeyboardEvent",
804
+ "references": {
805
+ "KeyboardEvent": {
806
+ "location": "global",
807
+ "id": "global::KeyboardEvent"
808
+ }
809
+ }
810
+ }
811
+ }];
812
+ }
813
+ static get methods() {
814
+ return {
815
+ "setById": {
816
+ "complexType": {
817
+ "signature": "(id: string | number) => Promise<void>",
818
+ "parameters": [{
819
+ "name": "id",
820
+ "type": "string | number",
821
+ "docs": ""
822
+ }],
823
+ "references": {
824
+ "Promise": {
825
+ "location": "global",
826
+ "id": "global::Promise"
827
+ },
828
+ "SelectOption": {
829
+ "location": "import",
830
+ "path": "./select.types",
831
+ "id": "src/components/dropi-select/select.types.ts::SelectOption",
832
+ "referenceLocation": "SelectOption"
833
+ }
834
+ },
835
+ "return": "Promise<void>"
836
+ },
837
+ "docs": {
838
+ "text": "Select an option by its id",
839
+ "tags": []
840
+ }
841
+ },
842
+ "setByLabel": {
843
+ "complexType": {
844
+ "signature": "(label: string) => Promise<void>",
845
+ "parameters": [{
846
+ "name": "label",
847
+ "type": "string",
848
+ "docs": ""
849
+ }],
850
+ "references": {
851
+ "Promise": {
852
+ "location": "global",
853
+ "id": "global::Promise"
854
+ },
855
+ "SelectOption": {
856
+ "location": "import",
857
+ "path": "./select.types",
858
+ "id": "src/components/dropi-select/select.types.ts::SelectOption",
859
+ "referenceLocation": "SelectOption"
860
+ }
861
+ },
862
+ "return": "Promise<void>"
863
+ },
864
+ "docs": {
865
+ "text": "Select an option by its label",
866
+ "tags": []
867
+ }
868
+ },
869
+ "clearSelection": {
870
+ "complexType": {
871
+ "signature": "() => Promise<void>",
872
+ "parameters": [],
873
+ "references": {
874
+ "Promise": {
875
+ "location": "global",
876
+ "id": "global::Promise"
877
+ }
878
+ },
879
+ "return": "Promise<void>"
880
+ },
881
+ "docs": {
882
+ "text": "Clear the current selection",
883
+ "tags": []
884
+ }
885
+ },
886
+ "resetMultiSelect": {
887
+ "complexType": {
888
+ "signature": "(_placeholder?: string) => Promise<void>",
889
+ "parameters": [{
890
+ "name": "_placeholder",
891
+ "type": "string",
892
+ "docs": ""
893
+ }],
894
+ "references": {
895
+ "Promise": {
896
+ "location": "global",
897
+ "id": "global::Promise"
898
+ }
899
+ },
900
+ "return": "Promise<void>"
901
+ },
902
+ "docs": {
903
+ "text": "Reset multi-select state and show a placeholder label",
904
+ "tags": []
905
+ }
906
+ }
907
+ };
908
+ }
909
+ static get elementRef() { return "el"; }
910
+ static get watchers() {
911
+ return [{
912
+ "propName": "options",
913
+ "methodName": "optionsChanged"
914
+ }, {
915
+ "propName": "defaultSelectedId",
916
+ "methodName": "defaultChanged"
917
+ }, {
918
+ "propName": "value",
919
+ "methodName": "valueChanged"
920
+ }];
921
+ }
922
+ static get listeners() {
923
+ return [{
924
+ "name": "click",
925
+ "method": "handleOutsideClick",
926
+ "target": "document",
927
+ "capture": false,
928
+ "passive": false
929
+ }];
930
+ }
931
+ static get attachInternalsMemberName() { return "internals"; }
932
+ }