tecnualng 21.1.8 → 21.1.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/tecnualng.mjs +115 -53
- package/fesm2022/tecnualng.mjs.map +1 -1
- package/package.json +1 -1
- package/types/tecnualng.d.ts +15 -4
package/fesm2022/tecnualng.mjs
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { input, ChangeDetectionStrategy, ViewEncapsulation, Component, inject, model, signal, computed, ElementRef, effect, HostListener, Directive, contentChild, forwardRef, viewChild, TemplateRef, contentChildren, Injectable, createComponent, Input, output, ContentChildren, ViewContainerRef, booleanAttribute } from '@angular/core';
|
|
2
|
+
import { input, ChangeDetectionStrategy, ViewEncapsulation, Component, inject, model, signal, computed, ElementRef, DestroyRef, effect, HostListener, Directive, contentChild, forwardRef, viewChild, TemplateRef, contentChildren, Injectable, createComponent, Input, output, ContentChildren, ViewContainerRef, booleanAttribute, untracked } from '@angular/core';
|
|
3
3
|
import * as i1$2 from '@angular/forms';
|
|
4
4
|
import { NgControl, FormsModule, NG_VALUE_ACCESSOR } from '@angular/forms';
|
|
5
5
|
import * as i1 from '@angular/common';
|
|
6
6
|
import { CommonModule } from '@angular/common';
|
|
7
|
+
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
|
|
7
8
|
import * as i1$1 from '@angular/router';
|
|
8
9
|
import { RouterModule } from '@angular/router';
|
|
9
10
|
|
|
@@ -133,6 +134,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImpor
|
|
|
133
134
|
class TngInputDirective {
|
|
134
135
|
el = inject((ElementRef));
|
|
135
136
|
ngControl = inject(NgControl, { optional: true, self: true });
|
|
137
|
+
destroyRef = inject(DestroyRef);
|
|
136
138
|
// Inputs
|
|
137
139
|
disabled = input(false, ...(ngDevMode ? [{ debugName: "disabled" }] : []));
|
|
138
140
|
placeholder = input('', ...(ngDevMode ? [{ debugName: "placeholder" }] : []));
|
|
@@ -162,6 +164,13 @@ class TngInputDirective {
|
|
|
162
164
|
this.detectInputType();
|
|
163
165
|
});
|
|
164
166
|
}
|
|
167
|
+
ngOnInit() {
|
|
168
|
+
if (this.ngControl) {
|
|
169
|
+
this.ngControl.valueChanges?.pipe(takeUntilDestroyed(this.destroyRef)).subscribe((val) => {
|
|
170
|
+
this._value.set(val);
|
|
171
|
+
});
|
|
172
|
+
}
|
|
173
|
+
}
|
|
165
174
|
onFocus() {
|
|
166
175
|
this.focused.set(true);
|
|
167
176
|
}
|
|
@@ -194,7 +203,8 @@ class TngInputDirective {
|
|
|
194
203
|
}
|
|
195
204
|
}
|
|
196
205
|
updateValue() {
|
|
197
|
-
this.
|
|
206
|
+
const val = this.el.nativeElement.value;
|
|
207
|
+
this._value.set(val);
|
|
198
208
|
}
|
|
199
209
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngInputDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive });
|
|
200
210
|
static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "21.0.0", type: TngInputDirective, isStandalone: true, selector: "input[tngInput], textarea[tngInput]", inputs: { disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null } }, host: { listeners: { "focus": "onFocus()", "blur": "onBlur()", "input": "onInput()", "change": "onChange()" }, properties: { "class.tng-input-field": "isTextField()", "class.tng-checkbox": "isCheckbox()", "class.tng-radio": "isRadio()", "disabled": "disabled()", "attr.placeholder": "computedPlaceholder()" } }, ngImport: i0 });
|
|
@@ -229,6 +239,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImpor
|
|
|
229
239
|
class TngTextareaDirective {
|
|
230
240
|
el = inject((ElementRef));
|
|
231
241
|
ngControl = inject(NgControl, { optional: true, self: true });
|
|
242
|
+
destroyRef = inject(DestroyRef);
|
|
232
243
|
// Inputs
|
|
233
244
|
disabled = input(false, ...(ngDevMode ? [{ debugName: "disabled" }] : []));
|
|
234
245
|
placeholder = input('', ...(ngDevMode ? [{ debugName: "placeholder" }] : []));
|
|
@@ -250,6 +261,13 @@ class TngTextareaDirective {
|
|
|
250
261
|
this.updateValue();
|
|
251
262
|
});
|
|
252
263
|
}
|
|
264
|
+
ngOnInit() {
|
|
265
|
+
if (this.ngControl) {
|
|
266
|
+
this.ngControl.valueChanges?.pipe(takeUntilDestroyed(this.destroyRef)).subscribe((val) => {
|
|
267
|
+
this._value.set(val);
|
|
268
|
+
});
|
|
269
|
+
}
|
|
270
|
+
}
|
|
253
271
|
onFocus() {
|
|
254
272
|
this.focused.set(true);
|
|
255
273
|
}
|
|
@@ -318,6 +336,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImpor
|
|
|
318
336
|
}], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], inputDirective: [{ type: i0.ContentChild, args: [i0.forwardRef(() => TngInputDirective), { isSignal: true }] }], textareaDirective: [{ type: i0.ContentChild, args: [i0.forwardRef(() => TngTextareaDirective), { isSignal: true }] }] } });
|
|
319
337
|
|
|
320
338
|
class TngTextareaComponent {
|
|
339
|
+
ngControl = inject(NgControl, { optional: true, self: true });
|
|
321
340
|
label = input('', ...(ngDevMode ? [{ debugName: "label" }] : []));
|
|
322
341
|
placeholder = input('', ...(ngDevMode ? [{ debugName: "placeholder" }] : []));
|
|
323
342
|
required = input(false, ...(ngDevMode ? [{ debugName: "required" }] : []));
|
|
@@ -327,6 +346,11 @@ class TngTextareaComponent {
|
|
|
327
346
|
value = signal('', ...(ngDevMode ? [{ debugName: "value" }] : []));
|
|
328
347
|
onChange = () => { };
|
|
329
348
|
onTouched = () => { };
|
|
349
|
+
constructor() {
|
|
350
|
+
if (this.ngControl) {
|
|
351
|
+
this.ngControl.valueAccessor = this;
|
|
352
|
+
}
|
|
353
|
+
}
|
|
330
354
|
onInput(event) {
|
|
331
355
|
const input = event.target;
|
|
332
356
|
this.value.set(input.value);
|
|
@@ -345,27 +369,15 @@ class TngTextareaComponent {
|
|
|
345
369
|
this.onTouched = fn;
|
|
346
370
|
}
|
|
347
371
|
setDisabledState(isDisabled) {
|
|
348
|
-
this.disabled.
|
|
372
|
+
this.disabled.set(isDisabled);
|
|
349
373
|
}
|
|
350
374
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngTextareaComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
351
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "21.0.0", type: TngTextareaComponent, isStandalone: true, selector: "tng-textarea", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, required: { classPropertyName: "required", publicName: "required", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, maxLength: { classPropertyName: "maxLength", publicName: "maxLength", isSignal: true, isRequired: false, transformFunction: null }, id: { classPropertyName: "id", publicName: "id", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { disabled: "disabledChange" },
|
|
352
|
-
{
|
|
353
|
-
provide: NG_VALUE_ACCESSOR,
|
|
354
|
-
useExisting: forwardRef(() => TngTextareaComponent),
|
|
355
|
-
multi: true
|
|
356
|
-
}
|
|
357
|
-
], ngImport: i0, template: "<tng-form-field [label]=\"label()\">\n <textarea\n tngTextarea\n [id]=\"id()\"\n [placeholder]=\"placeholder()\"\n [value]=\"value()\"\n [disabled]=\"disabled()\"\n [maxLength]=\"maxLength()\"\n [required]=\"required()\"\n (input)=\"onInput($event)\"\n (blur)=\"onBlur()\">\n </textarea>\n</tng-form-field>\n", styles: [":host{display:block}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "component", type: TngFormFieldComponent, selector: "tng-form-field", inputs: ["label"] }, { kind: "directive", type: TngTextareaDirective, selector: "textarea[tngTextarea]", inputs: ["disabled", "placeholder", "maxLength"], exportAs: ["tngTextarea"] }], encapsulation: i0.ViewEncapsulation.None });
|
|
375
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "21.0.0", type: TngTextareaComponent, isStandalone: true, selector: "tng-textarea", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, required: { classPropertyName: "required", publicName: "required", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, maxLength: { classPropertyName: "maxLength", publicName: "maxLength", isSignal: true, isRequired: false, transformFunction: null }, id: { classPropertyName: "id", publicName: "id", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { disabled: "disabledChange" }, ngImport: i0, template: "<tng-form-field [label]=\"label()\">\n <textarea\n tngTextarea\n [id]=\"id()\"\n [placeholder]=\"placeholder()\"\n [value]=\"value()\"\n [disabled]=\"disabled()\"\n [maxLength]=\"maxLength()\"\n [required]=\"required()\"\n (input)=\"onInput($event)\"\n (blur)=\"onBlur()\">\n </textarea>\n</tng-form-field>\n", styles: [":host{display:block}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "component", type: TngFormFieldComponent, selector: "tng-form-field", inputs: ["label"] }, { kind: "directive", type: TngTextareaDirective, selector: "textarea[tngTextarea]", inputs: ["disabled", "placeholder", "maxLength"], exportAs: ["tngTextarea"] }], encapsulation: i0.ViewEncapsulation.None });
|
|
358
376
|
}
|
|
359
377
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngTextareaComponent, decorators: [{
|
|
360
378
|
type: Component,
|
|
361
|
-
args: [{ selector: 'tng-textarea', standalone: true, imports: [CommonModule, FormsModule, TngFormFieldComponent, TngTextareaDirective],
|
|
362
|
-
|
|
363
|
-
provide: NG_VALUE_ACCESSOR,
|
|
364
|
-
useExisting: forwardRef(() => TngTextareaComponent),
|
|
365
|
-
multi: true
|
|
366
|
-
}
|
|
367
|
-
], encapsulation: ViewEncapsulation.None, template: "<tng-form-field [label]=\"label()\">\n <textarea\n tngTextarea\n [id]=\"id()\"\n [placeholder]=\"placeholder()\"\n [value]=\"value()\"\n [disabled]=\"disabled()\"\n [maxLength]=\"maxLength()\"\n [required]=\"required()\"\n (input)=\"onInput($event)\"\n (blur)=\"onBlur()\">\n </textarea>\n</tng-form-field>\n", styles: [":host{display:block}\n"] }]
|
|
368
|
-
}], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], required: [{ type: i0.Input, args: [{ isSignal: true, alias: "required", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }, { type: i0.Output, args: ["disabledChange"] }], maxLength: [{ type: i0.Input, args: [{ isSignal: true, alias: "maxLength", required: false }] }], id: [{ type: i0.Input, args: [{ isSignal: true, alias: "id", required: false }] }] } });
|
|
379
|
+
args: [{ selector: 'tng-textarea', standalone: true, imports: [CommonModule, FormsModule, TngFormFieldComponent, TngTextareaDirective], encapsulation: ViewEncapsulation.None, template: "<tng-form-field [label]=\"label()\">\n <textarea\n tngTextarea\n [id]=\"id()\"\n [placeholder]=\"placeholder()\"\n [value]=\"value()\"\n [disabled]=\"disabled()\"\n [maxLength]=\"maxLength()\"\n [required]=\"required()\"\n (input)=\"onInput($event)\"\n (blur)=\"onBlur()\">\n </textarea>\n</tng-form-field>\n", styles: [":host{display:block}\n"] }]
|
|
380
|
+
}], ctorParameters: () => [], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], required: [{ type: i0.Input, args: [{ isSignal: true, alias: "required", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }, { type: i0.Output, args: ["disabledChange"] }], maxLength: [{ type: i0.Input, args: [{ isSignal: true, alias: "maxLength", required: false }] }], id: [{ type: i0.Input, args: [{ isSignal: true, alias: "id", required: false }] }] } });
|
|
369
381
|
|
|
370
382
|
class TecnualDatepickerComponent {
|
|
371
383
|
elementRef;
|
|
@@ -1768,17 +1780,18 @@ class TngSelectPanelComponent {
|
|
|
1768
1780
|
this.optionSelected.emit(index);
|
|
1769
1781
|
}
|
|
1770
1782
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngSelectPanelComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
1771
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.0.0", type: TngSelectPanelComponent, isStandalone: true, selector: "tng-select-panel", outputs: { optionSelected: "optionSelected", searchQueryChanged: "searchQueryChanged", closeRequested: "closeRequested" }, ngImport: i0, template: "<div class=\"tng-select-panel\" \n role=\"listbox\"\n [attr.aria-multiselectable]=\"enableMulti()\">\n \n @if (enableSearch()) {\n <div class=\"tng-select-search\">\n <input \n type=\"text\"\n class=\"tng-select-search-input\"\n [value]=\"searchQuery()\"\n (input)=\"onSearchInput($event)\"\n placeholder=\"Search...\"\n aria-label=\"Search options\"\n (click)=\"$event.stopPropagation()\"\n />\n <i class=\"fa fa-search tng-select-search-icon\"></i>\n </div>\n }\n \n <div class=\"tng-select-options\" role=\"list\">\n @if (options().length === 0) {\n <div class=\"tng-select-no-results\">\n No options found\n </div>\n }\n \n @for (option of options(); track $index) {\n <div \n class=\"tng-select-option\"\n [class.selected]=\"isSelected($index)\"\n [class.disabled]=\"option.disabled\"\n role=\"option\"\n [attr.aria-selected]=\"isSelected($index)\"\n [attr.aria-disabled]=\"option.disabled\"\n (click)=\"onOptionClick($index, option)\"\n >\n @if (enableMulti()) {\n <input \n type=\"checkbox\"\n class=\"tng-select-checkbox\"\n [checked]=\"isSelected($index)\"\n [disabled]=\"option.disabled\"\n tabindex=\"-1\"\n />\n }\n <span class=\"tng-select-option-label\">{{ option.label }}</span>\n </div>\n }\n </div>\n</div>\n", styles: [":host{display:block;backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px)}.tng-select-panel{background:var(--tng-surface, #ffffff);border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);box-shadow:var(--tng-shadow-md, 0 4px 8px rgba(0, 0, 0, .12));overflow:hidden;animation:slideDown .2s cubic-bezier(.4,0,.2,1)}@keyframes slideDown{0%{opacity:0;transform:translateY(-8px)}to{opacity:1;transform:translateY(0)}}.tng-select-search{position:relative;padding:.75rem;border-bottom:1px solid var(--tng-border, #e0e0e0)}.tng-select-search-input{width:100%;padding:.5rem 2rem .5rem .75rem;border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);font-size:.9rem;color:var(--tng-text, #333);outline:none;transition:border-color .2s ease}.tng-select-search-input:focus{border-color:var(--tng-primary, #00f2ff)}.tng-select-search-icon{position:absolute;right:1.5rem;top:50%;transform:translateY(-50%);color:var(--tng-text-secondary, #757575);pointer-events:none}.tng-select-options{max-height:300px;overflow-y:auto;padding:.25rem 0}.tng-select-options::-webkit-scrollbar{width:8px}.tng-select-options::-webkit-scrollbar-track{background:var(--tng-background, #fafafa)}.tng-select-options::-webkit-scrollbar-thumb{background:var(--tng-border, #e0e0e0);border-radius:4px}.tng-select-options::-webkit-scrollbar-thumb:hover{background:var(--tng-text-secondary, #757575)}.tng-select-option{display:flex;align-items:center;gap:.75rem;padding:.75rem 1rem;cursor:pointer;transition:background-color .15s ease;-webkit-user-select:none;user-select:none}.tng-select-option:hover:not(.disabled){background:var(--tng-background, #fafafa)}.tng-select-option.selected{background:#00f2ff1a;color:var(--tng-primary, #00f2ff)}.tng-select-option.disabled{opacity:.5;cursor:not-allowed}.tng-select-checkbox{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:18px;height:18px;min-width:18px;min-height:18px;border:2px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background-color:var(--tng-surface, #ffffff);cursor:pointer;position:relative;transition:all .2s cubic-bezier(.4,0,.2,1);margin:0;pointer-events:none}.tng-select-checkbox:checked{background-color:var(--tng-primary, #00f2ff);border-color:var(--tng-primary, #00f2ff)}.tng-select-checkbox:checked:before{content:\"\";position:absolute;width:4px;height:8px;border:solid var(--tng-primary-contrast, #000000);border-width:0 2px 2px 0;transform:rotate(45deg);top:2px;left:5px}.tng-select-checkbox:disabled{opacity:.5;cursor:not-allowed}.tng-select-option-label{flex:1;font-size:.95rem}.tng-select-no-results{padding:1.5rem 1rem;text-align:center;color:var(--tng-text-secondary, #757575);font-size:.9rem}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
1783
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.0.0", type: TngSelectPanelComponent, isStandalone: true, selector: "tng-select-panel", outputs: { optionSelected: "optionSelected", searchQueryChanged: "searchQueryChanged", closeRequested: "closeRequested" }, ngImport: i0, template: "<div class=\"tng-select-panel\" \n role=\"listbox\"\n [attr.aria-multiselectable]=\"enableMulti()\">\n \n @if (enableSearch()) {\n <div class=\"tng-select-search\">\n <input \n type=\"text\"\n class=\"tng-select-search-input\"\n [value]=\"searchQuery()\"\n (input)=\"onSearchInput($event)\"\n placeholder=\"Search...\"\n aria-label=\"Search options\"\n (click)=\"$event.stopPropagation()\"\n />\n <i class=\"fa fa-search tng-select-search-icon\"></i>\n </div>\n }\n \n <div class=\"tng-select-options\" role=\"list\">\n @if (options().length === 0) {\n <div class=\"tng-select-no-results\">\n No options found\n </div>\n }\n \n @for (option of options(); track $index) {\n <div \n class=\"tng-select-option\"\n [class.selected]=\"isSelected($index)\"\n [class.disabled]=\"option.disabled\"\n role=\"option\"\n [attr.aria-selected]=\"isSelected($index)\"\n [attr.aria-disabled]=\"option.disabled\"\n (click)=\"onOptionClick($index, option)\"\n >\n @if (enableMulti()) {\n <input \n type=\"checkbox\"\n class=\"tng-select-checkbox\"\n [checked]=\"isSelected($index)\"\n [disabled]=\"option.disabled\"\n tabindex=\"-1\"\n />\n }\n <span class=\"tng-select-option-label\">{{ option.label }}</span>\n </div>\n }\n </div>\n</div>\n", styles: [":host{display:block;backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px)}.tng-select-panel{background:var(--tng-surface, #ffffff);border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);box-shadow:var(--tng-shadow-md, 0 4px 8px rgba(0, 0, 0, .12));overflow:hidden;animation:slideDown .2s cubic-bezier(.4,0,.2,1)}@keyframes slideDown{0%{opacity:0;transform:translateY(-8px)}to{opacity:1;transform:translateY(0)}}.tng-select-search{position:relative;padding:.75rem;border-bottom:1px solid var(--tng-border, #e0e0e0)}.tng-select-search-input{width:100%;padding:.5rem 2rem .5rem .75rem;border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);font-size:.9rem;color:var(--tng-text, #333);background-color:var(--tng-surface, #ffffff);outline:none;transition:border-color .2s ease}.tng-select-search-input:focus{border-color:var(--tng-primary, #00f2ff)}.tng-select-search-icon{position:absolute;right:1.5rem;top:50%;transform:translateY(-50%);color:var(--tng-text-secondary, #757575);pointer-events:none}.tng-select-options{max-height:300px;overflow-y:auto;padding:.25rem 0}.tng-select-options::-webkit-scrollbar{width:8px}.tng-select-options::-webkit-scrollbar-track{background:var(--tng-background, #fafafa)}.tng-select-options::-webkit-scrollbar-thumb{background:var(--tng-border, #e0e0e0);border-radius:4px}.tng-select-options::-webkit-scrollbar-thumb:hover{background:var(--tng-text-secondary, #757575)}.tng-select-option{display:flex;align-items:center;gap:.75rem;padding:.75rem 1rem;cursor:pointer;transition:background-color .15s ease;-webkit-user-select:none;user-select:none}.tng-select-option:hover:not(.disabled){background:var(--tng-background, #fafafa)}.tng-select-option.selected{background:#00f2ff1a;color:var(--tng-primary, #00f2ff)}.tng-select-option.disabled{opacity:.5;cursor:not-allowed}.tng-select-checkbox{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:18px;height:18px;min-width:18px;min-height:18px;border:2px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background-color:var(--tng-surface, #ffffff);cursor:pointer;position:relative;transition:all .2s cubic-bezier(.4,0,.2,1);margin:0;pointer-events:none}.tng-select-checkbox:checked{background-color:var(--tng-primary, #00f2ff);border-color:var(--tng-primary, #00f2ff)}.tng-select-checkbox:checked:before{content:\"\";position:absolute;width:4px;height:8px;border:solid var(--tng-primary-contrast, #000000);border-width:0 2px 2px 0;transform:rotate(45deg);top:2px;left:5px}.tng-select-checkbox:disabled{opacity:.5;cursor:not-allowed}.tng-select-option-label{flex:1;font-size:.95rem}.tng-select-no-results{padding:1.5rem 1rem;text-align:center;color:var(--tng-text-secondary, #757575);font-size:.9rem}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
1772
1784
|
}
|
|
1773
1785
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngSelectPanelComponent, decorators: [{
|
|
1774
1786
|
type: Component,
|
|
1775
|
-
args: [{ selector: 'tng-select-panel', standalone: true, imports: [CommonModule, FormsModule], changeDetection: ChangeDetectionStrategy.OnPush, template: "<div class=\"tng-select-panel\" \n role=\"listbox\"\n [attr.aria-multiselectable]=\"enableMulti()\">\n \n @if (enableSearch()) {\n <div class=\"tng-select-search\">\n <input \n type=\"text\"\n class=\"tng-select-search-input\"\n [value]=\"searchQuery()\"\n (input)=\"onSearchInput($event)\"\n placeholder=\"Search...\"\n aria-label=\"Search options\"\n (click)=\"$event.stopPropagation()\"\n />\n <i class=\"fa fa-search tng-select-search-icon\"></i>\n </div>\n }\n \n <div class=\"tng-select-options\" role=\"list\">\n @if (options().length === 0) {\n <div class=\"tng-select-no-results\">\n No options found\n </div>\n }\n \n @for (option of options(); track $index) {\n <div \n class=\"tng-select-option\"\n [class.selected]=\"isSelected($index)\"\n [class.disabled]=\"option.disabled\"\n role=\"option\"\n [attr.aria-selected]=\"isSelected($index)\"\n [attr.aria-disabled]=\"option.disabled\"\n (click)=\"onOptionClick($index, option)\"\n >\n @if (enableMulti()) {\n <input \n type=\"checkbox\"\n class=\"tng-select-checkbox\"\n [checked]=\"isSelected($index)\"\n [disabled]=\"option.disabled\"\n tabindex=\"-1\"\n />\n }\n <span class=\"tng-select-option-label\">{{ option.label }}</span>\n </div>\n }\n </div>\n</div>\n", styles: [":host{display:block;backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px)}.tng-select-panel{background:var(--tng-surface, #ffffff);border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);box-shadow:var(--tng-shadow-md, 0 4px 8px rgba(0, 0, 0, .12));overflow:hidden;animation:slideDown .2s cubic-bezier(.4,0,.2,1)}@keyframes slideDown{0%{opacity:0;transform:translateY(-8px)}to{opacity:1;transform:translateY(0)}}.tng-select-search{position:relative;padding:.75rem;border-bottom:1px solid var(--tng-border, #e0e0e0)}.tng-select-search-input{width:100%;padding:.5rem 2rem .5rem .75rem;border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);font-size:.9rem;color:var(--tng-text, #333);outline:none;transition:border-color .2s ease}.tng-select-search-input:focus{border-color:var(--tng-primary, #00f2ff)}.tng-select-search-icon{position:absolute;right:1.5rem;top:50%;transform:translateY(-50%);color:var(--tng-text-secondary, #757575);pointer-events:none}.tng-select-options{max-height:300px;overflow-y:auto;padding:.25rem 0}.tng-select-options::-webkit-scrollbar{width:8px}.tng-select-options::-webkit-scrollbar-track{background:var(--tng-background, #fafafa)}.tng-select-options::-webkit-scrollbar-thumb{background:var(--tng-border, #e0e0e0);border-radius:4px}.tng-select-options::-webkit-scrollbar-thumb:hover{background:var(--tng-text-secondary, #757575)}.tng-select-option{display:flex;align-items:center;gap:.75rem;padding:.75rem 1rem;cursor:pointer;transition:background-color .15s ease;-webkit-user-select:none;user-select:none}.tng-select-option:hover:not(.disabled){background:var(--tng-background, #fafafa)}.tng-select-option.selected{background:#00f2ff1a;color:var(--tng-primary, #00f2ff)}.tng-select-option.disabled{opacity:.5;cursor:not-allowed}.tng-select-checkbox{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:18px;height:18px;min-width:18px;min-height:18px;border:2px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background-color:var(--tng-surface, #ffffff);cursor:pointer;position:relative;transition:all .2s cubic-bezier(.4,0,.2,1);margin:0;pointer-events:none}.tng-select-checkbox:checked{background-color:var(--tng-primary, #00f2ff);border-color:var(--tng-primary, #00f2ff)}.tng-select-checkbox:checked:before{content:\"\";position:absolute;width:4px;height:8px;border:solid var(--tng-primary-contrast, #000000);border-width:0 2px 2px 0;transform:rotate(45deg);top:2px;left:5px}.tng-select-checkbox:disabled{opacity:.5;cursor:not-allowed}.tng-select-option-label{flex:1;font-size:.95rem}.tng-select-no-results{padding:1.5rem 1rem;text-align:center;color:var(--tng-text-secondary, #757575);font-size:.9rem}\n"] }]
|
|
1787
|
+
args: [{ selector: 'tng-select-panel', standalone: true, imports: [CommonModule, FormsModule], changeDetection: ChangeDetectionStrategy.OnPush, template: "<div class=\"tng-select-panel\" \n role=\"listbox\"\n [attr.aria-multiselectable]=\"enableMulti()\">\n \n @if (enableSearch()) {\n <div class=\"tng-select-search\">\n <input \n type=\"text\"\n class=\"tng-select-search-input\"\n [value]=\"searchQuery()\"\n (input)=\"onSearchInput($event)\"\n placeholder=\"Search...\"\n aria-label=\"Search options\"\n (click)=\"$event.stopPropagation()\"\n />\n <i class=\"fa fa-search tng-select-search-icon\"></i>\n </div>\n }\n \n <div class=\"tng-select-options\" role=\"list\">\n @if (options().length === 0) {\n <div class=\"tng-select-no-results\">\n No options found\n </div>\n }\n \n @for (option of options(); track $index) {\n <div \n class=\"tng-select-option\"\n [class.selected]=\"isSelected($index)\"\n [class.disabled]=\"option.disabled\"\n role=\"option\"\n [attr.aria-selected]=\"isSelected($index)\"\n [attr.aria-disabled]=\"option.disabled\"\n (click)=\"onOptionClick($index, option)\"\n >\n @if (enableMulti()) {\n <input \n type=\"checkbox\"\n class=\"tng-select-checkbox\"\n [checked]=\"isSelected($index)\"\n [disabled]=\"option.disabled\"\n tabindex=\"-1\"\n />\n }\n <span class=\"tng-select-option-label\">{{ option.label }}</span>\n </div>\n }\n </div>\n</div>\n", styles: [":host{display:block;backdrop-filter:blur(8px);-webkit-backdrop-filter:blur(8px)}.tng-select-panel{background:var(--tng-surface, #ffffff);border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);box-shadow:var(--tng-shadow-md, 0 4px 8px rgba(0, 0, 0, .12));overflow:hidden;animation:slideDown .2s cubic-bezier(.4,0,.2,1)}@keyframes slideDown{0%{opacity:0;transform:translateY(-8px)}to{opacity:1;transform:translateY(0)}}.tng-select-search{position:relative;padding:.75rem;border-bottom:1px solid var(--tng-border, #e0e0e0)}.tng-select-search-input{width:100%;padding:.5rem 2rem .5rem .75rem;border:1px solid var(--tng-border, #e0e0e0);border-radius:var(--tng-border-radius, 4px);font-size:.9rem;color:var(--tng-text, #333);background-color:var(--tng-surface, #ffffff);outline:none;transition:border-color .2s ease}.tng-select-search-input:focus{border-color:var(--tng-primary, #00f2ff)}.tng-select-search-icon{position:absolute;right:1.5rem;top:50%;transform:translateY(-50%);color:var(--tng-text-secondary, #757575);pointer-events:none}.tng-select-options{max-height:300px;overflow-y:auto;padding:.25rem 0}.tng-select-options::-webkit-scrollbar{width:8px}.tng-select-options::-webkit-scrollbar-track{background:var(--tng-background, #fafafa)}.tng-select-options::-webkit-scrollbar-thumb{background:var(--tng-border, #e0e0e0);border-radius:4px}.tng-select-options::-webkit-scrollbar-thumb:hover{background:var(--tng-text-secondary, #757575)}.tng-select-option{display:flex;align-items:center;gap:.75rem;padding:.75rem 1rem;cursor:pointer;transition:background-color .15s ease;-webkit-user-select:none;user-select:none}.tng-select-option:hover:not(.disabled){background:var(--tng-background, #fafafa)}.tng-select-option.selected{background:#00f2ff1a;color:var(--tng-primary, #00f2ff)}.tng-select-option.disabled{opacity:.5;cursor:not-allowed}.tng-select-checkbox{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:18px;height:18px;min-width:18px;min-height:18px;border:2px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background-color:var(--tng-surface, #ffffff);cursor:pointer;position:relative;transition:all .2s cubic-bezier(.4,0,.2,1);margin:0;pointer-events:none}.tng-select-checkbox:checked{background-color:var(--tng-primary, #00f2ff);border-color:var(--tng-primary, #00f2ff)}.tng-select-checkbox:checked:before{content:\"\";position:absolute;width:4px;height:8px;border:solid var(--tng-primary-contrast, #000000);border-width:0 2px 2px 0;transform:rotate(45deg);top:2px;left:5px}.tng-select-checkbox:disabled{opacity:.5;cursor:not-allowed}.tng-select-option-label{flex:1;font-size:.95rem}.tng-select-no-results{padding:1.5rem 1rem;text-align:center;color:var(--tng-text-secondary, #757575);font-size:.9rem}\n"] }]
|
|
1776
1788
|
}], propDecorators: { optionSelected: [{ type: i0.Output, args: ["optionSelected"] }], searchQueryChanged: [{ type: i0.Output, args: ["searchQueryChanged"] }], closeRequested: [{ type: i0.Output, args: ["closeRequested"] }] } });
|
|
1777
1789
|
|
|
1778
1790
|
class TngSelectDirective {
|
|
1779
1791
|
el = inject((ElementRef));
|
|
1780
1792
|
viewContainerRef = inject(ViewContainerRef);
|
|
1781
1793
|
ngControl = inject(NgControl, { optional: true, self: true });
|
|
1794
|
+
destroyRef = inject(DestroyRef);
|
|
1782
1795
|
// Inputs
|
|
1783
1796
|
enableMulti = input(false, ...(ngDevMode ? [{ debugName: "enableMulti" }] : []));
|
|
1784
1797
|
// Support native multiple attribute
|
|
@@ -1793,7 +1806,23 @@ class TngSelectDirective {
|
|
|
1793
1806
|
isOpen = signal(false, ...(ngDevMode ? [{ debugName: "isOpen" }] : []));
|
|
1794
1807
|
searchQuery = signal('', ...(ngDevMode ? [{ debugName: "searchQuery" }] : []));
|
|
1795
1808
|
_options = signal([], ...(ngDevMode ? [{ debugName: "_options" }] : []));
|
|
1796
|
-
_selectedIndices = signal([], ...(ngDevMode ? [{ debugName: "_selectedIndices"
|
|
1809
|
+
_selectedIndices = signal([], ...(ngDevMode ? [{ debugName: "_selectedIndices", equal: (a, b) => {
|
|
1810
|
+
if (a === b)
|
|
1811
|
+
return true;
|
|
1812
|
+
if (a.length !== b.length)
|
|
1813
|
+
return false;
|
|
1814
|
+
const sortedA = [...a].sort();
|
|
1815
|
+
const sortedB = [...b].sort();
|
|
1816
|
+
return sortedA.every((val, index) => val === sortedB[index]);
|
|
1817
|
+
} }] : [{ equal: (a, b) => {
|
|
1818
|
+
if (a === b)
|
|
1819
|
+
return true;
|
|
1820
|
+
if (a.length !== b.length)
|
|
1821
|
+
return false;
|
|
1822
|
+
const sortedA = [...a].sort();
|
|
1823
|
+
const sortedB = [...b].sort();
|
|
1824
|
+
return sortedA.every((val, index) => val === sortedB[index]);
|
|
1825
|
+
} }]));
|
|
1797
1826
|
// Component reference for the panel
|
|
1798
1827
|
panelRef = null;
|
|
1799
1828
|
// Generated trigger element
|
|
@@ -1825,16 +1854,29 @@ class TngSelectDirective {
|
|
|
1825
1854
|
return selected.map(opt => opt.label).join(', ');
|
|
1826
1855
|
}, ...(ngDevMode ? [{ debugName: "displayText" }] : []));
|
|
1827
1856
|
constructor() {
|
|
1828
|
-
// Sync selected values with model
|
|
1857
|
+
// Sync selected values with model (Output)
|
|
1829
1858
|
effect(() => {
|
|
1830
1859
|
const selected = this.selectedOptions();
|
|
1860
|
+
// Use untracked to avoid loop if selectedValues write triggers immediate read dependency? No.
|
|
1831
1861
|
this.selectedValues.set(selected.map(opt => opt.value));
|
|
1832
1862
|
});
|
|
1863
|
+
// Sync model with internal (Input)
|
|
1864
|
+
effect(() => {
|
|
1865
|
+
const values = this.selectedValues();
|
|
1866
|
+
// Avoid infinite loop by checking if values actally represent a change
|
|
1867
|
+
const currentSelected = untracked(() => this.selectedOptions());
|
|
1868
|
+
const currentValues = currentSelected.map(o => o.value);
|
|
1869
|
+
// Simple equality check (value-based)
|
|
1870
|
+
if (values.length !== currentValues.length || !values.every((v, i) => v == currentValues[i])) { // weak eq
|
|
1871
|
+
this.updateSelectionFromValue(values);
|
|
1872
|
+
}
|
|
1873
|
+
});
|
|
1833
1874
|
// Update form control value
|
|
1834
1875
|
effect(() => {
|
|
1835
1876
|
if (this.ngControl?.control) {
|
|
1836
1877
|
const values = this.selectedValues();
|
|
1837
1878
|
const newValue = this.isMulti() ? values : (values[0] ?? null);
|
|
1879
|
+
// Only setValue if changed? internal control handles checks usually
|
|
1838
1880
|
this.ngControl.control.setValue(newValue, { emitEvent: false });
|
|
1839
1881
|
}
|
|
1840
1882
|
});
|
|
@@ -1862,6 +1904,33 @@ class TngSelectDirective {
|
|
|
1862
1904
|
}
|
|
1863
1905
|
});
|
|
1864
1906
|
}
|
|
1907
|
+
ngOnInit() {
|
|
1908
|
+
if (this.ngControl) {
|
|
1909
|
+
this.ngControl.valueChanges?.pipe(takeUntilDestroyed(this.destroyRef)).subscribe((val) => {
|
|
1910
|
+
// Find indices matching value
|
|
1911
|
+
this.updateSelectionFromValue(val);
|
|
1912
|
+
});
|
|
1913
|
+
}
|
|
1914
|
+
}
|
|
1915
|
+
updateSelectionFromValue(value) {
|
|
1916
|
+
const opts = this._options();
|
|
1917
|
+
const indices = [];
|
|
1918
|
+
if (this.isMulti()) {
|
|
1919
|
+
const valArray = Array.isArray(value) ? value : (value ? [value] : []);
|
|
1920
|
+
valArray.forEach((v) => {
|
|
1921
|
+
const idx = opts.findIndex(o => o.value == v); // weak equality for numbers/strings?
|
|
1922
|
+
if (idx !== -1)
|
|
1923
|
+
indices.push(idx);
|
|
1924
|
+
});
|
|
1925
|
+
}
|
|
1926
|
+
else {
|
|
1927
|
+
const idx = opts.findIndex(o => o.value == value);
|
|
1928
|
+
if (idx !== -1)
|
|
1929
|
+
indices.push(idx);
|
|
1930
|
+
}
|
|
1931
|
+
this._selectedIndices.set(indices);
|
|
1932
|
+
this.updateNativeSelect(false);
|
|
1933
|
+
}
|
|
1865
1934
|
ngAfterViewInit() {
|
|
1866
1935
|
this.loadOptionsFromSelect();
|
|
1867
1936
|
this.loadInitialSelection();
|
|
@@ -2066,7 +2135,7 @@ class TngSelectDirective {
|
|
|
2066
2135
|
// Update native select
|
|
2067
2136
|
this.updateNativeSelect();
|
|
2068
2137
|
}
|
|
2069
|
-
updateNativeSelect() {
|
|
2138
|
+
updateNativeSelect(emitEvents = true) {
|
|
2070
2139
|
const selectEl = this.el.nativeElement;
|
|
2071
2140
|
const selectedIndices = this._selectedIndices();
|
|
2072
2141
|
// Clear all selections
|
|
@@ -2079,10 +2148,12 @@ class TngSelectDirective {
|
|
|
2079
2148
|
selectEl.options[idx].selected = true;
|
|
2080
2149
|
}
|
|
2081
2150
|
});
|
|
2082
|
-
|
|
2083
|
-
|
|
2084
|
-
|
|
2085
|
-
|
|
2151
|
+
if (emitEvents) {
|
|
2152
|
+
// Trigger change event
|
|
2153
|
+
selectEl.dispatchEvent(new Event('change', { bubbles: true }));
|
|
2154
|
+
// Also trigger input event for some frameworks
|
|
2155
|
+
selectEl.dispatchEvent(new Event('input', { bubbles: true }));
|
|
2156
|
+
}
|
|
2086
2157
|
}
|
|
2087
2158
|
onDocumentClick = (event) => {
|
|
2088
2159
|
const target = event.target;
|
|
@@ -2124,6 +2195,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImpor
|
|
|
2124
2195
|
}] } });
|
|
2125
2196
|
|
|
2126
2197
|
class TngSelectComponent {
|
|
2198
|
+
ngControl = inject(NgControl, { optional: true, self: true });
|
|
2127
2199
|
// Inputs
|
|
2128
2200
|
label = input('', ...(ngDevMode ? [{ debugName: "label" }] : []));
|
|
2129
2201
|
options = input.required(...(ngDevMode ? [{ debugName: "options" }] : []));
|
|
@@ -2155,18 +2227,20 @@ class TngSelectComponent {
|
|
|
2155
2227
|
onChange = () => { };
|
|
2156
2228
|
onTouched = () => { };
|
|
2157
2229
|
constructor() {
|
|
2158
|
-
|
|
2159
|
-
|
|
2160
|
-
|
|
2161
|
-
|
|
2162
|
-
|
|
2163
|
-
|
|
2164
|
-
|
|
2165
|
-
|
|
2166
|
-
|
|
2167
|
-
|
|
2168
|
-
|
|
2169
|
-
|
|
2230
|
+
if (this.ngControl) {
|
|
2231
|
+
this.ngControl.valueAccessor = this;
|
|
2232
|
+
}
|
|
2233
|
+
}
|
|
2234
|
+
onSelectionChange(newValues) {
|
|
2235
|
+
this.value.set(newValues);
|
|
2236
|
+
// Avoid circular updates if possible, but for now just emit
|
|
2237
|
+
if (this.enableMulti()) {
|
|
2238
|
+
this.onChange(newValues);
|
|
2239
|
+
}
|
|
2240
|
+
else {
|
|
2241
|
+
this.onChange(newValues.length > 0 ? newValues[0] : null);
|
|
2242
|
+
}
|
|
2243
|
+
this.onTouched();
|
|
2170
2244
|
}
|
|
2171
2245
|
onDisplayClick(event) {
|
|
2172
2246
|
if (this.effectiveDisabled())
|
|
@@ -2199,23 +2273,11 @@ class TngSelectComponent {
|
|
|
2199
2273
|
this.cvaDisabled.set(isDisabled);
|
|
2200
2274
|
}
|
|
2201
2275
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngSelectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
2202
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.0.0", type: TngSelectComponent, isStandalone: true, selector: "tng-select", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: true, transformFunction: null }, enableMulti: { classPropertyName: "enableMulti", publicName: "enableMulti", isSignal: true, isRequired: false, transformFunction: null }, enableSearch: { classPropertyName: "enableSearch", publicName: "enableSearch", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, hint: { classPropertyName: "hint", publicName: "hint", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange" },
|
|
2203
|
-
{
|
|
2204
|
-
provide: NG_VALUE_ACCESSOR,
|
|
2205
|
-
useExisting: forwardRef(() => TngSelectComponent),
|
|
2206
|
-
multi: true
|
|
2207
|
-
}
|
|
2208
|
-
], viewQueries: [{ propertyName: "selectDirective", first: true, predicate: TngSelectDirective, descendants: true, isSignal: true }], ngImport: i0, template: "<div class=\"tng-select-wrapper\" [class.tng-select-open]=\"selectDirective()?.isOpen()\">\n @if (label()) {\n <label class=\"tng-select-label\" [attr.for]=\"selectId()\">\n {{ label() }}\n </label>\n }\n\n <div class=\"tng-select-container\">\n <select\n [id]=\"selectId()\"\n tngSelect\n [enableMulti]=\"enableMulti()\"\n [enableSearch]=\"enableSearch()\"\n [placeholder]=\"placeholder()\"\n [customTrigger]=\"true\"\n [multiple]=\"enableMulti()\"\n [triggerRef]=\"triggerDisplay\"\n [(selectedValues)]=\"value\"\n [disabled]=\"effectiveDisabled()\"\n [attr.aria-label]=\"ariaLabel() || label()\"\n >\n @for (option of options(); track option.value) {\n <option [value]=\"option.value\" [disabled]=\"option.disabled\">\n {{ option.label }}\n </option>\n }\n </select>\n\n <div\n class=\"tng-select-display\"\n #triggerDisplay\n [class.disabled]=\"effectiveDisabled()\"\n (click)=\"onDisplayClick($event)\"\n >\n <span class=\"tng-select-display-text\">\n {{ displayText() }}\n </span>\n <i class=\"fa fa-chevron-down tng-select-arrow\"></i>\n </div>\n </div>\n\n @if (hint()) {\n <div class=\"tng-select-hint\">\n {{ hint() }}\n </div>\n }\n</div>\n", styles: [":host{display:block;margin-bottom:1.5rem;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-wrapper{width:100%}.tng-select-label{display:block;margin-bottom:.5rem;font-size:.9rem;font-weight:500;color:var(--tng-text, #333)}.tng-select-container{position:relative}.tng-select-display{display:flex;align-items:center;justify-content:space-between;gap:.75rem;padding:.75rem 1rem;border:1px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background:var(--tng-surface, #ffffff);cursor:pointer;transition:all .2s ease;min-height:48px;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-display:hover:not(.disabled){border-color:var(--tng-text-secondary, #757575)}.tng-select-display.disabled{opacity:.6;cursor:not-allowed;background:var(--tng-background, #fafafa)}.tng-select-wrapper.tng-select-open .tng-select-display,.tng-select-display.tng-select-open{border-color:var(--tng-primary, #00f2ff);border-width:2px;padding:calc(.75rem - 1px) calc(1rem - 1px)}.tng-select-display-text{flex:1;color:var(--tng-text, #333);font-size:1rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.tng-select-display-text:empty:before{content:attr(data-placeholder);color:var(--tng-text-secondary, #757575)}.tng-select-arrow{color:var(--tng-text-secondary, #757575);transition:transform .2s ease;font-size:.8rem}.tng-select-wrapper.tng-select-open .tng-select-arrow,.tng-select-display.tng-select-open .tng-select-arrow{transform:rotate(180deg)}.tng-select-hint{margin-top:.25rem;font-size:.85rem;color:var(--tng-text-secondary, #757575)}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.NgSelectOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i1$2.ɵNgSelectMultipleOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: TngSelectDirective, selector: "select[tngSelect]", inputs: ["enableMulti", "multiple", "enableSearch", "placeholder", "customTrigger", "triggerRef", "selectedValues"], outputs: ["selectedValuesChange"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
2276
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.0.0", type: TngSelectComponent, isStandalone: true, selector: "tng-select", inputs: { label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, options: { classPropertyName: "options", publicName: "options", isSignal: true, isRequired: true, transformFunction: null }, enableMulti: { classPropertyName: "enableMulti", publicName: "enableMulti", isSignal: true, isRequired: false, transformFunction: null }, enableSearch: { classPropertyName: "enableSearch", publicName: "enableSearch", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, hint: { classPropertyName: "hint", publicName: "hint", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange" }, viewQueries: [{ propertyName: "selectDirective", first: true, predicate: TngSelectDirective, descendants: true, isSignal: true }], ngImport: i0, template: "<div class=\"tng-select-wrapper\" [class.tng-select-open]=\"selectDirective()?.isOpen()\">\n @if (label()) {\n <label class=\"tng-select-label\" [attr.for]=\"selectId()\">\n {{ label() }}\n </label>\n }\n\n <div class=\"tng-select-container\">\n <select\n [id]=\"selectId()\"\n tngSelect\n [enableMulti]=\"enableMulti()\"\n [enableSearch]=\"enableSearch()\"\n [placeholder]=\"placeholder()\"\n [customTrigger]=\"true\"\n [multiple]=\"enableMulti()\"\n [triggerRef]=\"triggerDisplay\"\n [selectedValues]=\"value()\"\n (selectedValuesChange)=\"onSelectionChange($event)\"\n [disabled]=\"effectiveDisabled()\"\n [attr.aria-label]=\"ariaLabel() || label()\"\n >\n @for (option of options(); track option.value) {\n <option [value]=\"option.value\" [disabled]=\"option.disabled\">\n {{ option.label }}\n </option>\n }\n </select>\n\n <div\n class=\"tng-select-display\"\n #triggerDisplay\n [class.disabled]=\"effectiveDisabled()\"\n (click)=\"onDisplayClick($event)\"\n >\n <span class=\"tng-select-display-text\">\n {{ displayText() }}\n </span>\n <i class=\"fa fa-chevron-down tng-select-arrow\"></i>\n </div>\n </div>\n\n @if (hint()) {\n <div class=\"tng-select-hint\">\n {{ hint() }}\n </div>\n }\n</div>\n", styles: [":host{display:block;margin-bottom:1.5rem;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-wrapper{width:100%}.tng-select-label{display:block;margin-bottom:.5rem;font-size:.9rem;font-weight:500;color:var(--tng-text, #333)}.tng-select-container{position:relative}.tng-select-display{display:flex;align-items:center;justify-content:space-between;gap:.75rem;padding:.75rem 1rem;border:1px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background:var(--tng-surface, #ffffff);cursor:pointer;transition:all .2s ease;min-height:48px;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-display:hover:not(.disabled){border-color:var(--tng-text-secondary, #757575)}.tng-select-display.disabled{opacity:.6;cursor:not-allowed;background:var(--tng-background, #fafafa)}.tng-select-wrapper.tng-select-open .tng-select-display,.tng-select-display.tng-select-open{border-color:var(--tng-primary, #00f2ff);border-width:2px;padding:calc(.75rem - 1px) calc(1rem - 1px)}.tng-select-display-text{flex:1;color:var(--tng-text, #333);font-size:1rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.tng-select-display-text:empty:before{content:attr(data-placeholder);color:var(--tng-text-secondary, #757575)}.tng-select-arrow{color:var(--tng-text-secondary, #757575);transition:transform .2s ease;font-size:.8rem}.tng-select-wrapper.tng-select-open .tng-select-arrow,.tng-select-display.tng-select-open .tng-select-arrow{transform:rotate(180deg)}.tng-select-hint{margin-top:.25rem;font-size:.85rem;color:var(--tng-text-secondary, #757575)}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.NgSelectOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i1$2.ɵNgSelectMultipleOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: TngSelectDirective, selector: "select[tngSelect]", inputs: ["enableMulti", "multiple", "enableSearch", "placeholder", "customTrigger", "triggerRef", "selectedValues"], outputs: ["selectedValuesChange"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
|
|
2209
2277
|
}
|
|
2210
2278
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.0", ngImport: i0, type: TngSelectComponent, decorators: [{
|
|
2211
2279
|
type: Component,
|
|
2212
|
-
args: [{ selector: 'tng-select', standalone: true, imports: [CommonModule, FormsModule, TngSelectDirective],
|
|
2213
|
-
{
|
|
2214
|
-
provide: NG_VALUE_ACCESSOR,
|
|
2215
|
-
useExisting: forwardRef(() => TngSelectComponent),
|
|
2216
|
-
multi: true
|
|
2217
|
-
}
|
|
2218
|
-
], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, template: "<div class=\"tng-select-wrapper\" [class.tng-select-open]=\"selectDirective()?.isOpen()\">\n @if (label()) {\n <label class=\"tng-select-label\" [attr.for]=\"selectId()\">\n {{ label() }}\n </label>\n }\n\n <div class=\"tng-select-container\">\n <select\n [id]=\"selectId()\"\n tngSelect\n [enableMulti]=\"enableMulti()\"\n [enableSearch]=\"enableSearch()\"\n [placeholder]=\"placeholder()\"\n [customTrigger]=\"true\"\n [multiple]=\"enableMulti()\"\n [triggerRef]=\"triggerDisplay\"\n [(selectedValues)]=\"value\"\n [disabled]=\"effectiveDisabled()\"\n [attr.aria-label]=\"ariaLabel() || label()\"\n >\n @for (option of options(); track option.value) {\n <option [value]=\"option.value\" [disabled]=\"option.disabled\">\n {{ option.label }}\n </option>\n }\n </select>\n\n <div\n class=\"tng-select-display\"\n #triggerDisplay\n [class.disabled]=\"effectiveDisabled()\"\n (click)=\"onDisplayClick($event)\"\n >\n <span class=\"tng-select-display-text\">\n {{ displayText() }}\n </span>\n <i class=\"fa fa-chevron-down tng-select-arrow\"></i>\n </div>\n </div>\n\n @if (hint()) {\n <div class=\"tng-select-hint\">\n {{ hint() }}\n </div>\n }\n</div>\n", styles: [":host{display:block;margin-bottom:1.5rem;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-wrapper{width:100%}.tng-select-label{display:block;margin-bottom:.5rem;font-size:.9rem;font-weight:500;color:var(--tng-text, #333)}.tng-select-container{position:relative}.tng-select-display{display:flex;align-items:center;justify-content:space-between;gap:.75rem;padding:.75rem 1rem;border:1px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background:var(--tng-surface, #ffffff);cursor:pointer;transition:all .2s ease;min-height:48px;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-display:hover:not(.disabled){border-color:var(--tng-text-secondary, #757575)}.tng-select-display.disabled{opacity:.6;cursor:not-allowed;background:var(--tng-background, #fafafa)}.tng-select-wrapper.tng-select-open .tng-select-display,.tng-select-display.tng-select-open{border-color:var(--tng-primary, #00f2ff);border-width:2px;padding:calc(.75rem - 1px) calc(1rem - 1px)}.tng-select-display-text{flex:1;color:var(--tng-text, #333);font-size:1rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.tng-select-display-text:empty:before{content:attr(data-placeholder);color:var(--tng-text-secondary, #757575)}.tng-select-arrow{color:var(--tng-text-secondary, #757575);transition:transform .2s ease;font-size:.8rem}.tng-select-wrapper.tng-select-open .tng-select-arrow,.tng-select-display.tng-select-open .tng-select-arrow{transform:rotate(180deg)}.tng-select-hint{margin-top:.25rem;font-size:.85rem;color:var(--tng-text-secondary, #757575)}\n"] }]
|
|
2280
|
+
args: [{ selector: 'tng-select', standalone: true, imports: [CommonModule, FormsModule, TngSelectDirective], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, template: "<div class=\"tng-select-wrapper\" [class.tng-select-open]=\"selectDirective()?.isOpen()\">\n @if (label()) {\n <label class=\"tng-select-label\" [attr.for]=\"selectId()\">\n {{ label() }}\n </label>\n }\n\n <div class=\"tng-select-container\">\n <select\n [id]=\"selectId()\"\n tngSelect\n [enableMulti]=\"enableMulti()\"\n [enableSearch]=\"enableSearch()\"\n [placeholder]=\"placeholder()\"\n [customTrigger]=\"true\"\n [multiple]=\"enableMulti()\"\n [triggerRef]=\"triggerDisplay\"\n [selectedValues]=\"value()\"\n (selectedValuesChange)=\"onSelectionChange($event)\"\n [disabled]=\"effectiveDisabled()\"\n [attr.aria-label]=\"ariaLabel() || label()\"\n >\n @for (option of options(); track option.value) {\n <option [value]=\"option.value\" [disabled]=\"option.disabled\">\n {{ option.label }}\n </option>\n }\n </select>\n\n <div\n class=\"tng-select-display\"\n #triggerDisplay\n [class.disabled]=\"effectiveDisabled()\"\n (click)=\"onDisplayClick($event)\"\n >\n <span class=\"tng-select-display-text\">\n {{ displayText() }}\n </span>\n <i class=\"fa fa-chevron-down tng-select-arrow\"></i>\n </div>\n </div>\n\n @if (hint()) {\n <div class=\"tng-select-hint\">\n {{ hint() }}\n </div>\n }\n</div>\n", styles: [":host{display:block;margin-bottom:1.5rem;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-wrapper{width:100%}.tng-select-label{display:block;margin-bottom:.5rem;font-size:.9rem;font-weight:500;color:var(--tng-text, #333)}.tng-select-container{position:relative}.tng-select-display{display:flex;align-items:center;justify-content:space-between;gap:.75rem;padding:.75rem 1rem;border:1px solid var(--tng-border, #999);border-radius:var(--tng-border-radius, 4px);background:var(--tng-surface, #ffffff);cursor:pointer;transition:all .2s ease;min-height:48px;font-family:var(--tng-font-family, \"Inter\", sans-serif)}.tng-select-display:hover:not(.disabled){border-color:var(--tng-text-secondary, #757575)}.tng-select-display.disabled{opacity:.6;cursor:not-allowed;background:var(--tng-background, #fafafa)}.tng-select-wrapper.tng-select-open .tng-select-display,.tng-select-display.tng-select-open{border-color:var(--tng-primary, #00f2ff);border-width:2px;padding:calc(.75rem - 1px) calc(1rem - 1px)}.tng-select-display-text{flex:1;color:var(--tng-text, #333);font-size:1rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.tng-select-display-text:empty:before{content:attr(data-placeholder);color:var(--tng-text-secondary, #757575)}.tng-select-arrow{color:var(--tng-text-secondary, #757575);transition:transform .2s ease;font-size:.8rem}.tng-select-wrapper.tng-select-open .tng-select-arrow,.tng-select-display.tng-select-open .tng-select-arrow{transform:rotate(180deg)}.tng-select-hint{margin-top:.25rem;font-size:.85rem;color:var(--tng-text-secondary, #757575)}\n"] }]
|
|
2219
2281
|
}], ctorParameters: () => [], propDecorators: { label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], options: [{ type: i0.Input, args: [{ isSignal: true, alias: "options", required: true }] }], enableMulti: [{ type: i0.Input, args: [{ isSignal: true, alias: "enableMulti", required: false }] }], enableSearch: [{ type: i0.Input, args: [{ isSignal: true, alias: "enableSearch", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], hint: [{ type: i0.Input, args: [{ isSignal: true, alias: "hint", required: false }] }], ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], selectDirective: [{ type: i0.ViewChild, args: [i0.forwardRef(() => TngSelectDirective), { isSignal: true }] }] } });
|
|
2220
2282
|
|
|
2221
2283
|
class TngSliderComponent {
|