@flusys/ng-shared 8.1.3 → 8.1.5
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.
|
@@ -7,7 +7,7 @@ import { of, catchError as catchError$1, throwError, firstValueFrom, map as map$
|
|
|
7
7
|
import { map, tap, catchError } from 'rxjs/operators';
|
|
8
8
|
import * as i1 from '@angular/forms';
|
|
9
9
|
import { NgControl, NG_VALUE_ACCESSOR, FormsModule } from '@angular/forms';
|
|
10
|
-
import { MessageService, CardComponent, InputTextDirective, PasswordComponent, UiIconComponent, InputNumberComponent, TextareaDirective, SelectComponent, MultiSelectComponent, DatePickerComponent, CheckboxComponent, ToggleSwitchComponent, FButtonDirective, ConfirmationService, IconFieldComponent, InputIconComponent, TableComponent, TagComponent, TooltipDirective, ProgressbarComponent, DialogComponent, ButtonComponent } from '@flusys/ng-ui';
|
|
10
|
+
import { MessageService, CardComponent, InputTextDirective, PasswordComponent, UiIconComponent, InputNumberComponent, TextareaDirective, SelectComponent, MultiSelectComponent, DatePickerComponent, CheckboxComponent, ToggleSwitchComponent, FButtonDirective, ConfirmationService, IconFieldComponent, InputIconComponent, TableComponent, TagComponent, TooltipDirective, ProgressbarComponent, DialogComponent, ButtonComponent, OverlayStackService, attachOverlayPosition } from '@flusys/ng-ui';
|
|
11
11
|
import { Router, RouterLink, RouterLinkActive } from '@angular/router';
|
|
12
12
|
import { DomSanitizer } from '@angular/platform-browser';
|
|
13
13
|
|
|
@@ -1652,7 +1652,7 @@ class BaseFormComponent {
|
|
|
1652
1652
|
}
|
|
1653
1653
|
}
|
|
1654
1654
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: BaseFormComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
1655
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: BaseFormComponent, isStandalone: true, selector: "lib-base-form", inputs: { fields: { classPropertyName: "fields", publicName: "fields", isSignal: true, isRequired: true, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, createTitle: { classPropertyName: "createTitle", publicName: "createTitle", isSignal: true, isRequired: false, transformFunction: null }, editTitle: { classPropertyName: "editTitle", publicName: "editTitle", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, submitLabel: { classPropertyName: "submitLabel", publicName: "submitLabel", isSignal: true, isRequired: false, transformFunction: null }, cancelLabel: { classPropertyName: "cancelLabel", publicName: "cancelLabel", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, isEditMode: { classPropertyName: "isEditMode", publicName: "isEditMode", isSignal: true, isRequired: false, transformFunction: null }, initialValue: { classPropertyName: "initialValue", publicName: "initialValue", isSignal: true, isRequired: false, transformFunction: null }, service: { classPropertyName: "service", publicName: "service", isSignal: true, isRequired: false, transformFunction: null }, editId: { classPropertyName: "editId", publicName: "editId", isSignal: true, isRequired: false, transformFunction: null }, cancelRoute: { classPropertyName: "cancelRoute", publicName: "cancelRoute", isSignal: true, isRequired: false, transformFunction: null }, navigateOnSuccess: { classPropertyName: "navigateOnSuccess", publicName: "navigateOnSuccess", isSignal: true, isRequired: false, transformFunction: null }, mapToRequest: { classPropertyName: "mapToRequest", publicName: "mapToRequest", isSignal: true, isRequired: false, transformFunction: null }, mapFromEntity: { classPropertyName: "mapFromEntity", publicName: "mapFromEntity", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onSubmit: "onSubmit", onCancel: "onCancel", onValueChange: "onValueChange" }, queries: [{ propertyName: "fieldTemplates", predicate: BaseFormTemplateDirective, isSignal: true }], ngImport: i0, template: "<f-card>\n <ng-template #header>\n @if (resolvedTitle()) {\n <div class=\"flex justify-between items-center p-4\">\n <h2 class=\"text-xl font-semibold m-0\">{{ resolvedTitle() }}</h2>\n </div>\n }\n </ng-template>\n\n <form (ngSubmit)=\"handleSubmit()\" novalidate>\n <div class=\"grid gap-4\" [class]=\"gridClass()\">\n @for (field of fields(); track field.key) {\n <div class=\"flex flex-col gap-2\" [class.col-span-full]=\"field.fullWidth\">\n @if (field.type !== 'checkbox' && field.type !== 'toggle') {\n <label [for]=\"field.key\" class=\"font-medium\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n }\n\n @switch (field.type) {\n @case ('text') {\n <input\n fInputText\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('email') {\n <input\n fInputText\n type=\"email\"\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('password') {\n <f-password\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n />\n }\n\n @case ('number') {\n <f-inputnumber\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [min]=\"field.min ?? null\"\n [max]=\"field.max ?? null\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n inputStyleClass=\"w-full\"\n />\n }\n\n @case ('textarea') {\n <textarea\n fTextarea\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [rows]=\"field.rows ?? 3\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n ></textarea>\n }\n\n @case ('select') {\n <f-select\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [options]=\"field.options ?? []\"\n optionLabel=\"label\"\n optionValue=\"value\"\n [placeholder]=\"field.placeholder ?? t('shared.select.placeholder')\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('multiselect') {\n <f-multiselect\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [options]=\"field.options ?? []\"\n optionLabel=\"label\"\n optionValue=\"value\"\n [placeholder]=\"field.placeholder ?? t('shared.select.placeholder')\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('date') {\n <f-datepicker\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [minDate]=\"field.minDate ?? null\"\n [maxDate]=\"field.maxDate ?? null\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n inputStyleClass=\"w-full\"\n />\n }\n\n @case ('checkbox') {\n <div class=\"flex items-center gap-2 h-9\">\n <f-checkbox\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [disabled]=\"field.disabled ?? false\"\n [binary]=\"true\"\n [invalid]=\"isFieldInvalid(field)\"\n />\n <label [for]=\"field.key\" class=\"font-medium cursor-pointer select-none\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n </div>\n }\n\n @case ('toggle') {\n <div class=\"flex items-center gap-3 h-9\">\n <f-toggleswitch\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [disabled]=\"field.disabled ?? false\"\n />\n <label [for]=\"field.key\" class=\"font-medium cursor-pointer select-none\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n </div>\n }\n\n @case ('custom') {\n <ng-container\n [ngTemplateOutlet]=\"getFieldTemplate(field.key)\"\n [ngTemplateOutletContext]=\"{ $implicit: getFieldValue(field.key), field: field }\"\n />\n }\n }\n\n @if (isFieldInvalid(field)) {\n <small class=\"text-red-500\">{{ field.label }} {{ t('shared.required') }}</small>\n }\n\n @if (field.hint && !isFieldInvalid(field)) {\n <small class=\"text-surface-400\">{{ field.hint }}</small>\n }\n </div>\n }\n\n <div class=\"col-span-full flex justify-end gap-4 pt-4\">\n <button\n fButton\n type=\"button\"\n severity=\"secondary\"\n [outlined]=\"true\"\n [disabled]=\"effectiveIsLoading()\"\n (click)=\"handleCancel()\"\n >\n <span pButtonLabel>{{ cancelLabel() || t('shared.cancel') }}</span>\n </button>\n <button\n fButton\n type=\"submit\"\n [disabled]=\"!isFormValid() || effectiveIsLoading()\"\n >\n @if (effectiveIsLoading()) {\n <ui-icon pButtonIcon name=\"spinner\" [spin]=\"true\"></ui-icon>\n }\n <span pButtonLabel>{{ submitLabel() || (effectiveIsEditMode() ? t('shared.update') : t('shared.save')) }}</span>\n </button>\n </div>\n </div>\n </form>\n</f-card>\n", dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],[formArray],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "directive", type: i1.NgForm, selector: "form:not([ngNoForm]):not([formGroup]):not([formArray]),ng-form,[ngForm]", inputs: ["ngFormOptions"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: CardComponent, selector: "f-card", inputs: ["header", "subheader", "styleClass", "style"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "component", type: PasswordComponent, selector: "f-password", inputs: ["toggleMask", "feedback", "disabled", "placeholder", "inputId", "invalid", "touched", "inputStyleClass", "styleClass", "style", "ariaDescribedby", "autocomplete", "variant", "size", "fluid", "appendTo", "promptLabel", "weakLabel", "mediumLabel", "strongLabel", "mediumRegex", "strongRegex"], outputs: ["onBlur", "onFocus"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "component", type: InputNumberComponent, selector: "f-inputnumber", inputs: ["mode", "currency", "currencyDisplay", "locale", "min", "max", "step", "showButtons", "buttonLayout", "disabled", "readonly", "inputId", "invalid", "touched", "placeholder", "prefix", "suffix", "useGrouping", "minFractionDigits", "maxFractionDigits", "size", "ariaLabel", "ariaDescribedBy", "inputStyleClass", "styleClass", "style"], outputs: ["onInput", "onFocus", "onBlur", "onKeyDown"] }, { kind: "directive", type: TextareaDirective, selector: "[fTextarea]", inputs: ["invalid", "touched", "variant", "fluid", "autoResize"], outputs: ["onResize"] }, { kind: "component", type: SelectComponent, selector: "f-select", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "showClear", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "inputId", "invalid", "touched", "styleClass", "style", "appendTo", "editable", "readonly", "autofocus", "checkmark", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy"], outputs: ["onFilter", "onChange", "onShow", "onHide", "onBlur", "onFocus", "onClear", "onLazyLoad"] }, { kind: "component", type: MultiSelectComponent, selector: "f-multiselect", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "inputId", "invalid", "touched", "showClear", "optionDisabled", "display", "maxSelectedLabels", "selectionLimit", "showToggleAll", "styleClass", "style", "appendTo", "readonly", "autofocus", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy"], outputs: ["onBlur", "onFocus", "onChange", "onFilter", "onShow", "onHide", "onClear", "onLazyLoad", "onSelectAllChange"] }, { kind: "component", type: DatePickerComponent, selector: "f-datepicker", inputs: ["placeholder", "dateFormat", "disabled", "readonly", "readonlyInput", "showTime", "timeOnly", "hourFormat", "showSeconds", "selectionMode", "minDate", "maxDate", "disabledDates", "disabledDays", "inputId", "invalid", "touched", "showClear", "inputStyleClass", "showIcon", "iconDisplay", "showButtonBar", "inline", "numberOfMonths", "view", "showOtherMonths", "selectOtherMonths", "firstDayOfWeek", "appendTo", "styleClass", "style"], outputs: ["onBlur", "onSelect", "onShow", "onHide", "onClearClick", "onTodayClick", "onMonthChange", "onYearChange"] }, { kind: "component", type: CheckboxComponent, selector: "f-checkbox", inputs: ["label", "binary", "disabled", "readonly", "inputId", "invalid", "indeterminate", "variant", "size", "touched", "styleClass", "style", "checked"], outputs: ["onChange", "onBlur", "touch", "checkedChange"] }, { kind: "component", type: ToggleSwitchComponent, selector: "f-toggleswitch", inputs: ["disabled", "readonly", "invalid", "ariaLabel", "trueValue", "falseValue", "inputId", "size", "tabindex", "styleClass", "style"] }, { kind: "directive", type: FButtonDirective, selector: "[fButton]", inputs: ["severity", "text", "outlined", "link", "variant", "rounded", "raised", "fluid", "disabled", "loading", "loadingIcon", "size", "label", "icon", "iconPos", "ariaLabel", "plain"] }] });
|
|
1655
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: BaseFormComponent, isStandalone: true, selector: "lib-base-form", inputs: { fields: { classPropertyName: "fields", publicName: "fields", isSignal: true, isRequired: true, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, createTitle: { classPropertyName: "createTitle", publicName: "createTitle", isSignal: true, isRequired: false, transformFunction: null }, editTitle: { classPropertyName: "editTitle", publicName: "editTitle", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null }, submitLabel: { classPropertyName: "submitLabel", publicName: "submitLabel", isSignal: true, isRequired: false, transformFunction: null }, cancelLabel: { classPropertyName: "cancelLabel", publicName: "cancelLabel", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, isEditMode: { classPropertyName: "isEditMode", publicName: "isEditMode", isSignal: true, isRequired: false, transformFunction: null }, initialValue: { classPropertyName: "initialValue", publicName: "initialValue", isSignal: true, isRequired: false, transformFunction: null }, service: { classPropertyName: "service", publicName: "service", isSignal: true, isRequired: false, transformFunction: null }, editId: { classPropertyName: "editId", publicName: "editId", isSignal: true, isRequired: false, transformFunction: null }, cancelRoute: { classPropertyName: "cancelRoute", publicName: "cancelRoute", isSignal: true, isRequired: false, transformFunction: null }, navigateOnSuccess: { classPropertyName: "navigateOnSuccess", publicName: "navigateOnSuccess", isSignal: true, isRequired: false, transformFunction: null }, mapToRequest: { classPropertyName: "mapToRequest", publicName: "mapToRequest", isSignal: true, isRequired: false, transformFunction: null }, mapFromEntity: { classPropertyName: "mapFromEntity", publicName: "mapFromEntity", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onSubmit: "onSubmit", onCancel: "onCancel", onValueChange: "onValueChange" }, queries: [{ propertyName: "fieldTemplates", predicate: BaseFormTemplateDirective, isSignal: true }], ngImport: i0, template: "<f-card>\n <ng-template #header>\n @if (resolvedTitle()) {\n <div class=\"flex justify-between items-center p-4\">\n <h2 class=\"text-xl font-semibold m-0\">{{ resolvedTitle() }}</h2>\n </div>\n }\n </ng-template>\n\n <form (ngSubmit)=\"handleSubmit()\" novalidate>\n <div class=\"grid gap-4\" [class]=\"gridClass()\">\n @for (field of fields(); track field.key) {\n <div class=\"flex flex-col gap-2\" [class.col-span-full]=\"field.fullWidth\">\n @if (field.type !== 'checkbox' && field.type !== 'toggle') {\n <label [for]=\"field.key\" class=\"font-medium\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n }\n\n @switch (field.type) {\n @case ('text') {\n <input\n fInputText\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('email') {\n <input\n fInputText\n type=\"email\"\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('password') {\n <f-password\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n />\n }\n\n @case ('number') {\n <f-inputnumber\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [min]=\"field.min ?? null\"\n [max]=\"field.max ?? null\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n inputStyleClass=\"w-full\"\n />\n }\n\n @case ('textarea') {\n <textarea\n fTextarea\n [id]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (blur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [rows]=\"field.rows ?? 3\"\n [class.ng-invalid]=\"isFieldInvalid(field)\"\n [class.ng-dirty]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n ></textarea>\n }\n\n @case ('select') {\n <f-select\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [options]=\"field.options ?? []\"\n optionLabel=\"label\"\n optionValue=\"value\"\n [placeholder]=\"field.placeholder ?? t('shared.select.placeholder')\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('multiselect') {\n <f-multiselect\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [options]=\"field.options ?? []\"\n optionLabel=\"label\"\n optionValue=\"value\"\n [placeholder]=\"field.placeholder ?? t('shared.select.placeholder')\"\n [disabled]=\"field.disabled ?? false\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n />\n }\n\n @case ('date') {\n <f-datepicker\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n (onBlur)=\"markFieldTouched(field.key)\"\n [placeholder]=\"field.placeholder ?? ''\"\n [disabled]=\"field.disabled ?? false\"\n [minDate]=\"field.minDate ?? null\"\n [maxDate]=\"field.maxDate ?? null\"\n [invalid]=\"isFieldInvalid(field)\"\n class=\"w-full\"\n inputStyleClass=\"w-full\"\n />\n }\n\n @case ('checkbox') {\n <div class=\"flex items-center gap-2 h-9\">\n <f-checkbox\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [disabled]=\"field.disabled ?? false\"\n [binary]=\"true\"\n [invalid]=\"isFieldInvalid(field)\"\n />\n <label [for]=\"field.key\" class=\"font-medium cursor-pointer select-none\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n </div>\n }\n\n @case ('toggle') {\n <div class=\"flex items-center gap-3 h-9\">\n <f-toggleswitch\n [inputId]=\"field.key\"\n [name]=\"field.key\"\n [ngModel]=\"getFieldValue(field.key)\"\n (ngModelChange)=\"setFieldValue(field.key, $event)\"\n [disabled]=\"field.disabled ?? false\"\n />\n <label [for]=\"field.key\" class=\"font-medium cursor-pointer select-none\">\n {{ field.label }}\n @if (field.required) {\n <span class=\"text-red-500 ml-1\">*</span>\n }\n </label>\n </div>\n }\n\n @case ('custom') {\n <ng-container\n [ngTemplateOutlet]=\"getFieldTemplate(field.key)\"\n [ngTemplateOutletContext]=\"{ $implicit: getFieldValue(field.key), field: field }\"\n />\n }\n }\n\n @if (isFieldInvalid(field)) {\n <small class=\"text-red-500\">{{ field.label }} {{ t('shared.required') }}</small>\n }\n\n @if (field.hint && !isFieldInvalid(field)) {\n <small class=\"text-surface-400\">{{ field.hint }}</small>\n }\n </div>\n }\n\n <div class=\"col-span-full flex justify-end gap-4 pt-4\">\n <button\n fButton\n type=\"button\"\n severity=\"secondary\"\n [outlined]=\"true\"\n [disabled]=\"effectiveIsLoading()\"\n (click)=\"handleCancel()\"\n >\n <span pButtonLabel>{{ cancelLabel() || t('shared.cancel') }}</span>\n </button>\n <button\n fButton\n type=\"submit\"\n [disabled]=\"!isFormValid() || effectiveIsLoading()\"\n >\n @if (effectiveIsLoading()) {\n <ui-icon pButtonIcon name=\"spinner\" [spin]=\"true\"></ui-icon>\n }\n <span pButtonLabel>{{ submitLabel() || (effectiveIsEditMode() ? t('shared.update') : t('shared.save')) }}</span>\n </button>\n </div>\n </div>\n </form>\n</f-card>\n", dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],[formArray],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "directive", type: i1.NgForm, selector: "form:not([ngNoForm]):not([formGroup]):not([formArray]),ng-form,[ngForm]", inputs: ["ngFormOptions"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "component", type: CardComponent, selector: "f-card", inputs: ["header", "subheader", "styleClass", "style"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "component", type: PasswordComponent, selector: "f-password", inputs: ["toggleMask", "feedback", "disabled", "placeholder", "inputId", "invalid", "touched", "inputStyleClass", "styleClass", "style", "ariaDescribedby", "autocomplete", "variant", "size", "fluid", "appendTo", "promptLabel", "weakLabel", "mediumLabel", "strongLabel", "mediumRegex", "strongRegex"], outputs: ["onBlur", "onFocus"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "component", type: InputNumberComponent, selector: "f-inputnumber", inputs: ["mode", "currency", "currencyDisplay", "locale", "min", "max", "step", "showButtons", "buttonLayout", "disabled", "readonly", "inputId", "invalid", "touched", "placeholder", "prefix", "suffix", "useGrouping", "minFractionDigits", "maxFractionDigits", "size", "ariaLabel", "ariaDescribedBy", "inputStyleClass", "styleClass", "style"], outputs: ["onInput", "onFocus", "onBlur", "onKeyDown"] }, { kind: "directive", type: TextareaDirective, selector: "[fTextarea]", inputs: ["invalid", "touched", "variant", "fluid", "autoResize"], outputs: ["onResize"] }, { kind: "component", type: SelectComponent, selector: "f-select", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "showClear", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "inputId", "invalid", "touched", "styleClass", "style", "appendTo", "editable", "readonly", "autofocus", "checkmark", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy", "selectedObject"], outputs: ["onFilter", "onChange", "onShow", "onHide", "onBlur", "onFocus", "onClear", "onLazyLoad"] }, { kind: "component", type: MultiSelectComponent, selector: "f-multiselect", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "inputId", "invalid", "touched", "showClear", "optionDisabled", "display", "maxSelectedLabels", "selectionLimit", "showToggleAll", "styleClass", "style", "appendTo", "readonly", "autofocus", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy", "selectedObjects"], outputs: ["onBlur", "onFocus", "onChange", "onFilter", "onShow", "onHide", "onClear", "onLazyLoad", "onSelectAllChange"] }, { kind: "component", type: DatePickerComponent, selector: "f-datepicker", inputs: ["placeholder", "dateFormat", "disabled", "readonly", "readonlyInput", "showTime", "timeOnly", "hourFormat", "showSeconds", "selectionMode", "minDate", "maxDate", "disabledDates", "disabledDays", "inputId", "invalid", "touched", "showClear", "inputStyleClass", "showIcon", "iconDisplay", "showButtonBar", "inline", "numberOfMonths", "view", "showOtherMonths", "selectOtherMonths", "firstDayOfWeek", "appendTo", "styleClass", "style"], outputs: ["onBlur", "onSelect", "onShow", "onHide", "onClearClick", "onTodayClick", "onMonthChange", "onYearChange"] }, { kind: "component", type: CheckboxComponent, selector: "f-checkbox", inputs: ["label", "binary", "disabled", "readonly", "inputId", "invalid", "indeterminate", "variant", "size", "touched", "styleClass", "style", "checked"], outputs: ["onChange", "onBlur", "touch", "checkedChange"] }, { kind: "component", type: ToggleSwitchComponent, selector: "f-toggleswitch", inputs: ["disabled", "readonly", "invalid", "ariaLabel", "trueValue", "falseValue", "inputId", "size", "tabindex", "styleClass", "style"] }, { kind: "directive", type: FButtonDirective, selector: "[fButton]", inputs: ["severity", "text", "outlined", "link", "variant", "rounded", "raised", "fluid", "disabled", "loading", "loadingIcon", "size", "label", "icon", "iconPos", "ariaLabel", "plain"] }] });
|
|
1656
1656
|
}
|
|
1657
1657
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: BaseFormComponent, decorators: [{
|
|
1658
1658
|
type: Component,
|
|
@@ -1892,7 +1892,7 @@ class BaseListComponent {
|
|
|
1892
1892
|
return this.translateAdapter?.translate(key, vars) ?? key;
|
|
1893
1893
|
}
|
|
1894
1894
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: BaseListComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
1895
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: BaseListComponent, isStandalone: true, selector: "lib-base-list", inputs: { columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: true, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, showCreateButton: { classPropertyName: "showCreateButton", publicName: "showCreateButton", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, pageSize: { classPropertyName: "pageSize", publicName: "pageSize", isSignal: true, isRequired: false, transformFunction: null }, scrollHeight: { classPropertyName: "scrollHeight", publicName: "scrollHeight", isSignal: true, isRequired: false, transformFunction: null }, emptyMessage: { classPropertyName: "emptyMessage", publicName: "emptyMessage", isSignal: true, isRequired: false, transformFunction: null }, createButtonLabel: { classPropertyName: "createButtonLabel", publicName: "createButtonLabel", isSignal: true, isRequired: false, transformFunction: null }, createButtonIcon: { classPropertyName: "createButtonIcon", publicName: "createButtonIcon", isSignal: true, isRequired: false, transformFunction: null }, data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null }, total: { classPropertyName: "total", publicName: "total", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, service: { classPropertyName: "service", publicName: "service", isSignal: true, isRequired: false, transformFunction: null }, filter: { classPropertyName: "filter", publicName: "filter", isSignal: true, isRequired: false, transformFunction: null }, createRoute: { classPropertyName: "createRoute", publicName: "createRoute", isSignal: true, isRequired: false, transformFunction: null }, editRoute: { classPropertyName: "editRoute", publicName: "editRoute", isSignal: true, isRequired: false, transformFunction: null }, deleteConfirmField: { classPropertyName: "deleteConfirmField", publicName: "deleteConfirmField", isSignal: true, isRequired: false, transformFunction: null }, deleteType: { classPropertyName: "deleteType", publicName: "deleteType", isSignal: true, isRequired: false, transformFunction: null }, idField: { classPropertyName: "idField", publicName: "idField", isSignal: true, isRequired: false, transformFunction: null }, canEdit: { classPropertyName: "canEdit", publicName: "canEdit", isSignal: true, isRequired: false, transformFunction: null }, canDelete: { classPropertyName: "canDelete", publicName: "canDelete", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onCreate: "onCreate", onLazyLoad: "onLazyLoad", onSearch: "onSearch" }, queries: [{ propertyName: "columnTemplates", predicate: BaseListTemplateDirective, isSignal: true }], ngImport: i0, template: "<f-card>\n <ng-template #header>\n @if (title() || searchable() || showCreateButton()) {\n <div\n class=\"flex flex-col sm:flex-row justify-between items-start sm:items-center gap-3 p-4\"\n >\n @if (title()) {\n <h2 class=\"text-xl font-semibold m-0\">{{ title() }}</h2>\n }\n <div class=\"flex items-center gap-2\" [class.ml-auto]=\"!!title()\">\n @if (searchable()) {\n <f-iconfield>\n <f-inputicon\n ><ui-icon name=\"search\" class=\"text-sm\"></ui-icon\n ></f-inputicon>\n <input\n fInputText\n type=\"text\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"onSearchChange($event)\"\n [placeholder]=\"t('shared.search')\"\n />\n </f-iconfield>\n }\n @if (showCreateButton()) {\n <button fButton (click)=\"handleCreate()\">\n <ui-icon pButtonIcon [name]=\"createButtonIcon()\"></ui-icon>\n <span pButtonLabel>{{ resolvedCreateLabel() }}</span>\n </button>\n }\n </div>\n </div>\n }\n </ng-template>\n\n <div class=\"overflow-x-auto\">\n <f-table\n [value]=\"effectiveData()\"\n [loading]=\"effectiveIsLoading()\"\n [lazy]=\"true\"\n [scrollable]=\"true\"\n [scrollHeight]=\"scrollHeight()\"\n [paginator]=\"effectiveTotal() > pageSize()\"\n [rows]=\"pageSize()\"\n [totalRecords]=\"effectiveTotal()\"\n [first]=\"first()\"\n (onLazyLoad)=\"handleLazyLoad($event)\"\n [showCurrentPageReport]=\"true\"\n [currentPageReportTemplate]=\"t('shared.pagination.report')\"\n class=\"p-datatable-striped\"\n >\n <ng-template #header>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <th\n [style.width]=\"col.width\"\n [style.min-width]=\"col.minWidth\"\n [class]=\"getCellClass(col)\"\n >\n {{ col.header }}\n </th>\n }\n @if (effectiveActions().length > 0) {\n <th style=\"width: 120px; text-align: center\">\n {{ t(\"shared.actions\") }}\n </th>\n }\n </tr>\n </ng-template>\n\n <ng-template #body let-item>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <td [class]=\"getCellClass(col)\">\n @switch (col.type ?? \"text\") {\n @case (\"tag\") {\n @if (\n getTagConfig(col, getFieldValue(item, col.field));\n as tagCfg\n ) {\n <f-tag\n [severity]=\"tagCfg.severity\"\n [value]=\"\n tagCfg.label ?? getFieldValueAsString(item, col.field)\n \"\n />\n } @else {\n {{ getFieldValueAsString(item, col.field) }}\n }\n }\n @case (\"boolean\") {\n <f-tag\n [severity]=\"\n getFieldValue(item, col.field) ? 'success' : 'danger'\n \"\n [value]=\"\n getFieldValue(item, col.field)\n ? t('shared.yes')\n : t('shared.no')\n \"\n />\n }\n @case (\"date\") {\n {{\n getFieldValueAsString(item, col.field)\n | date: col.dateFormat ?? \"dd/MM/yyyy\"\n }}\n }\n @case (\"number\") {\n {{ getFieldValueAsString(item, col.field) | number }}\n }\n @case (\"custom\") {\n <ng-container\n [ngTemplateOutlet]=\"getColumnTemplate(col.field)\"\n [ngTemplateOutletContext]=\"{ $implicit: item, field: col.field }\"\n />\n }\n @default {\n {{\n truncateText(getFieldValue(item, col.field), col.truncate)\n }}\n }\n }\n </td>\n }\n @if (effectiveActions().length > 0) {\n <td>\n <div class=\"flex items-center justify-center gap-2\">\n @for (action of effectiveActions(); track $index) {\n @if (!action.show || action.show(item)) {\n <button\n fButton\n [severity]=\"action.severity ?? 'secondary'\"\n [fTooltip]=\"action.tooltip ? t(action.tooltip) : ''\"\n [disabled]=\"\n action.disabled ? action.disabled(item) : false\n \"\n (click)=\"action.handler(item)\"\n [rounded]=\"true\"\n [text]=\"true\"\n >\n <ui-icon pButtonIcon [name]=\"action.icon\"></ui-icon>\n </button>\n }\n }\n </div>\n </td>\n }\n </tr>\n </ng-template>\n\n <ng-template #emptymessage>\n <tr>\n <td [attr.colspan]=\"columnCount()\">\n <div\n class=\"flex flex-col items-center justify-center py-12 text-surface-400\"\n >\n <ui-icon name=\"inbox\" class=\"text-5xl mb-3\"></ui-icon>\n <span>{{ resolvedEmptyMessage() }}</span>\n </div>\n </td>\n </tr>\n </ng-template>\n </f-table>\n </div>\n</f-card>\n", dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: CardComponent, selector: "f-card", inputs: ["header", "subheader", "styleClass", "style"] }, { kind: "component", type: IconFieldComponent, selector: "f-iconfield", inputs: ["iconPosition", "styleClass"] }, { kind: "component", type: InputIconComponent, selector: "f-inputicon", inputs: ["icon", "position", "styleClass", "style"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "directive", type: FButtonDirective, selector: "[fButton]", inputs: ["severity", "text", "outlined", "link", "variant", "rounded", "raised", "fluid", "disabled", "loading", "loadingIcon", "size", "label", "icon", "iconPos", "ariaLabel", "plain"] }, { kind: "component", type: TableComponent, selector: "f-table", inputs: ["value", "lazy", "loading", "rows", "totalRecords", "rowHover", "dataKey", "scrollable", "scrollHeight", "paginator", "first", "rowsPerPageOptions", "showCurrentPageReport", "currentPageReportTemplate", "tableStyle", "styleClass", "globalFilterFields", "filterDelay", "responsiveLayout", "selectionMode", "sortMode", "rowExpandMode", "resizableColumns", "rowStyleClass", "virtualScroll", "virtualScrollItemSize", "sortField", "sortOrder", "multiSortMeta", "filters", "selection", "expandedRowKeys", "contextMenuSelection"], outputs: ["sortFieldChange", "sortOrderChange", "multiSortMetaChange", "filtersChange", "selectionChange", "expandedRowKeysChange", "contextMenuSelectionChange", "onLazyLoad", "onSort", "onFilter", "onRowSelect", "onRowUnselect", "onSelectAllChange", "onRowExpand", "onRowCollapse", "onColResize", "onRowContextMenu"] }, { kind: "component", type: TagComponent, selector: "f-tag", inputs: ["value", "severity", "icon", "rounded", "color", "styleClass", "style"] }, { kind: "directive", type: TooltipDirective, selector: "[fTooltip]", inputs: ["fTooltip", "tooltipPosition", "positionStyle", "tooltipStyleClass", "disabled", "tooltipEvent", "showDelay", "hideDelay", "life", "autoHide", "positionTop", "positionLeft", "escape"] }, { kind: "pipe", type: DatePipe, name: "date" }, { kind: "pipe", type: DecimalPipe, name: "number" }] });
|
|
1895
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: BaseListComponent, isStandalone: true, selector: "lib-base-list", inputs: { columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: true, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, showCreateButton: { classPropertyName: "showCreateButton", publicName: "showCreateButton", isSignal: true, isRequired: false, transformFunction: null }, searchable: { classPropertyName: "searchable", publicName: "searchable", isSignal: true, isRequired: false, transformFunction: null }, pageSize: { classPropertyName: "pageSize", publicName: "pageSize", isSignal: true, isRequired: false, transformFunction: null }, scrollHeight: { classPropertyName: "scrollHeight", publicName: "scrollHeight", isSignal: true, isRequired: false, transformFunction: null }, emptyMessage: { classPropertyName: "emptyMessage", publicName: "emptyMessage", isSignal: true, isRequired: false, transformFunction: null }, createButtonLabel: { classPropertyName: "createButtonLabel", publicName: "createButtonLabel", isSignal: true, isRequired: false, transformFunction: null }, createButtonIcon: { classPropertyName: "createButtonIcon", publicName: "createButtonIcon", isSignal: true, isRequired: false, transformFunction: null }, data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null }, total: { classPropertyName: "total", publicName: "total", isSignal: true, isRequired: false, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: false, transformFunction: null }, service: { classPropertyName: "service", publicName: "service", isSignal: true, isRequired: false, transformFunction: null }, filter: { classPropertyName: "filter", publicName: "filter", isSignal: true, isRequired: false, transformFunction: null }, createRoute: { classPropertyName: "createRoute", publicName: "createRoute", isSignal: true, isRequired: false, transformFunction: null }, editRoute: { classPropertyName: "editRoute", publicName: "editRoute", isSignal: true, isRequired: false, transformFunction: null }, deleteConfirmField: { classPropertyName: "deleteConfirmField", publicName: "deleteConfirmField", isSignal: true, isRequired: false, transformFunction: null }, deleteType: { classPropertyName: "deleteType", publicName: "deleteType", isSignal: true, isRequired: false, transformFunction: null }, idField: { classPropertyName: "idField", publicName: "idField", isSignal: true, isRequired: false, transformFunction: null }, canEdit: { classPropertyName: "canEdit", publicName: "canEdit", isSignal: true, isRequired: false, transformFunction: null }, canDelete: { classPropertyName: "canDelete", publicName: "canDelete", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onCreate: "onCreate", onLazyLoad: "onLazyLoad", onSearch: "onSearch" }, queries: [{ propertyName: "columnTemplates", predicate: BaseListTemplateDirective, isSignal: true }], ngImport: i0, template: "<f-card>\n <ng-template #header>\n @if (title() || searchable() || showCreateButton()) {\n <div\n class=\"flex flex-col sm:flex-row justify-between items-start sm:items-center gap-3 p-4\"\n >\n @if (title()) {\n <h2 class=\"text-xl font-semibold m-0\">{{ title() }}</h2>\n }\n <div class=\"flex items-center gap-2\" [class.ml-auto]=\"!!title()\">\n @if (searchable()) {\n <f-iconfield>\n <f-inputicon icon=\"search\" />\n <input\n fInputText\n type=\"text\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"onSearchChange($event)\"\n [placeholder]=\"t('shared.search')\"\n />\n </f-iconfield>\n }\n @if (showCreateButton()) {\n <button fButton (click)=\"handleCreate()\">\n <ui-icon pButtonIcon [name]=\"createButtonIcon()\"></ui-icon>\n <span pButtonLabel>{{ resolvedCreateLabel() }}</span>\n </button>\n }\n </div>\n </div>\n }\n </ng-template>\n\n <div class=\"overflow-x-auto\">\n <f-table\n [value]=\"effectiveData()\"\n [loading]=\"effectiveIsLoading()\"\n [lazy]=\"true\"\n [scrollable]=\"true\"\n [scrollHeight]=\"scrollHeight()\"\n [paginator]=\"effectiveTotal() > pageSize()\"\n [rows]=\"pageSize()\"\n [totalRecords]=\"effectiveTotal()\"\n [first]=\"first()\"\n (onLazyLoad)=\"handleLazyLoad($event)\"\n [showCurrentPageReport]=\"true\"\n [currentPageReportTemplate]=\"t('shared.pagination.report')\"\n class=\"p-datatable-striped\"\n >\n <ng-template #header>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <th\n [style.width]=\"col.width\"\n [style.min-width]=\"col.minWidth\"\n [class]=\"getCellClass(col)\"\n >\n {{ col.header }}\n </th>\n }\n @if (effectiveActions().length > 0) {\n <th style=\"width: 120px; text-align: center\">\n {{ t(\"shared.actions\") }}\n </th>\n }\n </tr>\n </ng-template>\n\n <ng-template #body let-item>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <td [class]=\"getCellClass(col)\">\n @switch (col.type ?? \"text\") {\n @case (\"tag\") {\n @if (\n getTagConfig(col, getFieldValue(item, col.field));\n as tagCfg\n ) {\n <f-tag\n [severity]=\"tagCfg.severity\"\n [value]=\"\n tagCfg.label ?? getFieldValueAsString(item, col.field)\n \"\n />\n } @else {\n {{ getFieldValueAsString(item, col.field) }}\n }\n }\n @case (\"boolean\") {\n <f-tag\n [severity]=\"\n getFieldValue(item, col.field) ? 'success' : 'danger'\n \"\n [value]=\"\n getFieldValue(item, col.field)\n ? t('shared.yes')\n : t('shared.no')\n \"\n />\n }\n @case (\"date\") {\n {{\n getFieldValueAsString(item, col.field)\n | date: col.dateFormat ?? \"dd/MM/yyyy\"\n }}\n }\n @case (\"number\") {\n {{ getFieldValueAsString(item, col.field) | number }}\n }\n @case (\"custom\") {\n <ng-container\n [ngTemplateOutlet]=\"getColumnTemplate(col.field)\"\n [ngTemplateOutletContext]=\"{ $implicit: item, field: col.field }\"\n />\n }\n @default {\n {{\n truncateText(getFieldValue(item, col.field), col.truncate)\n }}\n }\n }\n </td>\n }\n @if (effectiveActions().length > 0) {\n <td>\n <div class=\"flex items-center justify-center gap-2\">\n @for (action of effectiveActions(); track $index) {\n @if (!action.show || action.show(item)) {\n <button\n fButton\n [severity]=\"action.severity ?? 'secondary'\"\n [fTooltip]=\"action.tooltip ? t(action.tooltip) : ''\"\n [disabled]=\"\n action.disabled ? action.disabled(item) : false\n \"\n (click)=\"action.handler(item)\"\n [rounded]=\"true\"\n [text]=\"true\"\n >\n <ui-icon pButtonIcon [name]=\"action.icon\"></ui-icon>\n </button>\n }\n }\n </div>\n </td>\n }\n </tr>\n </ng-template>\n\n <ng-template #emptymessage>\n <tr>\n <td [attr.colspan]=\"columnCount()\">\n <div\n class=\"flex flex-col items-center justify-center py-12 text-surface-400\"\n >\n <ui-icon name=\"inbox\" class=\"text-5xl mb-3\"></ui-icon>\n <span>{{ resolvedEmptyMessage() }}</span>\n </div>\n </td>\n </tr>\n </ng-template>\n </f-table>\n </div>\n</f-card>\n", dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: CardComponent, selector: "f-card", inputs: ["header", "subheader", "styleClass", "style"] }, { kind: "component", type: IconFieldComponent, selector: "f-iconfield", inputs: ["iconPosition", "styleClass"] }, { kind: "component", type: InputIconComponent, selector: "f-inputicon", inputs: ["icon", "position", "styleClass", "style"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "directive", type: FButtonDirective, selector: "[fButton]", inputs: ["severity", "text", "outlined", "link", "variant", "rounded", "raised", "fluid", "disabled", "loading", "loadingIcon", "size", "label", "icon", "iconPos", "ariaLabel", "plain"] }, { kind: "component", type: TableComponent, selector: "f-table", inputs: ["value", "lazy", "loading", "rows", "totalRecords", "rowHover", "dataKey", "scrollable", "scrollHeight", "paginator", "first", "rowsPerPageOptions", "showCurrentPageReport", "currentPageReportTemplate", "tableStyle", "styleClass", "globalFilterFields", "filterDelay", "responsiveLayout", "selectionMode", "sortMode", "rowExpandMode", "resizableColumns", "rowStyleClass", "virtualScroll", "virtualScrollItemSize", "sortField", "sortOrder", "multiSortMeta", "filters", "selection", "expandedRowKeys", "contextMenuSelection"], outputs: ["sortFieldChange", "sortOrderChange", "multiSortMetaChange", "filtersChange", "selectionChange", "expandedRowKeysChange", "contextMenuSelectionChange", "onLazyLoad", "onSort", "onFilter", "onRowSelect", "onRowUnselect", "onSelectAllChange", "onRowExpand", "onRowCollapse", "onColResize", "onRowContextMenu"] }, { kind: "component", type: TagComponent, selector: "f-tag", inputs: ["value", "severity", "icon", "rounded", "color", "styleClass", "style"] }, { kind: "directive", type: TooltipDirective, selector: "[fTooltip]", inputs: ["fTooltip", "tooltipPosition", "positionStyle", "tooltipStyleClass", "disabled", "tooltipEvent", "showDelay", "hideDelay", "life", "autoHide", "positionTop", "positionLeft", "escape"] }, { kind: "pipe", type: DatePipe, name: "date" }, { kind: "pipe", type: DecimalPipe, name: "number" }] });
|
|
1896
1896
|
}
|
|
1897
1897
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: BaseListComponent, decorators: [{
|
|
1898
1898
|
type: Component,
|
|
@@ -1910,7 +1910,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
1910
1910
|
TableComponent,
|
|
1911
1911
|
TagComponent,
|
|
1912
1912
|
TooltipDirective,
|
|
1913
|
-
], template: "<f-card>\n <ng-template #header>\n @if (title() || searchable() || showCreateButton()) {\n <div\n class=\"flex flex-col sm:flex-row justify-between items-start sm:items-center gap-3 p-4\"\n >\n @if (title()) {\n <h2 class=\"text-xl font-semibold m-0\">{{ title() }}</h2>\n }\n <div class=\"flex items-center gap-2\" [class.ml-auto]=\"!!title()\">\n @if (searchable()) {\n <f-iconfield>\n <f-inputicon
|
|
1913
|
+
], template: "<f-card>\n <ng-template #header>\n @if (title() || searchable() || showCreateButton()) {\n <div\n class=\"flex flex-col sm:flex-row justify-between items-start sm:items-center gap-3 p-4\"\n >\n @if (title()) {\n <h2 class=\"text-xl font-semibold m-0\">{{ title() }}</h2>\n }\n <div class=\"flex items-center gap-2\" [class.ml-auto]=\"!!title()\">\n @if (searchable()) {\n <f-iconfield>\n <f-inputicon icon=\"search\" />\n <input\n fInputText\n type=\"text\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"onSearchChange($event)\"\n [placeholder]=\"t('shared.search')\"\n />\n </f-iconfield>\n }\n @if (showCreateButton()) {\n <button fButton (click)=\"handleCreate()\">\n <ui-icon pButtonIcon [name]=\"createButtonIcon()\"></ui-icon>\n <span pButtonLabel>{{ resolvedCreateLabel() }}</span>\n </button>\n }\n </div>\n </div>\n }\n </ng-template>\n\n <div class=\"overflow-x-auto\">\n <f-table\n [value]=\"effectiveData()\"\n [loading]=\"effectiveIsLoading()\"\n [lazy]=\"true\"\n [scrollable]=\"true\"\n [scrollHeight]=\"scrollHeight()\"\n [paginator]=\"effectiveTotal() > pageSize()\"\n [rows]=\"pageSize()\"\n [totalRecords]=\"effectiveTotal()\"\n [first]=\"first()\"\n (onLazyLoad)=\"handleLazyLoad($event)\"\n [showCurrentPageReport]=\"true\"\n [currentPageReportTemplate]=\"t('shared.pagination.report')\"\n class=\"p-datatable-striped\"\n >\n <ng-template #header>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <th\n [style.width]=\"col.width\"\n [style.min-width]=\"col.minWidth\"\n [class]=\"getCellClass(col)\"\n >\n {{ col.header }}\n </th>\n }\n @if (effectiveActions().length > 0) {\n <th style=\"width: 120px; text-align: center\">\n {{ t(\"shared.actions\") }}\n </th>\n }\n </tr>\n </ng-template>\n\n <ng-template #body let-item>\n <tr>\n @for (col of visibleColumns(); track col.field) {\n <td [class]=\"getCellClass(col)\">\n @switch (col.type ?? \"text\") {\n @case (\"tag\") {\n @if (\n getTagConfig(col, getFieldValue(item, col.field));\n as tagCfg\n ) {\n <f-tag\n [severity]=\"tagCfg.severity\"\n [value]=\"\n tagCfg.label ?? getFieldValueAsString(item, col.field)\n \"\n />\n } @else {\n {{ getFieldValueAsString(item, col.field) }}\n }\n }\n @case (\"boolean\") {\n <f-tag\n [severity]=\"\n getFieldValue(item, col.field) ? 'success' : 'danger'\n \"\n [value]=\"\n getFieldValue(item, col.field)\n ? t('shared.yes')\n : t('shared.no')\n \"\n />\n }\n @case (\"date\") {\n {{\n getFieldValueAsString(item, col.field)\n | date: col.dateFormat ?? \"dd/MM/yyyy\"\n }}\n }\n @case (\"number\") {\n {{ getFieldValueAsString(item, col.field) | number }}\n }\n @case (\"custom\") {\n <ng-container\n [ngTemplateOutlet]=\"getColumnTemplate(col.field)\"\n [ngTemplateOutletContext]=\"{ $implicit: item, field: col.field }\"\n />\n }\n @default {\n {{\n truncateText(getFieldValue(item, col.field), col.truncate)\n }}\n }\n }\n </td>\n }\n @if (effectiveActions().length > 0) {\n <td>\n <div class=\"flex items-center justify-center gap-2\">\n @for (action of effectiveActions(); track $index) {\n @if (!action.show || action.show(item)) {\n <button\n fButton\n [severity]=\"action.severity ?? 'secondary'\"\n [fTooltip]=\"action.tooltip ? t(action.tooltip) : ''\"\n [disabled]=\"\n action.disabled ? action.disabled(item) : false\n \"\n (click)=\"action.handler(item)\"\n [rounded]=\"true\"\n [text]=\"true\"\n >\n <ui-icon pButtonIcon [name]=\"action.icon\"></ui-icon>\n </button>\n }\n }\n </div>\n </td>\n }\n </tr>\n </ng-template>\n\n <ng-template #emptymessage>\n <tr>\n <td [attr.colspan]=\"columnCount()\">\n <div\n class=\"flex flex-col items-center justify-center py-12 text-surface-400\"\n >\n <ui-icon name=\"inbox\" class=\"text-5xl mb-3\"></ui-icon>\n <span>{{ resolvedEmptyMessage() }}</span>\n </div>\n </td>\n </tr>\n </ng-template>\n </f-table>\n </div>\n</f-card>\n" }]
|
|
1914
1914
|
}], propDecorators: { columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: true }] }], actions: [{ type: i0.Input, args: [{ isSignal: true, alias: "actions", required: false }] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], showCreateButton: [{ type: i0.Input, args: [{ isSignal: true, alias: "showCreateButton", required: false }] }], searchable: [{ type: i0.Input, args: [{ isSignal: true, alias: "searchable", required: false }] }], pageSize: [{ type: i0.Input, args: [{ isSignal: true, alias: "pageSize", required: false }] }], scrollHeight: [{ type: i0.Input, args: [{ isSignal: true, alias: "scrollHeight", required: false }] }], emptyMessage: [{ type: i0.Input, args: [{ isSignal: true, alias: "emptyMessage", required: false }] }], createButtonLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "createButtonLabel", required: false }] }], createButtonIcon: [{ type: i0.Input, args: [{ isSignal: true, alias: "createButtonIcon", required: false }] }], data: [{ type: i0.Input, args: [{ isSignal: true, alias: "data", required: false }] }], total: [{ type: i0.Input, args: [{ isSignal: true, alias: "total", required: false }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: false }] }], service: [{ type: i0.Input, args: [{ isSignal: true, alias: "service", required: false }] }], filter: [{ type: i0.Input, args: [{ isSignal: true, alias: "filter", required: false }] }], createRoute: [{ type: i0.Input, args: [{ isSignal: true, alias: "createRoute", required: false }] }], editRoute: [{ type: i0.Input, args: [{ isSignal: true, alias: "editRoute", required: false }] }], deleteConfirmField: [{ type: i0.Input, args: [{ isSignal: true, alias: "deleteConfirmField", required: false }] }], deleteType: [{ type: i0.Input, args: [{ isSignal: true, alias: "deleteType", required: false }] }], idField: [{ type: i0.Input, args: [{ isSignal: true, alias: "idField", required: false }] }], canEdit: [{ type: i0.Input, args: [{ isSignal: true, alias: "canEdit", required: false }] }], canDelete: [{ type: i0.Input, args: [{ isSignal: true, alias: "canDelete", required: false }] }], onCreate: [{ type: i0.Output, args: ["onCreate"] }], onLazyLoad: [{ type: i0.Output, args: ["onLazyLoad"] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }], columnTemplates: [{ type: i0.ContentChildren, args: [i0.forwardRef(() => BaseListTemplateDirective), { isSignal: true }] }] } });
|
|
1915
1915
|
|
|
1916
1916
|
/**
|
|
@@ -2572,6 +2572,11 @@ class FileSelectorDialogComponent {
|
|
|
2572
2572
|
...(ngDevMode ? [{ debugName: "folders" }] : /* istanbul ignore next */ []));
|
|
2573
2573
|
selectedFolderId = signal(null, /* @ts-ignore */
|
|
2574
2574
|
...(ngDevMode ? [{ debugName: "selectedFolderId" }] : /* istanbul ignore next */ []));
|
|
2575
|
+
// Captured at selection time so the trigger label survives a later
|
|
2576
|
+
// (onFilter) search replacing `folders()` with results that no longer
|
|
2577
|
+
// include the already-selected folder.
|
|
2578
|
+
selectedFolderObject = signal(null, /* @ts-ignore */
|
|
2579
|
+
...(ngDevMode ? [{ debugName: "selectedFolderObject" }] : /* istanbul ignore next */ []));
|
|
2575
2580
|
foldersLoading = signal(false, /* @ts-ignore */
|
|
2576
2581
|
...(ngDevMode ? [{ debugName: "foldersLoading" }] : /* istanbul ignore next */ []));
|
|
2577
2582
|
foldersPagination = signal({
|
|
@@ -2585,6 +2590,9 @@ class FileSelectorDialogComponent {
|
|
|
2585
2590
|
...(ngDevMode ? [{ debugName: "storageConfigs" }] : /* istanbul ignore next */ []));
|
|
2586
2591
|
selectedStorageConfigId = signal(null, /* @ts-ignore */
|
|
2587
2592
|
...(ngDevMode ? [{ debugName: "selectedStorageConfigId" }] : /* istanbul ignore next */ []));
|
|
2593
|
+
// Same reasoning as selectedFolderObject above.
|
|
2594
|
+
selectedStorageConfigObject = signal(null, /* @ts-ignore */
|
|
2595
|
+
...(ngDevMode ? [{ debugName: "selectedStorageConfigObject" }] : /* istanbul ignore next */ []));
|
|
2588
2596
|
storageConfigsLoading = signal(false, /* @ts-ignore */
|
|
2589
2597
|
...(ngDevMode ? [{ debugName: "storageConfigsLoading" }] : /* istanbul ignore next */ []));
|
|
2590
2598
|
storageConfigsPagination = signal({
|
|
@@ -2719,6 +2727,7 @@ class FileSelectorDialogComponent {
|
|
|
2719
2727
|
}
|
|
2720
2728
|
onFolderChange(folderId) {
|
|
2721
2729
|
this.selectedFolderId.set(folderId);
|
|
2730
|
+
this.selectedFolderObject.set(folderId ? (this.folders().find((f) => f.id === folderId) ?? null) : null);
|
|
2722
2731
|
this.pagination.update((p) => ({ ...p, currentPage: 0 }));
|
|
2723
2732
|
this.files.set([]);
|
|
2724
2733
|
this.fetchFiles();
|
|
@@ -2753,6 +2762,9 @@ class FileSelectorDialogComponent {
|
|
|
2753
2762
|
}
|
|
2754
2763
|
onStorageConfigChange(configId) {
|
|
2755
2764
|
this.selectedStorageConfigId.set(configId);
|
|
2765
|
+
this.selectedStorageConfigObject.set(configId
|
|
2766
|
+
? (this.storageConfigs().find((c) => c.id === configId) ?? null)
|
|
2767
|
+
: null);
|
|
2756
2768
|
this.pagination.update((p) => ({ ...p, currentPage: 0 }));
|
|
2757
2769
|
this.files.set([]);
|
|
2758
2770
|
this.fetchFiles();
|
|
@@ -2817,6 +2829,7 @@ class FileSelectorDialogComponent {
|
|
|
2817
2829
|
this.pagination.set({ pageSize: this.pageSize(), currentPage: 0 });
|
|
2818
2830
|
this.total.set(undefined);
|
|
2819
2831
|
this.selectedFolderId.set(null);
|
|
2832
|
+
this.selectedFolderObject.set(null);
|
|
2820
2833
|
this.folders.set([]);
|
|
2821
2834
|
this.foldersPagination.set({
|
|
2822
2835
|
pageSize: DEFAULT_SELECTOR_PAGE_SIZE,
|
|
@@ -2824,6 +2837,7 @@ class FileSelectorDialogComponent {
|
|
|
2824
2837
|
});
|
|
2825
2838
|
this.foldersTotal.set(undefined);
|
|
2826
2839
|
this.selectedStorageConfigId.set(null);
|
|
2840
|
+
this.selectedStorageConfigObject.set(null);
|
|
2827
2841
|
this.storageConfigs.set([]);
|
|
2828
2842
|
this.storageConfigsPagination.set({
|
|
2829
2843
|
pageSize: DEFAULT_SELECTOR_PAGE_SIZE,
|
|
@@ -2942,7 +2956,7 @@ class FileSelectorDialogComponent {
|
|
|
2942
2956
|
class="flex flex-col sm:flex-row gap-2 mb-3 items-stretch sm:items-center"
|
|
2943
2957
|
>
|
|
2944
2958
|
<f-iconfield class="flex-1">
|
|
2945
|
-
<f-inputicon
|
|
2959
|
+
<f-inputicon icon="search" />
|
|
2946
2960
|
<input
|
|
2947
2961
|
fInputText
|
|
2948
2962
|
type="text"
|
|
@@ -2967,6 +2981,7 @@ class FileSelectorDialogComponent {
|
|
|
2967
2981
|
[filter]="true"
|
|
2968
2982
|
filterBy="name"
|
|
2969
2983
|
(onFilter)="onFolderSearch($event)"
|
|
2984
|
+
[selectedObject]="selectedFolderObject()"
|
|
2970
2985
|
[loading]="foldersLoading()"
|
|
2971
2986
|
class="w-full sm:w-40"
|
|
2972
2987
|
(onShow)="loadFolders()"
|
|
@@ -2998,6 +3013,7 @@ class FileSelectorDialogComponent {
|
|
|
2998
3013
|
[filter]="true"
|
|
2999
3014
|
filterBy="name"
|
|
3000
3015
|
(onFilter)="onStorageConfigSearch($event)"
|
|
3016
|
+
[selectedObject]="selectedStorageConfigObject()"
|
|
3001
3017
|
[loading]="storageConfigsLoading()"
|
|
3002
3018
|
class="w-full sm:w-40"
|
|
3003
3019
|
(onShow)="loadStorageConfigs()"
|
|
@@ -3131,7 +3147,7 @@ class FileSelectorDialogComponent {
|
|
|
3131
3147
|
</ng-template>
|
|
3132
3148
|
}
|
|
3133
3149
|
</f-dialog>
|
|
3134
|
-
`, isInline: true, styles: [".file-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:.75rem;max-height:300px;overflow-y:auto;padding:.5rem}@media(min-width:480px){.file-grid{grid-template-columns:repeat(3,1fr);max-height:350px}}@media(min-width:640px){.file-grid{grid-template-columns:repeat(auto-fill,minmax(140px,1fr));gap:1rem;max-height:400px}}.file-card{border:2px solid var(--f-surface-300);border-radius:var(--f-border-radius);cursor:pointer;transition:all .2s ease;overflow:hidden;background:var(--f-surface-0)}:host-context(.app-dark) .file-card,.app-dark .file-card{border-color:var(--f-surface-600);background:var(--f-surface-800)}.file-card:hover:not(.disabled){border-color:var(--f-primary-color);transform:translateY(-2px);box-shadow:var(--f-overlay-shadow)}.file-card.selected{border-color:var(--f-primary-color);background:var(--f-primary-50)}:host-context(.app-dark) .file-card.selected,.app-dark .file-card.selected{background:var(--f-primary-900)}.file-card.disabled{opacity:.5;cursor:not-allowed}.file-preview{position:relative;height:80px;display:flex;align-items:center;justify-content:center;background:var(--f-surface-100)}@media(min-width:640px){.file-preview{height:100px}}:host-context(.app-dark) .file-preview,.app-dark .file-preview{background:var(--f-surface-700)}.selected-overlay{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;background:rgba(var(--f-primary-500-rgb, 59, 130, 246),.3)}.selected-overlay i{color:var(--f-primary-color);background:var(--f-surface-0);border-radius:50%;padding:.5rem}:host-context(.app-dark) .selected-overlay i,.app-dark .selected-overlay i{background:var(--f-surface-900)}\n"], dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "directive", type: IsEmptyImageDirective, selector: "img", inputs: ["src"] }, { kind: "component", type: DialogComponent, selector: "f-dialog", inputs: ["header", "visible", "modal", "closable", "closeOnEscape", "dismissableMask", "resizable", "draggable", "maximizable", "blockScroll", "returnFocusOnClose", "position", "style", "styleClass", "breakpoints"], outputs: ["visibleChange", "onShow", "onHide", "onMaximize"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "component", type: ButtonComponent, selector: "f-button", inputs: ["label", "icon", "iconPos", "severity", "type", "disabled", "loading", "loadingIcon", "text", "link", "outlined", "plain", "variant", "raised", "rounded", "fluid", "size", "ariaLabel", "autofocus", "tabindex", "styleClass", "style", "badge", "badgeSeverity", "badgeClass"], outputs: ["onClick", "onFocus", "onBlur"] }, { kind: "component", type: IconFieldComponent, selector: "f-iconfield", inputs: ["iconPosition", "styleClass"] }, { kind: "component", type: InputIconComponent, selector: "f-inputicon", inputs: ["icon", "position", "styleClass", "style"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "component", type: SelectComponent, selector: "f-select", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "showClear", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "inputId", "invalid", "touched", "styleClass", "style", "appendTo", "editable", "readonly", "autofocus", "checkmark", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy"], outputs: ["onFilter", "onChange", "onShow", "onHide", "onBlur", "onFocus", "onClear", "onLazyLoad"] }, { kind: "component", type: FileUploaderComponent, selector: "lib-file-uploader", inputs: ["uploadFile", "uploadMultipleFiles", "acceptTypes", "multiple", "maxFiles", "maxSizeMb", "uploadOptions", "disabled", "showPreview", "autoUpload"], outputs: ["fileUploaded", "filesUploaded", "onError", "fileSelected"] }, { kind: "pipe", type: TranslatePipe, name: "translate" }] });
|
|
3150
|
+
`, isInline: true, styles: [".file-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:.75rem;max-height:300px;overflow-y:auto;padding:.5rem}@media(min-width:480px){.file-grid{grid-template-columns:repeat(3,1fr);max-height:350px}}@media(min-width:640px){.file-grid{grid-template-columns:repeat(auto-fill,minmax(140px,1fr));gap:1rem;max-height:400px}}.file-card{border:2px solid var(--f-surface-300);border-radius:var(--f-border-radius);cursor:pointer;transition:all .2s ease;overflow:hidden;background:var(--f-surface-0)}:host-context(.app-dark) .file-card,.app-dark .file-card{border-color:var(--f-surface-600);background:var(--f-surface-800)}.file-card:hover:not(.disabled){border-color:var(--f-primary-color);transform:translateY(-2px);box-shadow:var(--f-overlay-shadow)}.file-card.selected{border-color:var(--f-primary-color);background:var(--f-primary-50)}:host-context(.app-dark) .file-card.selected,.app-dark .file-card.selected{background:var(--f-primary-900)}.file-card.disabled{opacity:.5;cursor:not-allowed}.file-preview{position:relative;height:80px;display:flex;align-items:center;justify-content:center;background:var(--f-surface-100)}@media(min-width:640px){.file-preview{height:100px}}:host-context(.app-dark) .file-preview,.app-dark .file-preview{background:var(--f-surface-700)}.selected-overlay{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;background:rgba(var(--f-primary-500-rgb, 59, 130, 246),.3)}.selected-overlay i{color:var(--f-primary-color);background:var(--f-surface-0);border-radius:50%;padding:.5rem}:host-context(.app-dark) .selected-overlay i,.app-dark .selected-overlay i{background:var(--f-surface-900)}\n"], dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "directive", type: IsEmptyImageDirective, selector: "img", inputs: ["src"] }, { kind: "component", type: DialogComponent, selector: "f-dialog", inputs: ["header", "visible", "modal", "closable", "closeOnEscape", "dismissableMask", "resizable", "draggable", "maximizable", "blockScroll", "returnFocusOnClose", "position", "style", "styleClass", "breakpoints"], outputs: ["visibleChange", "onShow", "onHide", "onMaximize"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "component", type: ButtonComponent, selector: "f-button", inputs: ["label", "icon", "iconPos", "severity", "type", "disabled", "loading", "loadingIcon", "text", "link", "outlined", "plain", "variant", "raised", "rounded", "fluid", "size", "ariaLabel", "autofocus", "tabindex", "styleClass", "style", "badge", "badgeSeverity", "badgeClass"], outputs: ["onClick", "onFocus", "onBlur"] }, { kind: "component", type: IconFieldComponent, selector: "f-iconfield", inputs: ["iconPosition", "styleClass"] }, { kind: "component", type: InputIconComponent, selector: "f-inputicon", inputs: ["icon", "position", "styleClass", "style"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "component", type: SelectComponent, selector: "f-select", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "showClear", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "inputId", "invalid", "touched", "styleClass", "style", "appendTo", "editable", "readonly", "autofocus", "checkmark", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy", "selectedObject"], outputs: ["onFilter", "onChange", "onShow", "onHide", "onBlur", "onFocus", "onClear", "onLazyLoad"] }, { kind: "component", type: FileUploaderComponent, selector: "lib-file-uploader", inputs: ["uploadFile", "uploadMultipleFiles", "acceptTypes", "multiple", "maxFiles", "maxSizeMb", "uploadOptions", "disabled", "showPreview", "autoUpload"], outputs: ["fileUploaded", "filesUploaded", "onError", "fileSelected"] }, { kind: "pipe", type: TranslatePipe, name: "translate" }] });
|
|
3135
3151
|
}
|
|
3136
3152
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: FileSelectorDialogComponent, decorators: [{
|
|
3137
3153
|
type: Component,
|
|
@@ -3201,7 +3217,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3201
3217
|
class="flex flex-col sm:flex-row gap-2 mb-3 items-stretch sm:items-center"
|
|
3202
3218
|
>
|
|
3203
3219
|
<f-iconfield class="flex-1">
|
|
3204
|
-
<f-inputicon
|
|
3220
|
+
<f-inputicon icon="search" />
|
|
3205
3221
|
<input
|
|
3206
3222
|
fInputText
|
|
3207
3223
|
type="text"
|
|
@@ -3226,6 +3242,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3226
3242
|
[filter]="true"
|
|
3227
3243
|
filterBy="name"
|
|
3228
3244
|
(onFilter)="onFolderSearch($event)"
|
|
3245
|
+
[selectedObject]="selectedFolderObject()"
|
|
3229
3246
|
[loading]="foldersLoading()"
|
|
3230
3247
|
class="w-full sm:w-40"
|
|
3231
3248
|
(onShow)="loadFolders()"
|
|
@@ -3257,6 +3274,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3257
3274
|
[filter]="true"
|
|
3258
3275
|
filterBy="name"
|
|
3259
3276
|
(onFilter)="onStorageConfigSearch($event)"
|
|
3277
|
+
[selectedObject]="selectedStorageConfigObject()"
|
|
3260
3278
|
[loading]="storageConfigsLoading()"
|
|
3261
3279
|
class="w-full sm:w-40"
|
|
3262
3280
|
(onShow)="loadStorageConfigs()"
|
|
@@ -3405,7 +3423,7 @@ class IconComponent {
|
|
|
3405
3423
|
@if (iconType() === IconTypeEnum.IMAGE_FILE_LINK) {
|
|
3406
3424
|
<img [alt]="icon()" [src]="icon()" />
|
|
3407
3425
|
} @else {
|
|
3408
|
-
<ui-icon [name]="icon()"></ui-icon>
|
|
3426
|
+
<ui-icon [name]="icon()" [size]="17"></ui-icon>
|
|
3409
3427
|
}
|
|
3410
3428
|
}
|
|
3411
3429
|
`, isInline: true, dependencies: [{ kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }] });
|
|
@@ -3420,7 +3438,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3420
3438
|
@if (iconType() === IconTypeEnum.IMAGE_FILE_LINK) {
|
|
3421
3439
|
<img [alt]="icon()" [src]="icon()" />
|
|
3422
3440
|
} @else {
|
|
3423
|
-
<ui-icon [name]="icon()"></ui-icon>
|
|
3441
|
+
<ui-icon [name]="icon()" [size]="17"></ui-icon>
|
|
3424
3442
|
}
|
|
3425
3443
|
}
|
|
3426
3444
|
`,
|
|
@@ -3495,6 +3513,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3495
3513
|
class LazyMultiSelectComponent extends BaseFormControl {
|
|
3496
3514
|
document = inject(DOCUMENT$1);
|
|
3497
3515
|
appRef = inject(ApplicationRef);
|
|
3516
|
+
overlayStack = inject(OverlayStackService);
|
|
3498
3517
|
translateAdapter = inject(TranslateService, {
|
|
3499
3518
|
optional: true,
|
|
3500
3519
|
});
|
|
@@ -3506,6 +3525,7 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3506
3525
|
...(ngDevMode ? [{ debugName: "overlayTemplate" }] : /* istanbul ignore next */ []));
|
|
3507
3526
|
// Portal state
|
|
3508
3527
|
overlayViewRef = null;
|
|
3528
|
+
detachOverlayPosition = null;
|
|
3509
3529
|
// Inputs
|
|
3510
3530
|
placeHolder = input('', /* @ts-ignore */
|
|
3511
3531
|
...(ngDevMode ? [{ debugName: "placeHolder" }] : /* istanbul ignore next */ []));
|
|
@@ -3529,9 +3549,30 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3529
3549
|
...(ngDevMode ? [{ debugName: "pagination" }] : /* istanbul ignore next */ []));
|
|
3530
3550
|
selectDataList = input.required(/* @ts-ignore */
|
|
3531
3551
|
...(ngDevMode ? [{ debugName: "selectDataList" }] : /* istanbul ignore next */ []));
|
|
3552
|
+
/**
|
|
3553
|
+
* Full option objects for the currently selected values, supplied by the
|
|
3554
|
+
* caller (or a subclass like UserMultiSelectComponent). Pinned into
|
|
3555
|
+
* `mergedDataList` (deduped by `value`) so chips/labels/checkboxes survive
|
|
3556
|
+
* a later search/page reload that replaces `selectDataList()` without the
|
|
3557
|
+
* selection having changed. This component renders its own overlay list
|
|
3558
|
+
* (it does not build on f-multiselect), so the merge has to happen here.
|
|
3559
|
+
*/
|
|
3560
|
+
selectedObjects = input([], /* @ts-ignore */
|
|
3561
|
+
...(ngDevMode ? [{ debugName: "selectedObjects" }] : /* istanbul ignore next */ []));
|
|
3532
3562
|
// Two-way bound value
|
|
3533
3563
|
value = model(null, /* @ts-ignore */
|
|
3534
3564
|
...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
|
|
3565
|
+
selectedObjectEntries = computed(() => {
|
|
3566
|
+
const vals = this.value() ?? [];
|
|
3567
|
+
return this.selectedObjects().filter((o) => vals.includes(o.value));
|
|
3568
|
+
}, /* @ts-ignore */
|
|
3569
|
+
...(ngDevMode ? [{ debugName: "selectedObjectEntries" }] : /* istanbul ignore next */ []));
|
|
3570
|
+
mergedDataList = computed(() => {
|
|
3571
|
+
const base = this.selectDataList();
|
|
3572
|
+
const extras = this.selectedObjectEntries().filter((sel) => !base.some((o) => o.value === sel.value));
|
|
3573
|
+
return extras.length ? [...extras, ...base] : base;
|
|
3574
|
+
}, /* @ts-ignore */
|
|
3575
|
+
...(ngDevMode ? [{ debugName: "mergedDataList" }] : /* istanbul ignore next */ []));
|
|
3535
3576
|
// Outputs
|
|
3536
3577
|
onSearch = output();
|
|
3537
3578
|
onPagination = output();
|
|
@@ -3550,7 +3591,7 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3550
3591
|
count: selectedValues.length,
|
|
3551
3592
|
});
|
|
3552
3593
|
}
|
|
3553
|
-
return this.
|
|
3594
|
+
return this.mergedDataList()
|
|
3554
3595
|
.filter((item) => selectedValues.includes(item.value))
|
|
3555
3596
|
.map((item) => item.label)
|
|
3556
3597
|
.join(', ');
|
|
@@ -3563,7 +3604,7 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3563
3604
|
...(ngDevMode ? [{ debugName: "hasSelectedValues" }] : /* istanbul ignore next */ []));
|
|
3564
3605
|
isSelectAll = computed(() => {
|
|
3565
3606
|
const selectedValues = this.value() ?? [];
|
|
3566
|
-
const allValues = this.
|
|
3607
|
+
const allValues = this.mergedDataList().map((item) => item.value);
|
|
3567
3608
|
if (selectedValues.length === 0 || allValues.length === 0)
|
|
3568
3609
|
return false;
|
|
3569
3610
|
return allValues.every((val) => selectedValues.includes(val));
|
|
@@ -3630,25 +3671,33 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3630
3671
|
// Create embedded view and append to body (portal pattern)
|
|
3631
3672
|
this.overlayViewRef = this.overlayTemplate().createEmbeddedView({});
|
|
3632
3673
|
this.appRef.attachView(this.overlayViewRef);
|
|
3674
|
+
// Zoneless CD only flushes this view on the next scheduler tick, so
|
|
3675
|
+
// without a synchronous detectChanges() here the panel is still just its
|
|
3676
|
+
// empty shell (no search box, no @for rows) at the moment we measure it
|
|
3677
|
+
// below. attachOverlayPosition() would place it for that near-zero
|
|
3678
|
+
// height, then the ResizeObserver correction a frame later — once the
|
|
3679
|
+
// real content has rendered — snaps it to its true (often much taller)
|
|
3680
|
+
// size, which is the visible "blip down and up" the panel does on open.
|
|
3681
|
+
this.overlayViewRef.detectChanges();
|
|
3633
3682
|
const overlayEl = this.overlayViewRef.rootNodes[0];
|
|
3634
3683
|
this.document.body.appendChild(overlayEl);
|
|
3635
|
-
|
|
3636
|
-
|
|
3637
|
-
|
|
3638
|
-
|
|
3639
|
-
|
|
3640
|
-
|
|
3641
|
-
|
|
3642
|
-
|
|
3643
|
-
|
|
3644
|
-
|
|
3645
|
-
|
|
3646
|
-
`;
|
|
3647
|
-
}
|
|
3684
|
+
const anchorEl = this.pSelectRef()?.nativeElement;
|
|
3685
|
+
if (!anchorEl)
|
|
3686
|
+
return;
|
|
3687
|
+
overlayEl.style.position = 'fixed';
|
|
3688
|
+
overlayEl.style.zIndex = `${this.overlayStack.open()}`;
|
|
3689
|
+
// Flips above the field and caps its height against the viewport, so a list
|
|
3690
|
+
// that grows after its lazy page arrives is never cut off by the screen edge.
|
|
3691
|
+
this.detachOverlayPosition = attachOverlayPosition(anchorEl, overlayEl, {
|
|
3692
|
+
gap: 2,
|
|
3693
|
+
matchAnchorWidth: true,
|
|
3694
|
+
});
|
|
3648
3695
|
}
|
|
3649
3696
|
closeOverlay() {
|
|
3650
3697
|
this.openOptions.set(false);
|
|
3651
3698
|
this.pSelectRef()?.nativeElement.classList.remove('p-focus');
|
|
3699
|
+
this.detachOverlayPosition?.();
|
|
3700
|
+
this.detachOverlayPosition = null;
|
|
3652
3701
|
if (this.overlayViewRef) {
|
|
3653
3702
|
this.appRef.detachView(this.overlayViewRef);
|
|
3654
3703
|
this.overlayViewRef.destroy();
|
|
@@ -3683,7 +3732,7 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3683
3732
|
}
|
|
3684
3733
|
changeSelectAll(event) {
|
|
3685
3734
|
if (event.checked) {
|
|
3686
|
-
this.value.set(this.
|
|
3735
|
+
this.value.set(this.mergedDataList().map((item) => item.value));
|
|
3687
3736
|
}
|
|
3688
3737
|
else {
|
|
3689
3738
|
this.value.set([]);
|
|
@@ -3700,7 +3749,7 @@ class LazyMultiSelectComponent extends BaseFormControl {
|
|
|
3700
3749
|
return key;
|
|
3701
3750
|
}
|
|
3702
3751
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: LazyMultiSelectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
3703
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: LazyMultiSelectComponent, isStandalone: true, selector: "lib-lazy-multi-select", inputs: { placeHolder: { classPropertyName: "placeHolder", publicName: "placeHolder", isSignal: true, isRequired: false, transformFunction: null }, showClear: { classPropertyName: "showClear", publicName: "showClear", isSignal: true, isRequired: false, transformFunction: null }, isEditMode: { classPropertyName: "isEditMode", publicName: "isEditMode", isSignal: true, isRequired: true, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: true, transformFunction: null }, total: { classPropertyName: "total", publicName: "total", isSignal: true, isRequired: true, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: true, transformFunction: null }, selectDataList: { classPropertyName: "selectDataList", publicName: "selectDataList", isSignal: true, isRequired: true, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange", onSearch: "onSearch", onPagination: "onPagination" }, providers: [provideValueAccessor(LazyMultiSelectComponent)], viewQueries: [{ propertyName: "pSelectRef", first: true, predicate: ["pSelect"], descendants: true, isSignal: true }, { propertyName: "overlayTemplate", first: true, predicate: ["overlayTpl"], descendants: true, isSignal: true }], usesInheritance: true, ngImport: i0, template: "<div\n class=\"w-full flex items-center justify-between px-3 py-2 text-sm rounded-lg border border-(--f-form-field-border-color) bg-(--f-form-field-background) cursor-pointer min-h-[34px]\"\n #pSelect\n (click)=\"onSelectClick()\"\n [class.opacity-50]=\"disabled()\"\n [class.pointer-events-none]=\"disabled()\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n [class.overflow-hidden]=\"!isEditMode()\"\n>\n @if (selectedValueDisplay()) {\n <span\n class=\"flex-1 truncate text-(--f-form-field-color)\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n >\n {{ selectedValueDisplay() }}\n </span>\n } @else {\n <span class=\"flex-1 truncate text-(--f-form-field-placeholder-color)\">{{\n displayPlaceholder()\n }}</span>\n }\n\n @if (showClear() && hasSelectedValues()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-text-muted-color) hover:text-(--f-text-hover-color) cursor-pointer\"\n (click)=\"clear($event)\"\n >\n <ui-icon name=\"times\" class=\"text-xs\"></ui-icon>\n </span>\n }\n\n @if (isEditMode()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-form-field-placeholder-color)\"\n >\n <ui-icon name=\"chevron-down\" class=\"text-xs\"></ui-icon>\n </span>\n }\n</div>\n\n<ng-template #overlayTpl>\n <div\n class=\"flex flex-col max-h-[250px] overflow-hidden\"\n (click)=\"onOverlayClick($event)\"\n >\n <div\n class=\"p-3 border-b border-(--f-content-border-color) bg-(--f-content-hover-background) shrink-0 w-full flex flex-row gap-2 items-center\"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isSelectAll()\"\n [disabled]=\"disabled()\"\n (onChange)=\"changeSelectAll($event)\"\n />\n <input\n type=\"text\"\n fInputText\n class=\"w-full\"\n [placeholder]=\"'shared.search' | translate\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </div>\n <div\n class=\"flex-1 overflow-y-auto min-h-0 w-full\"\n (scroll)=\"onScroll($event)\"\n >\n <ul\n class=\"m-0 py-1 list-none bg-(--f-overlay-popover-background) text-(--f-text-color) w-full\"\n >\n @for (data of
|
|
3752
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: LazyMultiSelectComponent, isStandalone: true, selector: "lib-lazy-multi-select", inputs: { placeHolder: { classPropertyName: "placeHolder", publicName: "placeHolder", isSignal: true, isRequired: false, transformFunction: null }, showClear: { classPropertyName: "showClear", publicName: "showClear", isSignal: true, isRequired: false, transformFunction: null }, isEditMode: { classPropertyName: "isEditMode", publicName: "isEditMode", isSignal: true, isRequired: true, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: true, transformFunction: null }, total: { classPropertyName: "total", publicName: "total", isSignal: true, isRequired: true, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: true, transformFunction: null }, selectDataList: { classPropertyName: "selectDataList", publicName: "selectDataList", isSignal: true, isRequired: true, transformFunction: null }, selectedObjects: { classPropertyName: "selectedObjects", publicName: "selectedObjects", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange", onSearch: "onSearch", onPagination: "onPagination" }, providers: [provideValueAccessor(LazyMultiSelectComponent)], viewQueries: [{ propertyName: "pSelectRef", first: true, predicate: ["pSelect"], descendants: true, isSignal: true }, { propertyName: "overlayTemplate", first: true, predicate: ["overlayTpl"], descendants: true, isSignal: true }], usesInheritance: true, ngImport: i0, template: "<div\n class=\"w-full flex items-center justify-between px-3 py-2 text-sm rounded-lg border border-(--f-form-field-border-color) bg-(--f-form-field-background) cursor-pointer min-h-[34px]\"\n #pSelect\n (click)=\"onSelectClick()\"\n [class.opacity-50]=\"disabled()\"\n [class.pointer-events-none]=\"disabled()\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n [class.overflow-hidden]=\"!isEditMode()\"\n>\n @if (selectedValueDisplay()) {\n <span\n class=\"flex-1 truncate text-(--f-form-field-color)\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n >\n {{ selectedValueDisplay() }}\n </span>\n } @else {\n <span class=\"flex-1 truncate text-(--f-form-field-placeholder-color)\">{{\n displayPlaceholder()\n }}</span>\n }\n\n @if (showClear() && hasSelectedValues()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-text-muted-color) hover:text-(--f-text-hover-color) cursor-pointer\"\n (click)=\"clear($event)\"\n >\n <ui-icon name=\"times\" class=\"text-xs\"></ui-icon>\n </span>\n }\n\n @if (isEditMode()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-form-field-placeholder-color)\"\n >\n <ui-icon name=\"chevron-down\" class=\"text-xs\"></ui-icon>\n </span>\n }\n</div>\n\n<ng-template #overlayTpl>\n <div\n class=\"flex flex-col max-h-[250px] overflow-hidden\"\n (click)=\"onOverlayClick($event)\"\n >\n <div\n class=\"p-3 border-b border-(--f-content-border-color) bg-(--f-content-hover-background) shrink-0 w-full flex flex-row gap-2 items-center\"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isSelectAll()\"\n [disabled]=\"disabled()\"\n (onChange)=\"changeSelectAll($event)\"\n />\n <input\n type=\"text\"\n fInputText\n class=\"w-full\"\n [placeholder]=\"'shared.search' | translate\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </div>\n <div\n class=\"flex-1 overflow-y-auto min-h-0 w-full\"\n (scroll)=\"onScroll($event)\"\n >\n <ul\n class=\"m-0 py-1 list-none bg-(--f-overlay-popover-background) text-(--f-text-color) w-full\"\n >\n @for (data of mergedDataList(); track data.value) {\n @let isItemSelected = isSelected(data);\n <li\n class=\"px-3 py-2 cursor-pointer transition-colors flex flex-row gap-2 items-center text-sm\"\n [class]=\"\n isItemSelected\n ? 'bg-primary/10 text-primary'\n : 'text-(--f-text-color) hover:bg-(--f-content-hover-background)'\n \"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isItemSelected\"\n [disabled]=\"disabled()\"\n (onChange)=\"selectValue($event, data)\"\n />\n <span class=\"flex flex-col min-w-0 flex-1\">\n <span class=\"truncate\">{{ data.label }}</span>\n @if (data.subLabel) {\n <span class=\"truncate text-xs text-(--f-text-muted-color)\">{{\n data.subLabel\n }}</span>\n }\n </span>\n </li>\n }\n </ul>\n </div>\n </div>\n</ng-template>\n", dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: UiIconComponent, selector: "ui-icon", inputs: ["name", "size", "spin", "fill", "severity"] }, { kind: "component", type: CheckboxComponent, selector: "f-checkbox", inputs: ["label", "binary", "disabled", "readonly", "inputId", "invalid", "indeterminate", "variant", "size", "touched", "styleClass", "style", "checked"], outputs: ["onChange", "onBlur", "touch", "checkedChange"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "pipe", type: TranslatePipe, name: "translate" }] });
|
|
3704
3753
|
}
|
|
3705
3754
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: LazyMultiSelectComponent, decorators: [{
|
|
3706
3755
|
type: Component,
|
|
@@ -3710,8 +3759,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3710
3759
|
CheckboxComponent,
|
|
3711
3760
|
InputTextDirective,
|
|
3712
3761
|
TranslatePipe,
|
|
3713
|
-
], providers: [provideValueAccessor(LazyMultiSelectComponent)], template: "<div\n class=\"w-full flex items-center justify-between px-3 py-2 text-sm rounded-lg border border-(--f-form-field-border-color) bg-(--f-form-field-background) cursor-pointer min-h-[34px]\"\n #pSelect\n (click)=\"onSelectClick()\"\n [class.opacity-50]=\"disabled()\"\n [class.pointer-events-none]=\"disabled()\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n [class.overflow-hidden]=\"!isEditMode()\"\n>\n @if (selectedValueDisplay()) {\n <span\n class=\"flex-1 truncate text-(--f-form-field-color)\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n >\n {{ selectedValueDisplay() }}\n </span>\n } @else {\n <span class=\"flex-1 truncate text-(--f-form-field-placeholder-color)\">{{\n displayPlaceholder()\n }}</span>\n }\n\n @if (showClear() && hasSelectedValues()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-text-muted-color) hover:text-(--f-text-hover-color) cursor-pointer\"\n (click)=\"clear($event)\"\n >\n <ui-icon name=\"times\" class=\"text-xs\"></ui-icon>\n </span>\n }\n\n @if (isEditMode()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-form-field-placeholder-color)\"\n >\n <ui-icon name=\"chevron-down\" class=\"text-xs\"></ui-icon>\n </span>\n }\n</div>\n\n<ng-template #overlayTpl>\n <div\n class=\"flex flex-col max-h-[250px] overflow-hidden\"\n (click)=\"onOverlayClick($event)\"\n >\n <div\n class=\"p-3 border-b border-(--f-content-border-color) bg-(--f-content-hover-background) shrink-0 w-full flex flex-row gap-2 items-center\"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isSelectAll()\"\n [disabled]=\"disabled()\"\n (onChange)=\"changeSelectAll($event)\"\n />\n <input\n type=\"text\"\n fInputText\n class=\"w-full\"\n [placeholder]=\"'shared.search' | translate\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </div>\n <div\n class=\"flex-1 overflow-y-auto min-h-0 w-full\"\n (scroll)=\"onScroll($event)\"\n >\n <ul\n class=\"m-0 py-1 list-none bg-(--f-overlay-popover-background) text-(--f-text-color) w-full\"\n >\n @for (data of
|
|
3714
|
-
}], ctorParameters: () => [], propDecorators: { pSelectRef: [{ type: i0.ViewChild, args: ['pSelect', { isSignal: true }] }], overlayTemplate: [{ type: i0.ViewChild, args: ['overlayTpl', { isSignal: true }] }], placeHolder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeHolder", required: false }] }], showClear: [{ type: i0.Input, args: [{ isSignal: true, alias: "showClear", required: false }] }], isEditMode: [{ type: i0.Input, args: [{ isSignal: true, alias: "isEditMode", required: true }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: true }] }], total: [{ type: i0.Input, args: [{ isSignal: true, alias: "total", required: true }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: true }] }], selectDataList: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectDataList", required: true }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }], onPagination: [{ type: i0.Output, args: ["onPagination"] }] } });
|
|
3762
|
+
], providers: [provideValueAccessor(LazyMultiSelectComponent)], template: "<div\n class=\"w-full flex items-center justify-between px-3 py-2 text-sm rounded-lg border border-(--f-form-field-border-color) bg-(--f-form-field-background) cursor-pointer min-h-[34px]\"\n #pSelect\n (click)=\"onSelectClick()\"\n [class.opacity-50]=\"disabled()\"\n [class.pointer-events-none]=\"disabled()\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n [class.overflow-hidden]=\"!isEditMode()\"\n>\n @if (selectedValueDisplay()) {\n <span\n class=\"flex-1 truncate text-(--f-form-field-color)\"\n [class.edit-mode-element-css]=\"!isEditMode()\"\n >\n {{ selectedValueDisplay() }}\n </span>\n } @else {\n <span class=\"flex-1 truncate text-(--f-form-field-placeholder-color)\">{{\n displayPlaceholder()\n }}</span>\n }\n\n @if (showClear() && hasSelectedValues()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-text-muted-color) hover:text-(--f-text-hover-color) cursor-pointer\"\n (click)=\"clear($event)\"\n >\n <ui-icon name=\"times\" class=\"text-xs\"></ui-icon>\n </span>\n }\n\n @if (isEditMode()) {\n <span\n class=\"inline-flex items-center px-1 text-(--f-form-field-placeholder-color)\"\n >\n <ui-icon name=\"chevron-down\" class=\"text-xs\"></ui-icon>\n </span>\n }\n</div>\n\n<ng-template #overlayTpl>\n <div\n class=\"flex flex-col max-h-[250px] overflow-hidden\"\n (click)=\"onOverlayClick($event)\"\n >\n <div\n class=\"p-3 border-b border-(--f-content-border-color) bg-(--f-content-hover-background) shrink-0 w-full flex flex-row gap-2 items-center\"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isSelectAll()\"\n [disabled]=\"disabled()\"\n (onChange)=\"changeSelectAll($event)\"\n />\n <input\n type=\"text\"\n fInputText\n class=\"w-full\"\n [placeholder]=\"'shared.search' | translate\"\n [ngModel]=\"searchTerm()\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </div>\n <div\n class=\"flex-1 overflow-y-auto min-h-0 w-full\"\n (scroll)=\"onScroll($event)\"\n >\n <ul\n class=\"m-0 py-1 list-none bg-(--f-overlay-popover-background) text-(--f-text-color) w-full\"\n >\n @for (data of mergedDataList(); track data.value) {\n @let isItemSelected = isSelected(data);\n <li\n class=\"px-3 py-2 cursor-pointer transition-colors flex flex-row gap-2 items-center text-sm\"\n [class]=\"\n isItemSelected\n ? 'bg-primary/10 text-primary'\n : 'text-(--f-text-color) hover:bg-(--f-content-hover-background)'\n \"\n >\n <f-checkbox\n [binary]=\"true\"\n [ngModel]=\"isItemSelected\"\n [disabled]=\"disabled()\"\n (onChange)=\"selectValue($event, data)\"\n />\n <span class=\"flex flex-col min-w-0 flex-1\">\n <span class=\"truncate\">{{ data.label }}</span>\n @if (data.subLabel) {\n <span class=\"truncate text-xs text-(--f-text-muted-color)\">{{\n data.subLabel\n }}</span>\n }\n </span>\n </li>\n }\n </ul>\n </div>\n </div>\n</ng-template>\n" }]
|
|
3763
|
+
}], ctorParameters: () => [], propDecorators: { pSelectRef: [{ type: i0.ViewChild, args: ['pSelect', { isSignal: true }] }], overlayTemplate: [{ type: i0.ViewChild, args: ['overlayTpl', { isSignal: true }] }], placeHolder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeHolder", required: false }] }], showClear: [{ type: i0.Input, args: [{ isSignal: true, alias: "showClear", required: false }] }], isEditMode: [{ type: i0.Input, args: [{ isSignal: true, alias: "isEditMode", required: true }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: true }] }], total: [{ type: i0.Input, args: [{ isSignal: true, alias: "total", required: true }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: true }] }], selectDataList: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectDataList", required: true }] }], selectedObjects: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectedObjects", required: false }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }], onPagination: [{ type: i0.Output, args: ["onPagination"] }] } });
|
|
3715
3764
|
|
|
3716
3765
|
/**
|
|
3717
3766
|
* Lazy-loading single select component with search and pagination.
|
|
@@ -3759,6 +3808,14 @@ class LazySelectComponent extends BaseFormControl {
|
|
|
3759
3808
|
...(ngDevMode ? [{ debugName: "pagination" }] : /* istanbul ignore next */ []));
|
|
3760
3809
|
selectDataList = input.required(/* @ts-ignore */
|
|
3761
3810
|
...(ngDevMode ? [{ debugName: "selectDataList" }] : /* istanbul ignore next */ []));
|
|
3811
|
+
/**
|
|
3812
|
+
* Full option object for the current value, supplied by the caller (or a
|
|
3813
|
+
* subclass like UserSelectComponent). Forwarded to f-select's own
|
|
3814
|
+
* `selectedObject` input so the label survives a later search/page reload
|
|
3815
|
+
* that replaces `selectDataList()` without the value having changed.
|
|
3816
|
+
*/
|
|
3817
|
+
selectedObject = input(null, /* @ts-ignore */
|
|
3818
|
+
...(ngDevMode ? [{ debugName: "selectedObject" }] : /* istanbul ignore next */ []));
|
|
3762
3819
|
// Two-way bound value
|
|
3763
3820
|
value = model(null, /* @ts-ignore */
|
|
3764
3821
|
...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
|
|
@@ -3841,7 +3898,7 @@ class LazySelectComponent extends BaseFormControl {
|
|
|
3841
3898
|
return key;
|
|
3842
3899
|
}
|
|
3843
3900
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: LazySelectComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
3844
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.
|
|
3901
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.5", type: LazySelectComponent, isStandalone: true, selector: "lib-lazy-select", inputs: { placeHolder: { classPropertyName: "placeHolder", publicName: "placeHolder", isSignal: true, isRequired: false, transformFunction: null }, showClear: { classPropertyName: "showClear", publicName: "showClear", isSignal: true, isRequired: false, transformFunction: null }, optionLabel: { classPropertyName: "optionLabel", publicName: "optionLabel", isSignal: true, isRequired: true, transformFunction: null }, optionValue: { classPropertyName: "optionValue", publicName: "optionValue", isSignal: true, isRequired: true, transformFunction: null }, isEditMode: { classPropertyName: "isEditMode", publicName: "isEditMode", isSignal: true, isRequired: true, transformFunction: null }, isLoading: { classPropertyName: "isLoading", publicName: "isLoading", isSignal: true, isRequired: true, transformFunction: null }, total: { classPropertyName: "total", publicName: "total", isSignal: true, isRequired: true, transformFunction: null }, pagination: { classPropertyName: "pagination", publicName: "pagination", isSignal: true, isRequired: true, transformFunction: null }, selectDataList: { classPropertyName: "selectDataList", publicName: "selectDataList", isSignal: true, isRequired: true, transformFunction: null }, selectedObject: { classPropertyName: "selectedObject", publicName: "selectedObject", isSignal: true, isRequired: false, transformFunction: null }, value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange", onSearch: "onSearch", onPagination: "onPagination" }, providers: [provideValueAccessor(LazySelectComponent)], viewQueries: [{ propertyName: "scrollContainer", first: true, predicate: ["scrollContainer"], descendants: true, isSignal: true }], usesInheritance: true, ngImport: i0, template: "<div #scrollContainer class=\"lib-scroll-container\">\n <f-select\n class=\"w-full\"\n [options]=\"selectDataList()\"\n [optionLabel]=\"optionLabel()\"\n [optionValue]=\"optionValue()\"\n [filter]=\"true\"\n [showClear]=\"showClear()\"\n [placeholder]=\"displayPlaceholder()\"\n [disabled]=\"disabled()\"\n [(ngModel)]=\"value\"\n [selectedObject]=\"selectedObject()\"\n appEditModeElementChanger\n [isEditMode]=\"isEditMode()\"\n (click)=\"showPanel()\"\n (onBlur)=\"markAsTouched()\"\n >\n <ng-template #filter let-filter>\n <input\n fInputText\n class=\"w-full\"\n [ngModel]=\"searchTerm()\"\n [ngModelOptions]=\"{ standalone: true }\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </ng-template>\n <ng-template #selectedItem let-selectedOption>\n {{ selectedOption[optionLabel()] }}\n </ng-template>\n <ng-template #item let-item>\n <div class=\"flex flex-col min-w-0\">\n <span class=\"truncate\">{{ item[optionLabel()] }}</span>\n @if (item.subLabel) {\n <span class=\"truncate text-xs text-(--f-text-muted-color)\">{{\n item.subLabel\n }}</span>\n }\n </div>\n </ng-template>\n </f-select>\n</div>\n", styles: [""], dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: SelectComponent, selector: "f-select", inputs: ["options", "optionLabel", "optionValue", "placeholder", "disabled", "filter", "filterBy", "filterMatchMode", "filterLocale", "filterPlaceholder", "resetFilterOnHide", "autofocusFilter", "emptyMessage", "emptyFilterMessage", "showClear", "loading", "loadingIcon", "dropdownIcon", "clearIcon", "inputId", "invalid", "touched", "styleClass", "style", "appendTo", "editable", "readonly", "autofocus", "checkmark", "group", "optionGroupLabel", "optionGroupChildren", "virtualScroll", "virtualScrollItemSize", "lazy", "selectedObject"], outputs: ["onFilter", "onChange", "onShow", "onHide", "onBlur", "onFocus", "onClear", "onLazyLoad"] }, { kind: "directive", type: InputTextDirective, selector: "[fInputText]", inputs: ["invalid", "touched", "variant", "size", "fluid"] }, { kind: "directive", type: EditModeElementChangerDirective, selector: "[appEditModeElementChanger]", inputs: ["isEditMode"] }] });
|
|
3845
3902
|
}
|
|
3846
3903
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: LazySelectComponent, decorators: [{
|
|
3847
3904
|
type: Component,
|
|
@@ -3850,8 +3907,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
3850
3907
|
SelectComponent,
|
|
3851
3908
|
InputTextDirective,
|
|
3852
3909
|
EditModeElementChangerDirective,
|
|
3853
|
-
], providers: [provideValueAccessor(LazySelectComponent)], template: "<div #scrollContainer class=\"lib-scroll-container\">\n <f-select\n class=\"w-full\"\n [options]=\"selectDataList()\"\n [optionLabel]=\"optionLabel()\"\n [optionValue]=\"optionValue()\"\n [filter]=\"true\"\n [showClear]=\"showClear()\"\n [placeholder]=\"displayPlaceholder()\"\n [disabled]=\"disabled()\"\n [(ngModel)]=\"value\"\n appEditModeElementChanger\n [isEditMode]=\"isEditMode()\"\n (click)=\"showPanel()\"\n (onBlur)=\"markAsTouched()\"\n >\n <ng-template #filter let-filter>\n <input\n fInputText\n class=\"w-full\"\n [ngModel]=\"searchTerm()\"\n [ngModelOptions]=\"{ standalone: true }\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </ng-template>\n <ng-template #selectedItem let-selectedOption>\n {{ selectedOption[optionLabel()] }}\n </ng-template>\n <ng-template #item let-item>\n {{ item[optionLabel()] }}\n </ng-template>\n </f-select>\n</div>\n" }]
|
|
3854
|
-
}], ctorParameters: () => [], propDecorators: { scrollContainer: [{ type: i0.ViewChild, args: ['scrollContainer', { isSignal: true }] }], placeHolder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeHolder", required: false }] }], showClear: [{ type: i0.Input, args: [{ isSignal: true, alias: "showClear", required: false }] }], optionLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "optionLabel", required: true }] }], optionValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "optionValue", required: true }] }], isEditMode: [{ type: i0.Input, args: [{ isSignal: true, alias: "isEditMode", required: true }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: true }] }], total: [{ type: i0.Input, args: [{ isSignal: true, alias: "total", required: true }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: true }] }], selectDataList: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectDataList", required: true }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }], onPagination: [{ type: i0.Output, args: ["onPagination"] }] } });
|
|
3910
|
+
], providers: [provideValueAccessor(LazySelectComponent)], template: "<div #scrollContainer class=\"lib-scroll-container\">\n <f-select\n class=\"w-full\"\n [options]=\"selectDataList()\"\n [optionLabel]=\"optionLabel()\"\n [optionValue]=\"optionValue()\"\n [filter]=\"true\"\n [showClear]=\"showClear()\"\n [placeholder]=\"displayPlaceholder()\"\n [disabled]=\"disabled()\"\n [(ngModel)]=\"value\"\n [selectedObject]=\"selectedObject()\"\n appEditModeElementChanger\n [isEditMode]=\"isEditMode()\"\n (click)=\"showPanel()\"\n (onBlur)=\"markAsTouched()\"\n >\n <ng-template #filter let-filter>\n <input\n fInputText\n class=\"w-full\"\n [ngModel]=\"searchTerm()\"\n [ngModelOptions]=\"{ standalone: true }\"\n (ngModelChange)=\"searchTerm.set($event)\"\n />\n </ng-template>\n <ng-template #selectedItem let-selectedOption>\n {{ selectedOption[optionLabel()] }}\n </ng-template>\n <ng-template #item let-item>\n <div class=\"flex flex-col min-w-0\">\n <span class=\"truncate\">{{ item[optionLabel()] }}</span>\n @if (item.subLabel) {\n <span class=\"truncate text-xs text-(--f-text-muted-color)\">{{\n item.subLabel\n }}</span>\n }\n </div>\n </ng-template>\n </f-select>\n</div>\n" }]
|
|
3911
|
+
}], ctorParameters: () => [], propDecorators: { scrollContainer: [{ type: i0.ViewChild, args: ['scrollContainer', { isSignal: true }] }], placeHolder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeHolder", required: false }] }], showClear: [{ type: i0.Input, args: [{ isSignal: true, alias: "showClear", required: false }] }], optionLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "optionLabel", required: true }] }], optionValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "optionValue", required: true }] }], isEditMode: [{ type: i0.Input, args: [{ isSignal: true, alias: "isEditMode", required: true }] }], isLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "isLoading", required: true }] }], total: [{ type: i0.Input, args: [{ isSignal: true, alias: "total", required: true }] }], pagination: [{ type: i0.Input, args: [{ isSignal: true, alias: "pagination", required: true }] }], selectDataList: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectDataList", required: true }] }], selectedObject: [{ type: i0.Input, args: [{ isSignal: true, alias: "selectedObject", required: false }] }], value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }], onPagination: [{ type: i0.Output, args: ["onPagination"] }] } });
|
|
3855
3912
|
|
|
3856
3913
|
class RouterTabsComponent {
|
|
3857
3914
|
tabs = input([], /* @ts-ignore */
|
|
@@ -3940,11 +3997,64 @@ class BaseUserSelectComponent {
|
|
|
3940
3997
|
searchTerm = signal('', /* @ts-ignore */
|
|
3941
3998
|
...(ngDevMode ? [{ debugName: "searchTerm" }] : /* istanbul ignore next */ []));
|
|
3942
3999
|
// Computed dropdown data
|
|
3943
|
-
dropdownUsers = computed(() => this.users().map((user) => (
|
|
3944
|
-
label: user.name || user.email,
|
|
3945
|
-
value: user.id,
|
|
3946
|
-
})), /* @ts-ignore */
|
|
4000
|
+
dropdownUsers = computed(() => this.users().map((user) => this.toDropDown(user)), /* @ts-ignore */
|
|
3947
4001
|
...(ngDevMode ? [{ debugName: "dropdownUsers" }] : /* istanbul ignore next */ []));
|
|
4002
|
+
// Every user this component has ever seen, keyed by id. Search/pagination
|
|
4003
|
+
// replace `users()` wholesale, so without this a user selected before a
|
|
4004
|
+
// later search would silently disappear from `dropdownUsers()` even though
|
|
4005
|
+
// the selection itself hasn't changed.
|
|
4006
|
+
_knownUsers = signal(new Map(), /* @ts-ignore */
|
|
4007
|
+
...(ngDevMode ? [{ debugName: "_knownUsers" }] : /* istanbul ignore next */ []));
|
|
4008
|
+
toDropDown(user) {
|
|
4009
|
+
// Names collide across users; showing the email as a subLabel keeps entries distinguishable.
|
|
4010
|
+
return {
|
|
4011
|
+
label: user.name || user.email,
|
|
4012
|
+
value: user.id,
|
|
4013
|
+
subLabel: user.name ? user.email : undefined,
|
|
4014
|
+
};
|
|
4015
|
+
}
|
|
4016
|
+
/** Resolves a single previously-seen user id, even if it's no longer in `users()`. */
|
|
4017
|
+
resolveKnownUser(id) {
|
|
4018
|
+
const user = this.resolveKnownUserRaw(id);
|
|
4019
|
+
return user ? this.toDropDown(user) : null;
|
|
4020
|
+
}
|
|
4021
|
+
/** Resolves multiple previously-seen user ids, even if no longer in `users()`. */
|
|
4022
|
+
resolveKnownUsers(ids) {
|
|
4023
|
+
return this.resolveKnownUsersRaw(ids).map((u) => this.toDropDown(u));
|
|
4024
|
+
}
|
|
4025
|
+
/** Same as resolveKnownUser, but returns the raw IUserBasicInfo (for outputs like userSelected). */
|
|
4026
|
+
resolveKnownUserRaw(id) {
|
|
4027
|
+
if (!id)
|
|
4028
|
+
return null;
|
|
4029
|
+
return this._knownUsers().get(id) ?? null;
|
|
4030
|
+
}
|
|
4031
|
+
/** Same as resolveKnownUsers, but returns the raw IUserBasicInfo[] (for outputs like usersSelected). */
|
|
4032
|
+
resolveKnownUsersRaw(ids) {
|
|
4033
|
+
const known = this._knownUsers();
|
|
4034
|
+
return ids
|
|
4035
|
+
.map((id) => known.get(id))
|
|
4036
|
+
.filter((u) => !!u);
|
|
4037
|
+
}
|
|
4038
|
+
// Called synchronously wherever `users()` gains new entries (fetchUsers),
|
|
4039
|
+
// rather than via an effect watching `users()`: fetchUsers is invoked from
|
|
4040
|
+
// afterNextRender's callback, whose async continuation runs outside the
|
|
4041
|
+
// normal change-detection flush cycle, so an effect there is not
|
|
4042
|
+
// guaranteed to re-run promptly when the fetch resolves.
|
|
4043
|
+
rememberUsers(list) {
|
|
4044
|
+
if (!list.length)
|
|
4045
|
+
return;
|
|
4046
|
+
this._knownUsers.update((map) => {
|
|
4047
|
+
let changed = false;
|
|
4048
|
+
const next = new Map(map);
|
|
4049
|
+
for (const u of list) {
|
|
4050
|
+
if (next.get(u.id) !== u) {
|
|
4051
|
+
next.set(u.id, u);
|
|
4052
|
+
changed = true;
|
|
4053
|
+
}
|
|
4054
|
+
}
|
|
4055
|
+
return changed ? next : map;
|
|
4056
|
+
});
|
|
4057
|
+
}
|
|
3948
4058
|
// Computed placeholder with translation fallback
|
|
3949
4059
|
displayPlaceholder = computed(() => {
|
|
3950
4060
|
const customPlaceholder = this.placeHolder();
|
|
@@ -4016,6 +4126,7 @@ class BaseUserSelectComponent {
|
|
|
4016
4126
|
this.users.set(response.data);
|
|
4017
4127
|
}
|
|
4018
4128
|
this.total.set(response.meta?.total);
|
|
4129
|
+
this.rememberUsers(response.data);
|
|
4019
4130
|
}
|
|
4020
4131
|
}
|
|
4021
4132
|
catch (error) {
|
|
@@ -4099,13 +4210,16 @@ class UserMultiSelectComponent extends BaseUserSelectComponent {
|
|
|
4099
4210
|
...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
|
|
4100
4211
|
// Outputs
|
|
4101
4212
|
usersSelected = output();
|
|
4213
|
+
selectedObjects = computed(() => this.resolveKnownUsers(this.value() ?? []), /* @ts-ignore */
|
|
4214
|
+
...(ngDevMode ? [{ debugName: "selectedObjects" }] : /* istanbul ignore next */ []));
|
|
4102
4215
|
setupValueEffect() {
|
|
4103
|
-
// Emit selected users when value changes
|
|
4216
|
+
// Emit selected users when value changes. Resolves via the sticky known-
|
|
4217
|
+
// users cache (not the transient users() page) so this stays correct
|
|
4218
|
+
// across searches, matching selectedObjects()'s behavior above.
|
|
4104
4219
|
effect(() => {
|
|
4105
4220
|
const selectedIds = this.value() ?? [];
|
|
4106
|
-
const
|
|
4221
|
+
const selectedUsers = this.resolveKnownUsersRaw(selectedIds);
|
|
4107
4222
|
untracked(() => {
|
|
4108
|
-
const selectedUsers = users.filter((u) => selectedIds.includes(u.id));
|
|
4109
4223
|
this.usersSelected.emit(selectedUsers);
|
|
4110
4224
|
});
|
|
4111
4225
|
});
|
|
@@ -4121,10 +4235,11 @@ class UserMultiSelectComponent extends BaseUserSelectComponent {
|
|
|
4121
4235
|
[total]="total()"
|
|
4122
4236
|
[pagination]="pagination()"
|
|
4123
4237
|
[selectDataList]="dropdownUsers()"
|
|
4238
|
+
[selectedObjects]="selectedObjects()"
|
|
4124
4239
|
(onSearch)="handleSearch($event)"
|
|
4125
4240
|
(onPagination)="handlePagination($event)"
|
|
4126
4241
|
/>
|
|
4127
|
-
`, isInline: true, dependencies: [{ kind: "component", type: LazyMultiSelectComponent, selector: "lib-lazy-multi-select", inputs: ["placeHolder", "showClear", "isEditMode", "isLoading", "total", "pagination", "selectDataList", "value"], outputs: ["valueChange", "onSearch", "onPagination"] }] });
|
|
4242
|
+
`, isInline: true, dependencies: [{ kind: "component", type: LazyMultiSelectComponent, selector: "lib-lazy-multi-select", inputs: ["placeHolder", "showClear", "isEditMode", "isLoading", "total", "pagination", "selectDataList", "selectedObjects", "value"], outputs: ["valueChange", "onSearch", "onPagination"] }] });
|
|
4128
4243
|
}
|
|
4129
4244
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: UserMultiSelectComponent, decorators: [{
|
|
4130
4245
|
type: Component,
|
|
@@ -4141,6 +4256,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
4141
4256
|
[total]="total()"
|
|
4142
4257
|
[pagination]="pagination()"
|
|
4143
4258
|
[selectDataList]="dropdownUsers()"
|
|
4259
|
+
[selectedObjects]="selectedObjects()"
|
|
4144
4260
|
(onSearch)="handleSearch($event)"
|
|
4145
4261
|
(onPagination)="handlePagination($event)"
|
|
4146
4262
|
/>
|
|
@@ -4184,19 +4300,17 @@ class UserSelectComponent extends BaseUserSelectComponent {
|
|
|
4184
4300
|
...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
|
|
4185
4301
|
// Outputs
|
|
4186
4302
|
userSelected = output();
|
|
4303
|
+
selectedObject = computed(() => this.resolveKnownUser(this.value()), /* @ts-ignore */
|
|
4304
|
+
...(ngDevMode ? [{ debugName: "selectedObject" }] : /* istanbul ignore next */ []));
|
|
4187
4305
|
setupValueEffect() {
|
|
4188
|
-
// Emit selected user when value changes
|
|
4306
|
+
// Emit selected user when value changes. Resolves via the sticky known-
|
|
4307
|
+
// users cache (not the transient users() page) so this stays correct
|
|
4308
|
+
// across searches, matching selectedObject()'s behavior above.
|
|
4189
4309
|
effect(() => {
|
|
4190
4310
|
const selectedId = this.value();
|
|
4191
|
-
const
|
|
4311
|
+
const user = this.resolveKnownUserRaw(selectedId);
|
|
4192
4312
|
untracked(() => {
|
|
4193
|
-
|
|
4194
|
-
const user = users.find((u) => u.id === selectedId);
|
|
4195
|
-
this.userSelected.emit(user ?? null);
|
|
4196
|
-
}
|
|
4197
|
-
else {
|
|
4198
|
-
this.userSelected.emit(null);
|
|
4199
|
-
}
|
|
4313
|
+
this.userSelected.emit(user);
|
|
4200
4314
|
});
|
|
4201
4315
|
});
|
|
4202
4316
|
}
|
|
@@ -4213,10 +4327,11 @@ class UserSelectComponent extends BaseUserSelectComponent {
|
|
|
4213
4327
|
[total]="total()"
|
|
4214
4328
|
[pagination]="pagination()"
|
|
4215
4329
|
[selectDataList]="dropdownUsers()"
|
|
4330
|
+
[selectedObject]="selectedObject()"
|
|
4216
4331
|
(onSearch)="handleSearch($event)"
|
|
4217
4332
|
(onPagination)="handlePagination($event)"
|
|
4218
4333
|
/>
|
|
4219
|
-
`, isInline: true, dependencies: [{ kind: "component", type: LazySelectComponent, selector: "lib-lazy-select", inputs: ["placeHolder", "showClear", "optionLabel", "optionValue", "isEditMode", "isLoading", "total", "pagination", "selectDataList", "value"], outputs: ["valueChange", "onSearch", "onPagination"] }] });
|
|
4334
|
+
`, isInline: true, dependencies: [{ kind: "component", type: LazySelectComponent, selector: "lib-lazy-select", inputs: ["placeHolder", "showClear", "optionLabel", "optionValue", "isEditMode", "isLoading", "total", "pagination", "selectDataList", "selectedObject", "value"], outputs: ["valueChange", "onSearch", "onPagination"] }] });
|
|
4220
4335
|
}
|
|
4221
4336
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImport: i0, type: UserSelectComponent, decorators: [{
|
|
4222
4337
|
type: Component,
|
|
@@ -4235,6 +4350,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.5", ngImpor
|
|
|
4235
4350
|
[total]="total()"
|
|
4236
4351
|
[pagination]="pagination()"
|
|
4237
4352
|
[selectDataList]="dropdownUsers()"
|
|
4353
|
+
[selectedObject]="selectedObject()"
|
|
4238
4354
|
(onSearch)="handleSearch($event)"
|
|
4239
4355
|
(onPagination)="handlePagination($event)"
|
|
4240
4356
|
/>
|