@neural-ui/core 1.1.2 → 1.2.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.
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { makeEnvironmentProviders, inject, computed, Injectable, signal, input, forwardRef, ChangeDetectionStrategy, ViewEncapsulation, Component, ElementRef, TemplateRef, Directive,
|
|
2
|
+
import { makeEnvironmentProviders, inject, computed, Injectable, signal, input, forwardRef, ChangeDetectionStrategy, ViewEncapsulation, Component, ElementRef, TemplateRef, Directive, effect, untracked, contentChild, output, InjectionToken, viewChild, Injector, HostListener, afterNextRender, DestroyRef } from '@angular/core';
|
|
3
3
|
import { provideIcons, provideNgIconsConfig, NgIcon } from '@ng-icons/core';
|
|
4
4
|
import { lucideMinus, lucideTrendingDown, lucideTrendingUp, lucideInbox, lucideExternalLink, lucideChevronLeft, lucideChevronRight, lucideX, lucideInfo, lucideAlertTriangle, lucideXCircle, lucideCheckCircle, lucideAlertCircle } from '@ng-icons/lucide';
|
|
5
5
|
import { toSignal } from '@angular/core/rxjs-interop';
|
|
@@ -1536,6 +1536,21 @@ let _neuMultiselectIdSeq = 0;
|
|
|
1536
1536
|
*/
|
|
1537
1537
|
class NeuMultiselectComponent {
|
|
1538
1538
|
elementRef = inject(ElementRef);
|
|
1539
|
+
_urlState = inject(NeuUrlStateService);
|
|
1540
|
+
constructor() {
|
|
1541
|
+
effect(() => {
|
|
1542
|
+
const param = this.urlParam();
|
|
1543
|
+
if (!param)
|
|
1544
|
+
return;
|
|
1545
|
+
const urlRaw = this._urlState.getParam(param)();
|
|
1546
|
+
const urlVals = urlRaw ? urlRaw.split(',').filter(Boolean) : [];
|
|
1547
|
+
const current = untracked(() => this._values());
|
|
1548
|
+
if (JSON.stringify(urlVals) !== JSON.stringify(current)) {
|
|
1549
|
+
this._values.set(urlVals);
|
|
1550
|
+
this._onChange(urlVals);
|
|
1551
|
+
}
|
|
1552
|
+
});
|
|
1553
|
+
}
|
|
1539
1554
|
/** @internal */
|
|
1540
1555
|
_triggerId = `neu-multiselect-trigger-${_neuMultiselectIdSeq++}`;
|
|
1541
1556
|
/** Template personalizado para cada opción del dropdown */
|
|
@@ -1564,6 +1579,18 @@ class NeuMultiselectComponent {
|
|
|
1564
1579
|
clearable = input(false, ...(ngDevMode ? [{ debugName: "clearable" }] : /* istanbul ignore next */ []));
|
|
1565
1580
|
/** Aria-label del botón clear que aparece en el trigger */
|
|
1566
1581
|
clearAriaLabel = input('Limpiar selección', ...(ngDevMode ? [{ debugName: "clearAriaLabel" }] : /* istanbul ignore next */ []));
|
|
1582
|
+
/**
|
|
1583
|
+
* Sincroniza los valores seleccionados con este query param de la URL.
|
|
1584
|
+
* Los valores se codifican como lista separada por comas: `?{urlParam}=a,b,c`.
|
|
1585
|
+
* Pasar `null` (default) deshabilita la sincronización.
|
|
1586
|
+
*/
|
|
1587
|
+
urlParam = input(null, ...(ngDevMode ? [{ debugName: "urlParam" }] : /* istanbul ignore next */ []));
|
|
1588
|
+
/**
|
|
1589
|
+
* Emite el array de NeuSelectOption completo (incluyendo data) al cambiar la selección.
|
|
1590
|
+
* Emite [] al limpiar toda la selección.
|
|
1591
|
+
* Los valores de ngModel / formControl siguen siendo string[].
|
|
1592
|
+
*/
|
|
1593
|
+
selectionChange = output();
|
|
1567
1594
|
// --- Estado interno ---
|
|
1568
1595
|
_values = signal([], ...(ngDevMode ? [{ debugName: "_values" }] : /* istanbul ignore next */ []));
|
|
1569
1596
|
isOpen = signal(false, ...(ngDevMode ? [{ debugName: "isOpen" }] : /* istanbul ignore next */ []));
|
|
@@ -1652,6 +1679,10 @@ class NeuMultiselectComponent {
|
|
|
1652
1679
|
: [...current, option.value];
|
|
1653
1680
|
this._values.set(next);
|
|
1654
1681
|
this._onChange(next);
|
|
1682
|
+
this.selectionChange.emit(this.options().filter((o) => next.includes(o.value)));
|
|
1683
|
+
const param = this.urlParam();
|
|
1684
|
+
if (param)
|
|
1685
|
+
this._urlState.setParam(param, next.length ? next.join(',') : null);
|
|
1655
1686
|
}
|
|
1656
1687
|
removeValue(value, event) {
|
|
1657
1688
|
event.stopPropagation();
|
|
@@ -1659,12 +1690,20 @@ class NeuMultiselectComponent {
|
|
|
1659
1690
|
this._values.set(next);
|
|
1660
1691
|
this._onChange(next);
|
|
1661
1692
|
this._onTouched();
|
|
1693
|
+
this.selectionChange.emit(this.options().filter((o) => next.includes(o.value)));
|
|
1694
|
+
const param = this.urlParam();
|
|
1695
|
+
if (param)
|
|
1696
|
+
this._urlState.setParam(param, next.length ? next.join(',') : null);
|
|
1662
1697
|
}
|
|
1663
1698
|
clearAll(event) {
|
|
1664
1699
|
event.stopPropagation();
|
|
1665
1700
|
this._values.set([]);
|
|
1666
1701
|
this._onChange([]);
|
|
1667
1702
|
this._onTouched();
|
|
1703
|
+
this.selectionChange.emit([]);
|
|
1704
|
+
const param = this.urlParam();
|
|
1705
|
+
if (param)
|
|
1706
|
+
this._urlState.setParam(param, null);
|
|
1668
1707
|
}
|
|
1669
1708
|
toggleChipMode(event) {
|
|
1670
1709
|
event.stopPropagation();
|
|
@@ -1676,7 +1715,7 @@ class NeuMultiselectComponent {
|
|
|
1676
1715
|
}
|
|
1677
1716
|
}
|
|
1678
1717
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.7", ngImport: i0, type: NeuMultiselectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
1679
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.7", type: NeuMultiselectComponent, isStandalone: true, selector: "neu-multiselect", inputs: { options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, floatingLabel: { classPropertyName: "floatingLabel", publicName: "floatingLabel", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, noResultsMessage: { classPropertyName: "noResultsMessage", publicName: "noResultsMessage", isSignal: true, isRequired: false, transformFunction: null }, clearAllLabel: { classPropertyName: "clearAllLabel", publicName: "clearAllLabel", isSignal: true, isRequired: false, transformFunction: null }, clearable: { classPropertyName: "clearable", publicName: "clearable", isSignal: true, isRequired: false, transformFunction: null }, clearAriaLabel: { classPropertyName: "clearAriaLabel", publicName: "clearAriaLabel", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "document:click": "onDocumentClick($event)", "keydown.escape": "close()" } }, providers: [
|
|
1718
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.7", type: NeuMultiselectComponent, isStandalone: true, selector: "neu-multiselect", inputs: { options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, floatingLabel: { classPropertyName: "floatingLabel", publicName: "floatingLabel", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, noResultsMessage: { classPropertyName: "noResultsMessage", publicName: "noResultsMessage", isSignal: true, isRequired: false, transformFunction: null }, clearAllLabel: { classPropertyName: "clearAllLabel", publicName: "clearAllLabel", isSignal: true, isRequired: false, transformFunction: null }, clearable: { classPropertyName: "clearable", publicName: "clearable", isSignal: true, isRequired: false, transformFunction: null }, clearAriaLabel: { classPropertyName: "clearAriaLabel", publicName: "clearAriaLabel", isSignal: true, isRequired: false, transformFunction: null }, urlParam: { classPropertyName: "urlParam", publicName: "urlParam", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { selectionChange: "selectionChange" }, host: { listeners: { "document:click": "onDocumentClick($event)", "keydown.escape": "close()" } }, providers: [
|
|
1680
1719
|
{
|
|
1681
1720
|
provide: NG_VALUE_ACCESSOR,
|
|
1682
1721
|
useExisting: forwardRef(() => NeuMultiselectComponent),
|
|
@@ -2120,7 +2159,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.7", ngImpor
|
|
|
2120
2159
|
<p class="neu-multiselect__error" role="alert">{{ errorMessage() }}</p>
|
|
2121
2160
|
}
|
|
2122
2161
|
`, styles: [".neu-multiselect__static-label{display:block;font-size:var(--neu-text-sm);font-weight:500;color:var(--neu-text-muted);margin-bottom:var(--neu-space-2)}.neu-multiselect__label{position:absolute;left:var(--neu-space-3);top:50%;transform:translateY(-50%);font-size:var(--neu-text-base);color:var(--neu-text-muted);pointer-events:none;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:calc(100% - var(--neu-space-8));transition:top var(--neu-transition),font-size var(--neu-transition),color var(--neu-transition),transform var(--neu-transition),padding var(--neu-transition),background var(--neu-transition)}.neu-multiselect--open .neu-multiselect__label,.neu-multiselect--has-value .neu-multiselect__label{top:0;transform:translateY(-50%);font-size:12px;font-weight:600;letter-spacing:.01em;background:var(--neu-surface);padding:0 4px;left:calc(var(--neu-space-3) - 4px)}.neu-multiselect--open .neu-multiselect__label{color:var(--neu-primary)}.neu-multiselect--error .neu-multiselect__label{color:var(--neu-error)}.neu-multiselect--disabled .neu-multiselect__label{background:var(--neu-surface-2)}.neu-multiselect{position:relative;font-family:var(--neu-font-sans)}.neu-multiselect__trigger{display:flex;align-items:center;width:100%;min-height:48px;padding:var(--neu-space-2) var(--neu-space-3);padding-right:36px;background:var(--neu-surface);border:1.5px solid var(--neu-border);border-radius:var(--neu-radius);cursor:pointer;text-align:left;transition:border-color var(--neu-transition),box-shadow var(--neu-transition)}.neu-multiselect__trigger:hover:not(:disabled){border-color:var(--neu-border-hover)}.neu-multiselect__trigger:disabled{opacity:.6;cursor:not-allowed;background:var(--neu-surface-2)}.neu-multiselect--open .neu-multiselect__trigger{border-color:var(--neu-primary);box-shadow:0 0 0 3px #007aff1f}.neu-multiselect--error .neu-multiselect__trigger{border-color:var(--neu-error)}.neu-multiselect__chips{display:flex;flex-wrap:wrap;gap:var(--neu-space-1);flex:1;min-width:0}.neu-multiselect__placeholder{color:var(--neu-text-disabled);font-size:var(--neu-text-base);line-height:1.5}.neu-multiselect:not(.neu-multiselect--no-float):not(.neu-multiselect--open) .neu-multiselect__placeholder{visibility:hidden}.neu-multiselect__chip{display:inline-flex;align-items:center;gap:4px;padding:2px 4px 2px 8px;background:var(--neu-primary-soft, rgba(0, 122, 255, .1));color:var(--neu-primary);border-radius:var(--neu-radius-sm);font-size:var(--neu-text-xs);font-weight:500;max-width:160px;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.neu-multiselect__chip-remove{display:flex;align-items:center;justify-content:center;width:16px;height:16px;padding:0;border:none;background:transparent;cursor:pointer;color:inherit;opacity:.7;border-radius:2px;transition:opacity var(--neu-transition);flex-shrink:0}.neu-multiselect__chip-remove:hover{opacity:1}.neu-multiselect__chip-remove svg{width:10px;height:10px}.neu-multiselect__clear{display:inline-flex;align-items:center;justify-content:center;width:20px;height:20px;margin-right:2px;padding:0;border:none;background:transparent;color:var(--neu-text-muted);cursor:pointer;border-radius:var(--neu-radius-sm);flex-shrink:0;transition:color var(--neu-transition),background var(--neu-transition)}.neu-multiselect__clear svg{width:14px;height:14px}.neu-multiselect__clear:hover{color:var(--neu-text);background:var(--neu-surface-3)}.neu-multiselect__chevron{position:absolute;right:var(--neu-space-3);top:50%;transform:translateY(-50%);width:16px;height:16px;color:var(--neu-text-muted);pointer-events:none;transition:transform var(--neu-transition);flex-shrink:0}.neu-multiselect--open .neu-multiselect__chevron{transform:translateY(-50%) rotate(180deg)}.neu-multiselect__panel{position:absolute;top:calc(100% + 6px);left:0;right:0;z-index:200;background:var(--neu-surface);border:1.5px solid var(--neu-border);border-radius:var(--neu-radius);box-shadow:var(--neu-shadow-lg);overflow:hidden;max-height:280px;display:flex;flex-direction:column;animation:neu-multiselect-fade-in .12s ease}@keyframes neu-multiselect-fade-in{0%{opacity:0;transform:translateY(-4px)}to{opacity:1;transform:translateY(0)}}.neu-multiselect__search{padding:var(--neu-space-2);border-bottom:1px solid var(--neu-border);flex-shrink:0}.neu-multiselect__search-input{width:100%;height:34px;padding:0 var(--neu-space-3);border:1.5px solid var(--neu-border);border-radius:var(--neu-radius-sm);background:var(--neu-bg);font-family:var(--neu-font-sans);font-size:var(--neu-text-sm);color:var(--neu-text);outline:none;transition:border-color var(--neu-transition),box-shadow var(--neu-transition)}.neu-multiselect__search-input:focus{border-color:var(--neu-primary);box-shadow:0 0 0 2px #007aff1f}.neu-multiselect__search-input::placeholder{color:var(--neu-text-disabled)}.neu-multiselect__options{flex:1;overflow-y:auto;min-height:0}.neu-multiselect__option{display:flex;align-items:center;gap:var(--neu-space-2);padding:10px var(--neu-space-3);cursor:pointer;font-size:var(--neu-text-sm);color:var(--neu-text);transition:background var(--neu-transition)}.neu-multiselect__option:hover:not(.neu-multiselect__option--disabled){background:var(--neu-surface-2)}.neu-multiselect__option--selected{background:var(--neu-primary-soft, rgba(0, 122, 255, .06));color:var(--neu-primary);font-weight:500}.neu-multiselect__option--disabled{opacity:.4;cursor:not-allowed}.neu-multiselect__checkbox{display:flex;align-items:center;justify-content:center;width:16px;height:16px;border-radius:3px;border:1.5px solid var(--neu-border);background:var(--neu-bg);flex-shrink:0;transition:border-color var(--neu-transition),background var(--neu-transition)}.neu-multiselect__checkbox--checked{background:var(--neu-primary);border-color:var(--neu-primary);color:#fff}.neu-multiselect__checkbox-check{width:10px;height:8px;opacity:0;transform:scale(.6);transition:opacity .12s ease,transform .12s ease}.neu-multiselect__checkbox--checked .neu-multiselect__checkbox-check{opacity:1;transform:scale(1)}.neu-multiselect__empty{padding:var(--neu-space-4);text-align:center;font-size:var(--neu-text-sm);color:var(--neu-text-disabled);font-family:var(--neu-font-sans)}.neu-multiselect__footer{display:flex;align-items:center;justify-content:space-between;padding:var(--neu-space-2) var(--neu-space-3);border-top:1px solid var(--neu-border);background:var(--neu-surface);flex-shrink:0}.neu-multiselect__footer-count{font-size:var(--neu-text-xs);color:var(--neu-text-muted)}.neu-multiselect__footer-actions{display:flex;align-items:center;gap:var(--neu-space-2)}.neu-multiselect__footer-mode{background:none;border:1px solid var(--neu-border);border-radius:var(--neu-radius-sm);padding:2px 6px;font-size:var(--neu-text-xs);font-family:var(--neu-font-sans);color:var(--neu-text-muted);cursor:pointer;line-height:1.4}.neu-multiselect__footer-mode:hover{background:var(--neu-surface-2);color:var(--neu-text)}.neu-multiselect__footer-clear{background:none;border:none;padding:0;font-size:var(--neu-text-xs);font-family:var(--neu-font-sans);color:var(--neu-primary);cursor:pointer;font-weight:500}.neu-multiselect__footer-clear:hover{text-decoration:underline}.neu-multiselect__count-badge{display:inline-flex;align-items:center;padding:2px 10px;background:var(--neu-primary-100, rgba(14, 165, 233, .12));color:var(--neu-primary);border-radius:var(--neu-radius-full);font-size:var(--neu-text-sm);font-weight:500}.neu-multiselect__chip--overflow{background:var(--neu-surface-2);color:var(--neu-text-muted);border:1px dashed var(--neu-border);cursor:default;pointer-events:none}.neu-multiselect__error{margin-top:var(--neu-space-1);font-size:var(--neu-text-xs);color:var(--neu-error-text, var(--neu-error));font-family:var(--neu-font-sans)}\n"] }]
|
|
2123
|
-
}], propDecorators: { itemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuMultiselectItemDirective), { isSignal: true }] }], options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], floatingLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "floatingLabel", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], errorMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "errorMessage", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], searchable: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchable", required: false }] }], searchPlaceholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchPlaceholder", required: false }] }], noResultsMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "noResultsMessage", required: false }] }], clearAllLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAllLabel", required: false }] }], clearable: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearable", required: false }] }], clearAriaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAriaLabel", required: false }] }] } });
|
|
2162
|
+
}], ctorParameters: () => [], propDecorators: { itemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuMultiselectItemDirective), { isSignal: true }] }], options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], floatingLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "floatingLabel", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], errorMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "errorMessage", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], searchable: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchable", required: false }] }], searchPlaceholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchPlaceholder", required: false }] }], noResultsMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "noResultsMessage", required: false }] }], clearAllLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAllLabel", required: false }] }], clearable: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearable", required: false }] }], clearAriaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAriaLabel", required: false }] }], urlParam: [{ type: i0.Input, args: [{ isSignal: true, alias: "urlParam", required: false }] }], selectionChange: [{ type: i0.Output, args: ["selectionChange"] }] } });
|
|
2124
2163
|
|
|
2125
2164
|
/** Token para que neu-radio encuentre a su grupo padre */
|
|
2126
2165
|
const NEU_RADIO_GROUP = new InjectionToken('NEU_RADIO_GROUP');
|
|
@@ -2342,6 +2381,19 @@ let _neuSelectIdSeq = 0;
|
|
|
2342
2381
|
*/
|
|
2343
2382
|
class NeuSelectComponent {
|
|
2344
2383
|
elementRef = inject(ElementRef);
|
|
2384
|
+
_urlState = inject(NeuUrlStateService);
|
|
2385
|
+
constructor() {
|
|
2386
|
+
effect(() => {
|
|
2387
|
+
const param = this.urlParam();
|
|
2388
|
+
if (!param)
|
|
2389
|
+
return;
|
|
2390
|
+
const urlVal = this._urlState.getParam(param)();
|
|
2391
|
+
if (urlVal !== untracked(() => this._value())) {
|
|
2392
|
+
this._value.set(urlVal);
|
|
2393
|
+
this._onChange(urlVal);
|
|
2394
|
+
}
|
|
2395
|
+
});
|
|
2396
|
+
}
|
|
2345
2397
|
/** @internal — ID \u00fanico para asociar label con trigger */
|
|
2346
2398
|
_triggerId = `neu-select-trigger-${_neuSelectIdSeq++}`;
|
|
2347
2399
|
/** Template personalizado para cada opción del dropdown */
|
|
@@ -2370,6 +2422,18 @@ class NeuSelectComponent {
|
|
|
2370
2422
|
noResultsMessage = input('Sin resultados', ...(ngDevMode ? [{ debugName: "noResultsMessage" }] : /* istanbul ignore next */ []));
|
|
2371
2423
|
/** Aria-label del botón de limpiar */
|
|
2372
2424
|
clearAriaLabel = input('Limpiar selección', ...(ngDevMode ? [{ debugName: "clearAriaLabel" }] : /* istanbul ignore next */ []));
|
|
2425
|
+
/**
|
|
2426
|
+
* Sincroniza el valor seleccionado con este query param de la URL.
|
|
2427
|
+
* Al seleccionar una opción se añade `?{urlParam}=value` a la URL.
|
|
2428
|
+
* Pasar `null` (default) deshabilita la sincronización.
|
|
2429
|
+
*/
|
|
2430
|
+
urlParam = input(null, ...(ngDevMode ? [{ debugName: "urlParam" }] : /* istanbul ignore next */ []));
|
|
2431
|
+
/**
|
|
2432
|
+
* Emite el objeto NeuSelectOption completo (incluyendo data) al seleccionar una opción.
|
|
2433
|
+
* Emite null al limpiar la selección.
|
|
2434
|
+
* El valor de ngModel / formControl sigue siendo string.
|
|
2435
|
+
*/
|
|
2436
|
+
selectionChange = output();
|
|
2373
2437
|
// Estado interno
|
|
2374
2438
|
_value = signal(null, ...(ngDevMode ? [{ debugName: "_value" }] : /* istanbul ignore next */ []));
|
|
2375
2439
|
isOpen = signal(false, ...(ngDevMode ? [{ debugName: "isOpen" }] : /* istanbul ignore next */ []));
|
|
@@ -2442,7 +2506,11 @@ class NeuSelectComponent {
|
|
|
2442
2506
|
event.stopPropagation();
|
|
2443
2507
|
this._value.set(null);
|
|
2444
2508
|
this._onChange(null);
|
|
2509
|
+
const param = this.urlParam();
|
|
2510
|
+
if (param)
|
|
2511
|
+
this._urlState.setParam(param, null);
|
|
2445
2512
|
this._onTouched();
|
|
2513
|
+
this.selectionChange.emit(null);
|
|
2446
2514
|
this.close();
|
|
2447
2515
|
}
|
|
2448
2516
|
selectOption(option) {
|
|
@@ -2450,6 +2518,10 @@ class NeuSelectComponent {
|
|
|
2450
2518
|
return;
|
|
2451
2519
|
this._value.set(option.value);
|
|
2452
2520
|
this._onChange(option.value);
|
|
2521
|
+
const param = this.urlParam();
|
|
2522
|
+
if (param)
|
|
2523
|
+
this._urlState.setParam(param, option.value);
|
|
2524
|
+
this.selectionChange.emit(option);
|
|
2453
2525
|
this.close();
|
|
2454
2526
|
}
|
|
2455
2527
|
onDocumentClick(event) {
|
|
@@ -2458,7 +2530,7 @@ class NeuSelectComponent {
|
|
|
2458
2530
|
}
|
|
2459
2531
|
}
|
|
2460
2532
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.7", ngImport: i0, type: NeuSelectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
2461
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.7", type: NeuSelectComponent, isStandalone: true, selector: "neu-select", inputs: { options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, floatingLabel: { classPropertyName: "floatingLabel", publicName: "floatingLabel", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, clearable: { classPropertyName: "clearable", publicName: "clearable", isSignal: true, isRequired: false, transformFunction: null }, noResultsMessage: { classPropertyName: "noResultsMessage", publicName: "noResultsMessage", isSignal: true, isRequired: false, transformFunction: null }, clearAriaLabel: { classPropertyName: "clearAriaLabel", publicName: "clearAriaLabel", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "document:click": "onDocumentClick($event)", "keydown.escape": "close()" } }, providers: [
|
|
2533
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.7", type: NeuSelectComponent, isStandalone: true, selector: "neu-select", inputs: { options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, errorMessage: { classPropertyName: "errorMessage", publicName: "errorMessage", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, floatingLabel: { classPropertyName: "floatingLabel", publicName: "floatingLabel", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, searchPlaceholder: { classPropertyName: "searchPlaceholder", publicName: "searchPlaceholder", isSignal: true, isRequired: false, transformFunction: null }, clearable: { classPropertyName: "clearable", publicName: "clearable", isSignal: true, isRequired: false, transformFunction: null }, noResultsMessage: { classPropertyName: "noResultsMessage", publicName: "noResultsMessage", isSignal: true, isRequired: false, transformFunction: null }, clearAriaLabel: { classPropertyName: "clearAriaLabel", publicName: "clearAriaLabel", isSignal: true, isRequired: false, transformFunction: null }, urlParam: { classPropertyName: "urlParam", publicName: "urlParam", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { selectionChange: "selectionChange" }, host: { listeners: { "document:click": "onDocumentClick($event)", "keydown.escape": "close()" } }, providers: [
|
|
2462
2534
|
{
|
|
2463
2535
|
provide: NG_VALUE_ACCESSOR,
|
|
2464
2536
|
useExisting: forwardRef(() => NeuSelectComponent),
|
|
@@ -2784,7 +2856,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.7", ngImpor
|
|
|
2784
2856
|
<p class="neu-select__error" role="alert">{{ errorMessage() }}</p>
|
|
2785
2857
|
}
|
|
2786
2858
|
`, styles: [".neu-select{position:relative;display:block}.neu-select--disabled{opacity:.6;pointer-events:none}.neu-select__trigger{display:flex;align-items:center;width:100%;height:48px;padding:0 var(--neu-space-3);padding-right:36px;background:var(--neu-surface);border:1.5px solid var(--neu-border);border-radius:var(--neu-radius);font-family:var(--neu-font-sans);font-size:var(--neu-text-base);color:var(--neu-text);cursor:pointer;text-align:left;outline:none;transition:border-color var(--neu-transition),box-shadow var(--neu-transition);position:relative}.neu-select__trigger:hover:not(:disabled){border-color:var(--neu-border-hover)}.neu-select__trigger:focus-visible{border-color:var(--neu-primary);box-shadow:0 0 0 3px #007aff1f}.neu-select--open .neu-select__trigger{border-color:var(--neu-primary);box-shadow:0 0 0 3px #007aff1f;border-bottom-left-radius:0;border-bottom-right-radius:0}.neu-select--error .neu-select__trigger{border-color:var(--neu-error)}.neu-select--error .neu-select__trigger:focus-visible{box-shadow:0 0 0 3px #ef44441f}.neu-select__label{position:absolute;left:var(--neu-space-3);top:50%;transform:translateY(-50%);font-size:var(--neu-text-base);color:var(--neu-text-muted);pointer-events:none;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:calc(100% - var(--neu-space-6));transition:top var(--neu-transition),font-size var(--neu-transition),color var(--neu-transition),transform var(--neu-transition),padding var(--neu-transition),background var(--neu-transition)}.neu-select--open .neu-select__label,.neu-select--has-value .neu-select__label{top:0;transform:translateY(-50%);font-size:12px;font-weight:600;letter-spacing:.01em;background:var(--neu-surface);padding:0 4px;left:calc(var(--neu-space-3) - 4px)}.neu-select--open .neu-select__label{color:var(--neu-primary)}.neu-select--error .neu-select__label{color:var(--neu-error)}.neu-select--disabled .neu-select__label{background:var(--neu-surface-2)}.neu-select__value{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.neu-select--no-float .neu-select__value{padding-top:0}.neu-select__placeholder{color:var(--neu-text-disabled)}.neu-select:not(.neu-select--no-float):not(.neu-select--open) .neu-select__placeholder{visibility:hidden}.neu-select__chevron{position:absolute;right:var(--neu-space-3);top:50%;transform:translateY(-50%);width:18px;height:18px;color:var(--neu-text-muted);flex-shrink:0;transition:transform var(--neu-transition)}.neu-select--open .neu-select__chevron{transform:translateY(-50%) rotate(180deg);color:var(--neu-primary)}.neu-select__clear{display:inline-flex;align-items:center;justify-content:center;width:20px;height:20px;margin-right:2px;padding:0;border:none;background:transparent;color:var(--neu-text-muted);cursor:pointer;border-radius:var(--neu-radius-sm);flex-shrink:0;transition:color var(--neu-transition),background var(--neu-transition)}.neu-select__clear svg{width:14px;height:14px}.neu-select__clear:hover{color:var(--neu-text);background:var(--neu-surface-3)}.neu-select__panel{position:absolute;top:100%;left:0;right:0;z-index:var(--neu-z-dropdown);background:var(--neu-surface);border:1.5px solid var(--neu-primary);border-top:none;border-bottom-left-radius:var(--neu-radius);border-bottom-right-radius:var(--neu-radius);box-shadow:var(--neu-shadow-lg);max-height:240px;overflow-y:auto;scrollbar-width:thin;scrollbar-color:var(--neu-surface-3) transparent;animation:neu-select-open .15s ease forwards}.neu-select__panel::-webkit-scrollbar{width:4px}.neu-select__panel::-webkit-scrollbar-thumb{background:var(--neu-surface-3);border-radius:99px}@keyframes neu-select-open{0%{opacity:0;transform:translateY(-4px)}to{opacity:1;transform:translateY(0)}}.neu-select__option{display:flex;align-items:center;gap:var(--neu-space-2);padding:var(--neu-space-3) var(--neu-space-4);font-size:var(--neu-text-sm);color:var(--neu-text);cursor:pointer;transition:background-color var(--neu-transition)}.neu-select__option:hover:not(.neu-select__option--disabled){background:var(--neu-primary-50);color:var(--neu-primary)}.neu-select__option--selected{color:var(--neu-primary);font-weight:600;background:var(--neu-primary-50)}.neu-select__option--disabled{opacity:.4;cursor:not-allowed}.neu-select__check{width:14px;height:14px;flex-shrink:0}.neu-select__error{margin-top:var(--neu-space-1);font-size:var(--neu-text-xs);color:var(--neu-error-text);font-family:var(--neu-font-sans)}.neu-select__static-label{display:block;font-size:var(--neu-text-sm);font-weight:500;color:var(--neu-text-muted);margin-bottom:var(--neu-space-2)}.neu-select__search{padding:var(--neu-space-2);border-bottom:1px solid var(--neu-border);position:sticky;top:0;background:var(--neu-surface);z-index:1}.neu-select__search-input{width:100%;height:34px;padding:0 var(--neu-space-3);border:1.5px solid var(--neu-border);border-radius:var(--neu-radius-sm);background:var(--neu-bg);font-family:var(--neu-font-sans);font-size:var(--neu-text-sm);color:var(--neu-text);outline:none;transition:border-color var(--neu-transition),box-shadow var(--neu-transition)}.neu-select__search-input:focus{border-color:var(--neu-primary);box-shadow:0 0 0 2px #007aff1f}.neu-select__search-input::placeholder{color:var(--neu-text-disabled)}.neu-select__empty{padding:var(--neu-space-4);text-align:center;font-size:var(--neu-text-sm);color:var(--neu-text-disabled);font-family:var(--neu-font-sans)}\n"] }]
|
|
2787
|
-
}], propDecorators: { itemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuSelectItemDirective), { isSignal: true }] }], selectedItemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuSelectSelectedDirective), { isSignal: true }] }], options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], errorMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "errorMessage", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], floatingLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "floatingLabel", required: false }] }], searchable: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchable", required: false }] }], searchPlaceholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchPlaceholder", required: false }] }], clearable: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearable", required: false }] }], noResultsMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "noResultsMessage", required: false }] }], clearAriaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAriaLabel", required: false }] }] } });
|
|
2859
|
+
}], ctorParameters: () => [], propDecorators: { itemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuSelectItemDirective), { isSignal: true }] }], selectedItemTpl: [{ type: i0.ContentChild, args: [i0.forwardRef(() => NeuSelectSelectedDirective), { isSignal: true }] }], options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], errorMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "errorMessage", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], floatingLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "floatingLabel", required: false }] }], searchable: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchable", required: false }] }], searchPlaceholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchPlaceholder", required: false }] }], clearable: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearable", required: false }] }], noResultsMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "noResultsMessage", required: false }] }], clearAriaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "clearAriaLabel", required: false }] }], urlParam: [{ type: i0.Input, args: [{ isSignal: true, alias: "urlParam", required: false }] }], selectionChange: [{ type: i0.Output, args: ["selectionChange"] }] } });
|
|
2788
2860
|
|
|
2789
2861
|
/**
|
|
2790
2862
|
* NeuralUI Slider Component
|