@ethlete/cdk 3.19.0 → 3.19.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/CHANGELOG.md +6 -0
  2. package/esm2022/lib/components/button/directives/button/button.directive.mjs +10 -25
  3. package/esm2022/lib/components/button/directives/query-button/query-button.directive.mjs +8 -17
  4. package/esm2022/lib/components/forms/components/checkbox/directives/checkbox/checkbox.directive.mjs +7 -11
  5. package/esm2022/lib/components/forms/components/checkbox/directives/checkbox-field/checkbox-field.directive.mjs +17 -14
  6. package/esm2022/lib/components/forms/components/checkbox/directives/checkbox-group-control/checkbox-group-control.directive.mjs +6 -13
  7. package/esm2022/lib/components/forms/components/error/components/error/error.component.mjs +7 -9
  8. package/esm2022/lib/components/forms/components/radio/directives/radio/radio.directive.mjs +6 -8
  9. package/esm2022/lib/components/forms/components/radio/directives/radio-field/radio-field.directive.mjs +14 -18
  10. package/esm2022/lib/components/forms/components/radio/directives/radio-group/radio-group.directive.mjs +5 -11
  11. package/esm2022/lib/components/forms/components/segmented-button/directives/segmented-button/segmented-button.directive.mjs +6 -8
  12. package/esm2022/lib/components/forms/components/segmented-button/directives/segmented-button-field/segmented-button-field.directive.mjs +14 -18
  13. package/esm2022/lib/components/forms/components/segmented-button/directives/segmented-button-group/segmented-button-group.directive.mjs +6 -11
  14. package/esm2022/lib/components/forms/components/select/components/combobox/directives/combobox/combobox.directive.mjs +14 -25
  15. package/esm2022/lib/components/forms/components/select/components/combobox/partials/combobox-body/combobox-body.component.mjs +13 -23
  16. package/esm2022/lib/components/forms/components/select/components/combobox/partials/combobox-option/combobox-option.component.mjs +11 -23
  17. package/esm2022/lib/components/forms/components/select/components/select/directives/select/select.directive.mjs +26 -22
  18. package/esm2022/lib/components/forms/components/select/components/select/directives/select-body/select-body.directive.mjs +7 -15
  19. package/esm2022/lib/components/forms/components/select/components/select/directives/select-option/select-option.directive.mjs +13 -14
  20. package/esm2022/lib/components/forms/components/select/directives/select-field/select-field.directive.mjs +3 -4
  21. package/esm2022/lib/components/forms/components/slide-toggle/directives/slide-toggle/slide-toggle.directive.mjs +6 -8
  22. package/esm2022/lib/components/forms/components/slider/components/slider/slider.component.mjs +18 -41
  23. package/esm2022/lib/components/forms/directives/input/input.directive.mjs +4 -1
  24. package/esm2022/lib/components/forms/directives/writeable-input/writeable-input.directive.mjs +10 -23
  25. package/esm2022/lib/components/forms/services/input-state.service.mjs +21 -4
  26. package/esm2022/lib/components/forms/utils/decorated-form-field.base.mjs +5 -8
  27. package/esm2022/lib/components/forms/utils/decorated-input.base.mjs +26 -23
  28. package/esm2022/lib/components/masonry/components/masonry/masonry.component.mjs +6 -8
  29. package/fesm2022/ethlete-cdk.mjs +207 -342
  30. package/fesm2022/ethlete-cdk.mjs.map +1 -1
  31. package/lib/components/button/directives/button/button.directive.d.ts +4 -1
  32. package/lib/components/button/directives/query-button/query-button.directive.d.ts +4 -1
  33. package/lib/components/forms/components/checkbox/directives/checkbox/checkbox.directive.d.ts +4 -1
  34. package/lib/components/forms/components/checkbox/directives/checkbox-field/checkbox-field.directive.d.ts +11 -6
  35. package/lib/components/forms/components/checkbox/directives/checkbox-group-control/checkbox-group-control.directive.d.ts +6 -4
  36. package/lib/components/forms/components/error/components/error/error.component.d.ts +4 -1
  37. package/lib/components/forms/components/radio/directives/radio/radio.directive.d.ts +4 -1
  38. package/lib/components/forms/components/radio/directives/radio-field/radio-field.directive.d.ts +12 -6
  39. package/lib/components/forms/components/radio/directives/radio-group/radio-group.directive.d.ts +4 -1
  40. package/lib/components/forms/components/segmented-button/directives/segmented-button/segmented-button.directive.d.ts +4 -1
  41. package/lib/components/forms/components/segmented-button/directives/segmented-button-field/segmented-button-field.directive.d.ts +12 -7
  42. package/lib/components/forms/components/segmented-button/directives/segmented-button-group/segmented-button-group.directive.d.ts +4 -1
  43. package/lib/components/forms/components/select/components/combobox/directives/combobox/combobox.directive.d.ts +9 -1
  44. package/lib/components/forms/components/select/components/combobox/partials/combobox-body/combobox-body.component.d.ts +8 -1
  45. package/lib/components/forms/components/select/components/combobox/partials/combobox-option/combobox-option.component.d.ts +8 -1
  46. package/lib/components/forms/components/select/components/select/directives/select/select.directive.d.ts +14 -3
  47. package/lib/components/forms/components/select/components/select/directives/select-body/select-body.directive.d.ts +4 -1
  48. package/lib/components/forms/components/select/components/select/directives/select-option/select-option.directive.d.ts +10 -1
  49. package/lib/components/forms/components/select/directives/select-field/select-field.directive.d.ts +2 -2
  50. package/lib/components/forms/components/slide-toggle/directives/slide-toggle/slide-toggle.directive.d.ts +4 -1
  51. package/lib/components/forms/components/slider/components/slider/slider.component.d.ts +8 -1
  52. package/lib/components/forms/directives/input/input.directive.d.ts +21 -19
  53. package/lib/components/forms/directives/writeable-input/writeable-input.directive.d.ts +4 -1
  54. package/lib/components/forms/services/input-state.service.d.ts +13 -6
  55. package/lib/components/forms/utils/decorated-form-field.base.d.ts +4 -1
  56. package/lib/components/forms/utils/decorated-input.base.d.ts +13 -6
  57. package/lib/components/masonry/components/masonry/masonry.component.d.ts +4 -1
  58. package/package.json +2 -2
@@ -4,10 +4,11 @@ import { AsyncPipe, NgIf, NgClass, NgTemplateOutlet, NgForOf, NgFor, NgComponent
4
4
  import * as i0 from '@angular/core';
5
5
  import { Component, ViewEncapsulation, ChangeDetectionStrategy, Directive, InjectionToken, booleanAttribute, Input, ContentChild, ContentChildren, inject, ElementRef, Injector, HostBinding, computed, signal, Optional, Inject, Injectable, SkipSelf, HostListener, ViewContainerRef, EventEmitter, NgZone, isDevMode, Output, NgModule, ChangeDetectorRef, ViewChild, runInInjectionContext, TemplateRef, forwardRef, LOCALE_ID, numberAttribute, ViewChildren, Renderer2, Attribute } from '@angular/core';
6
6
  import * as i1$2 from '@ethlete/core';
7
- import { LetDirective, createDestroy, ScrollObserverFirstElementDirective, ScrollObserverLastElementDirective, Memo, createReactiveBindings, signalHostClasses, AnimatedIfDirective, AnimatedLifecycleDirective, SmartBlockScrollStrategy, RouterStateService, ANIMATED_LIFECYCLE_TOKEN, nextFrame, elementCanScroll, equal, ViewportService, AnimatedOverlayDirective, ClickObserverService, FocusVisibleService, cloneFormGroup, getFormGroupValue, ObserveVisibilityDirective, signalVisibilityChangeClasses, IS_EMAIL, MUST_MATCH, IS_ARRAY_NOT_EMPTY, AT_LEAST_ONE_REQUIRED, ResizeObserverService, createFlipAnimation, RuntimeError, SelectionModel, ActiveSelectionModel, KeyPressManager, scrollToElement, isEmptyArray, isObjectArray, isPrimitiveArray, ClickOutsideDirective, ObserveContentDirective, clamp, DELAYABLE_TOKEN, ObserveResizeDirective, getElementVisibleStates, IS_ACTIVE_ELEMENT, IS_ELEMENT, CursorDragScrollDirective, ObserveScrollStateDirective, IsElementDirective, IsActiveElementDirective, ScrollObserverIgnoreTargetDirective, TypedQueryList } from '@ethlete/core';
8
- import { BehaviorSubject, startWith, map, switchMap, combineLatest, pairwise, tap, takeUntil, skip, of, Subject, filter, take, merge, skipUntil, defer, fromEvent, partition, debounceTime as debounceTime$1, distinctUntilChanged as distinctUntilChanged$1, withLatestFrom, skipWhile, catchError, throwError, firstValueFrom, timer, Subscription, Observable } from 'rxjs';
7
+ import { LetDirective, createDestroy, ScrollObserverFirstElementDirective, ScrollObserverLastElementDirective, Memo, signalHostAttributes, signalHostClasses, AnimatedIfDirective, AnimatedLifecycleDirective, SmartBlockScrollStrategy, RouterStateService, ANIMATED_LIFECYCLE_TOKEN, nextFrame, elementCanScroll, equal, ViewportService, AnimatedOverlayDirective, ClickObserverService, FocusVisibleService, cloneFormGroup, getFormGroupValue, ObserveVisibilityDirective, signalVisibilityChangeClasses, IS_EMAIL, MUST_MATCH, IS_ARRAY_NOT_EMPTY, AT_LEAST_ONE_REQUIRED, switchQueryListChanges, signalAttributes, ResizeObserverService, createFlipAnimation, RuntimeError, SelectionModel, ActiveSelectionModel, KeyPressManager, signalClasses, scrollToElement, isEmptyArray, isObjectArray, isPrimitiveArray, ClickOutsideDirective, ObserveContentDirective, clamp, DELAYABLE_TOKEN, ObserveResizeDirective, getElementVisibleStates, IS_ACTIVE_ELEMENT, IS_ELEMENT, CursorDragScrollDirective, ObserveScrollStateDirective, IsElementDirective, IsActiveElementDirective, ScrollObserverIgnoreTargetDirective, TypedQueryList } from '@ethlete/core';
8
+ import { BehaviorSubject, startWith, map, switchMap, combineLatest, pairwise, tap, takeUntil, skip, of, Subject, filter, take, merge, skipUntil, defer, fromEvent, partition, debounceTime as debounceTime$1, Observable, distinctUntilChanged as distinctUntilChanged$1, withLatestFrom, skipWhile, catchError, throwError, firstValueFrom, timer, Subscription } from 'rxjs';
9
9
  import { trigger, state, style, transition, animate } from '@angular/animations';
10
10
  import { __decorate, __metadata } from 'tslib';
11
+ import { toSignal, takeUntilDestroyed } from '@angular/core/rxjs-interop';
11
12
  import { extractQuery, isQueryStateLoading, isQueryStateSuccess, isQueryStateFailure, QueryDirective, shouldRetryRequest, isClassValidatorError, isSymfonyFormViolationListError } from '@ethlete/query';
12
13
  import { CdkDialogContainer, Dialog, DialogConfig, DIALOG_SCROLL_STRATEGY_PROVIDER as DIALOG_SCROLL_STRATEGY_PROVIDER$1 } from '@angular/cdk/dialog';
13
14
  import * as i1$1 from '@angular/cdk/a11y';
@@ -22,7 +23,6 @@ import * as i2$1 from '@angular/cdk/platform';
22
23
  import { _getEventTarget } from '@angular/cdk/platform';
23
24
  import { startWith as startWith$1, debounceTime, distinctUntilChanged, takeUntil as takeUntil$1, skip as skip$1, filter as filter$1, mergeMap, mapTo, mergeAll, switchMap as switchMap$1, take as take$1 } from 'rxjs/operators';
24
25
  import { UniqueSelectionDispatcher, _VIEW_REPEATER_STRATEGY, _RecycleViewRepeaterStrategy, _DisposeViewRepeaterStrategy, DataSource } from '@angular/cdk/collections';
25
- import { toSignal } from '@angular/core/rxjs-interop';
26
26
  import { AutofillMonitor } from '@angular/cdk/text-field';
27
27
  import { FormControl, NgControl, Validators, NG_VALUE_ACCESSOR } from '@angular/forms';
28
28
  import { Title } from '@angular/platform-browser';
@@ -1027,27 +1027,11 @@ class ButtonDirective {
1027
1027
  this._disabled$ = new BehaviorSubject(false);
1028
1028
  this._type$ = new BehaviorSubject('button');
1029
1029
  this._pressed$ = new BehaviorSubject(false);
1030
- this._bindings = createReactiveBindings({
1031
- attribute: ['disabled', 'aria-disabled'],
1032
- observable: this.disabled$.pipe(map((disabled) => ({
1033
- render: disabled,
1034
- value: true,
1035
- }))),
1036
- }, {
1037
- attribute: ['tabindex'],
1038
- observable: this.disabled$.pipe(map((disabled) => ({
1039
- render: disabled && this.isAnchor,
1040
- value: -1,
1041
- }))),
1042
- }, {
1043
- attribute: ['type'],
1044
- observable: this.type$.pipe(map((type) => ({
1045
- render: this.isButton,
1046
- value: type,
1047
- }))),
1048
- }, {
1049
- attribute: ['aria-pressed'],
1050
- observable: this._pressed$,
1030
+ this.hostAttributeBindings = signalHostAttributes({
1031
+ 'disabled aria-disabled': toSignal(this.disabled$),
1032
+ 'aria-pressed': toSignal(this._pressed$),
1033
+ ...(this.isAnchor ? { tabindex: toSignal(this.disabled$.pipe(map((disabled) => (disabled ? -1 : 0)))) } : {}),
1034
+ ...(this.isButton ? { type: toSignal(this.type$) } : {}),
1051
1035
  });
1052
1036
  }
1053
1037
  get disabled() {
@@ -1075,10 +1059,10 @@ class ButtonDirective {
1075
1059
  this._pressed$.next(booleanAttribute(value));
1076
1060
  }
1077
1061
  _removeDisabledBindings() {
1078
- this._bindings.remove('disabled', 'aria-disabled');
1062
+ this.hostAttributeBindings.remove('disabled', 'aria-disabled');
1079
1063
  }
1080
1064
  _removeTabIndexBindings() {
1081
- this._bindings.remove('tabindex');
1065
+ this.hostAttributeBindings.remove('tabindex');
1082
1066
  }
1083
1067
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: ButtonDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
1084
1068
  static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: ButtonDirective, isStandalone: true, inputs: { disabled: "disabled", type: "type", pressed: "pressed" }, exportAs: ["etButton"], ngImport: i0 }); }
@@ -1133,7 +1117,6 @@ class QueryButtonDirective {
1133
1117
  classList.remove(CLASSES.success);
1134
1118
  classList.remove(CLASSES.failure);
1135
1119
  classList.remove(CLASSES.loading);
1136
- this._bindings.reset();
1137
1120
  const query = extractQuery(this._query$.value);
1138
1121
  if (!query) {
1139
1122
  return;
@@ -1184,15 +1167,9 @@ class QueryButtonDirective {
1184
1167
  this._skipFailure = false;
1185
1168
  this._skipLoading = false;
1186
1169
  this._query$ = new BehaviorSubject(null);
1187
- this._bindings = createReactiveBindings({
1188
- attribute: ['disabled', 'aria-disabled'],
1189
- observable: combineLatest([this._button.disabled$, this.showFailure$, this.showSuccess$, this.isLoading$]).pipe(map(([disabled, showFailure, showSuccess, isLoading]) => ({
1190
- render: disabled || showFailure || showSuccess || isLoading,
1191
- value: true,
1192
- }))),
1193
- }, {
1194
- attribute: ['aria-live'],
1195
- observable: combineLatest([
1170
+ this.hostAttributeBindings = signalHostAttributes({
1171
+ 'disabled aria-disabled': toSignal(combineLatest([this._button.disabled$, this.showFailure$, this.showSuccess$, this.isLoading$]).pipe(map(([disabled, showFailure, showSuccess, isLoading]) => disabled || showFailure || showSuccess || isLoading))),
1172
+ 'aria-live': toSignal(combineLatest([
1196
1173
  this.query$.pipe(map((q) => extractQuery(q)), switchMap((q) => q?.state$ ?? of(null))),
1197
1174
  this.didLoadOnce$,
1198
1175
  ]).pipe(map(([state, didLoadOnce]) => {
@@ -1200,11 +1177,8 @@ class QueryButtonDirective {
1200
1177
  if (isQueryStateLoading(state) || isQueryStateSuccess(state) || isQueryStateFailure(state) || didLoadOnce) {
1201
1178
  value = 'assertive';
1202
1179
  }
1203
- return {
1204
- render: true,
1205
- value,
1206
- };
1207
- })),
1180
+ return value;
1181
+ }))),
1208
1182
  });
1209
1183
  this._button._removeDisabledBindings();
1210
1184
  }
@@ -5854,8 +5828,25 @@ class InputStateService {
5854
5828
  this.valueIsTruthy = toSignal(this.valueIsTruthy$, { requireSync: true });
5855
5829
  this.valueIsFalsy$ = this.value$.pipe(map((value) => !value));
5856
5830
  this.valueIsFalsy = toSignal(this.valueIsFalsy$, { requireSync: true });
5857
- this.valueIsEmpty$ = combineLatest([this.value$, this.autofilled$]).pipe(map(([value, autofilled]) => (value === null || value === undefined || value === '' || (Array.isArray(value) && !value.length)) &&
5858
- !autofilled));
5831
+ /**
5832
+ * Selects might have a option that is "null".
5833
+ * This helper can be used to enhance the detection of empty values.
5834
+ * The input is empty if the helper returns a falsy value and the value itself is falsy or an empty array.
5835
+ */
5836
+ this.isEmptyHelper$ = new BehaviorSubject(undefined);
5837
+ this.isEmptyHelper = toSignal(this.isEmptyHelper$, { requireSync: true });
5838
+ this.valueIsEmpty$ = combineLatest([
5839
+ this.value$,
5840
+ this.autofilled$,
5841
+ this.isEmptyHelper$.pipe(switchMap((isEmptyHelper) => (isEmptyHelper instanceof Observable ? isEmptyHelper : of(isEmptyHelper)))),
5842
+ ]).pipe(map(([value, autofilled, isEmptyHelper]) => {
5843
+ const defaultIsEmpty = (value === null || value === undefined || value === '' || (Array.isArray(value) && !value.length)) &&
5844
+ !autofilled;
5845
+ if (isEmptyHelper !== undefined) {
5846
+ return !isEmptyHelper && defaultIsEmpty;
5847
+ }
5848
+ return defaultIsEmpty;
5849
+ }));
5859
5850
  this.valueIsEmpty = toSignal(this.valueIsEmpty$, { requireSync: true });
5860
5851
  this.errors$ = new BehaviorSubject(null);
5861
5852
  this.errors = toSignal(this.errors$, { requireSync: true });
@@ -6335,6 +6326,9 @@ class InputDirective {
6335
6326
  }
6336
6327
  this._inputStateService.shouldDisplayError$.next(value);
6337
6328
  }
6329
+ _setEmptyHelper(value) {
6330
+ this._inputStateService.isEmptyHelper$.next(value);
6331
+ }
6338
6332
  _detectControlRequiredValidationChanges() {
6339
6333
  const hasRequired = this.control.hasValidator(Validators.required) ?? false;
6340
6334
  const hasRequiredTrue = this.control.hasValidator(Validators.requiredTrue) ?? false;
@@ -6618,27 +6612,14 @@ const WRITEABLE_INPUT_VALUE_ACCESSOR = {
6618
6612
  class WriteableInputDirective {
6619
6613
  constructor() {
6620
6614
  this._inputStateService = inject(InputStateService);
6621
- this._bindings = createReactiveBindings({
6622
- attribute: 'class.et-required',
6623
- observable: this._inputStateService.required$,
6624
- }, {
6625
- attribute: 'class.et-disabled',
6626
- observable: this._inputStateService.disabled$,
6627
- }, {
6628
- attribute: 'class.et-value-is-truthy',
6629
- observable: this._inputStateService.valueIsTruthy$,
6630
- }, {
6631
- attribute: 'class.et-value-is-falsy',
6632
- observable: this._inputStateService.valueIsFalsy$,
6633
- }, {
6634
- attribute: 'class.et-empty',
6635
- observable: this._inputStateService.valueIsEmpty$,
6636
- }, {
6637
- attribute: 'class.et-should-display-error',
6638
- observable: this._inputStateService.shouldDisplayError$,
6639
- }, {
6640
- attribute: 'class.et-autofilled',
6641
- observable: this._inputStateService.autofilled$,
6615
+ this.hostClassBindings = signalHostClasses({
6616
+ 'et-required': this._inputStateService.required,
6617
+ 'et-disabled': this._inputStateService.disabled,
6618
+ 'et-value-is-truthy': this._inputStateService.valueIsTruthy,
6619
+ 'et-value-is-falsy': this._inputStateService.valueIsFalsy,
6620
+ 'et-empty': this._inputStateService.valueIsEmpty,
6621
+ 'et-should-display-error': this._inputStateService.shouldDisplayError,
6622
+ 'et-autofilled': this._inputStateService.autofilled,
6642
6623
  });
6643
6624
  }
6644
6625
  writeValue(value) {
@@ -6682,12 +6663,9 @@ class ErrorComponent {
6682
6663
  this.errorText$ = new BehaviorSubject(null);
6683
6664
  this.id = `et-error-${_uniqueIdCounter++}`;
6684
6665
  this._errors = null;
6685
- this._bindings = createReactiveBindings({
6686
- attribute: 'class.et-error--has-errors',
6687
- observable: this.errorText$.pipe(map((v) => !!v)),
6688
- }, {
6689
- attribute: 'class.cdk-visually-hidden',
6690
- observable: this._dynamicFormGroupOrField.hideErrorMessage$,
6666
+ this.hostClassBindings = signalHostClasses({
6667
+ 'et-error--has-errors': toSignal(this.errorText$),
6668
+ 'cdk-visually-hidden': toSignal(this._dynamicFormGroupOrField.hideErrorMessage$),
6691
6669
  });
6692
6670
  }
6693
6671
  get errors() {
@@ -6726,19 +6704,21 @@ const CHECKBOX_FIELD_TOKEN = new InjectionToken('ET_CHECKBOX_FIELD_DIRECTIVE_TOK
6726
6704
  class CheckboxFieldDirective {
6727
6705
  constructor() {
6728
6706
  this.inputState = inject(InputStateService);
6729
- this._bindings = createReactiveBindings();
6730
- }
6731
- ngAfterContentInit() {
6732
- if (!this._checkbox) {
6733
- return;
6734
- }
6735
- this._bindings.push({
6736
- attribute: 'class.et-checkbox-field--indeterminate',
6737
- observable: this._checkbox.changes.pipe(startWith(this._checkbox)).pipe(switchMap((checkboxes) => combineLatest(checkboxes.filter((cb) => !!cb).map((checkbox) => checkbox.indeterminate$))), map((checked) => checked.some((value) => value))),
6707
+ this._checkbox$ = new BehaviorSubject(null);
6708
+ this.hostClassBindings = signalHostClasses({
6709
+ 'et-checkbox-field--indeterminate': toSignal(this._checkbox$.pipe(switchQueryListChanges(), switchMap((checkboxes) => {
6710
+ if (!checkboxes?.length) {
6711
+ return of(null);
6712
+ }
6713
+ return combineLatest(checkboxes.map((checkbox) => checkbox.indeterminate$)).pipe(map((indeterminateStates) => indeterminateStates.some((isIndeterminate) => isIndeterminate)));
6714
+ }))),
6738
6715
  });
6739
6716
  }
6717
+ set checkbox(checkbox) {
6718
+ this._checkbox$.next(checkbox);
6719
+ }
6740
6720
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: CheckboxFieldDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
6741
- static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: CheckboxFieldDirective, isStandalone: true, providers: [{ provide: CHECKBOX_FIELD_TOKEN, useExisting: CheckboxFieldDirective }], queries: [{ propertyName: "_checkbox", predicate: i0.forwardRef(function () { return CHECKBOX_TOKEN; }), descendants: true }], exportAs: ["etCheckboxGroup"], ngImport: i0 }); }
6721
+ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: CheckboxFieldDirective, isStandalone: true, providers: [{ provide: CHECKBOX_FIELD_TOKEN, useExisting: CheckboxFieldDirective }], queries: [{ propertyName: "checkbox", predicate: i0.forwardRef(function () { return CHECKBOX_TOKEN; }), descendants: true }], exportAs: ["etCheckboxGroup"], ngImport: i0 }); }
6742
6722
  }
6743
6723
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: CheckboxFieldDirective, decorators: [{
6744
6724
  type: Directive,
@@ -6747,7 +6727,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
6747
6727
  providers: [{ provide: CHECKBOX_FIELD_TOKEN, useExisting: CheckboxFieldDirective }],
6748
6728
  exportAs: 'etCheckboxGroup',
6749
6729
  }]
6750
- }], propDecorators: { _checkbox: [{
6730
+ }], propDecorators: { checkbox: [{
6751
6731
  type: ContentChildren,
6752
6732
  args: [forwardRef(() => CHECKBOX_TOKEN), { descendants: true }]
6753
6733
  }] } });
@@ -6758,15 +6738,10 @@ class CheckboxDirective {
6758
6738
  this.input = inject(INPUT_TOKEN);
6759
6739
  this.checked$ = this.input.value$.pipe(map((value) => !!value));
6760
6740
  this.indeterminate$ = new BehaviorSubject(false);
6761
- this._bindings = createReactiveBindings({
6762
- attribute: ['class.et-checkbox--checked'],
6763
- observable: this.checked$,
6764
- }, {
6765
- attribute: ['class.et-checkbox--disabled'],
6766
- observable: this.input.disabled$,
6767
- }, {
6768
- attribute: ['class.et-checkbox--indeterminate'],
6769
- observable: combineLatest([this.checked$, this.indeterminate$]).pipe(map(([checked, indeterminate]) => !checked && indeterminate)),
6741
+ this.hostClassBindings = signalHostClasses({
6742
+ 'et-checkbox--checked': toSignal(this.checked$),
6743
+ 'et-checkbox--disabled': toSignal(this.input.disabled$),
6744
+ 'et-checkbox--indeterminate': toSignal(combineLatest([this.checked$, this.indeterminate$]).pipe(map(([checked, indeterminate]) => !checked && indeterminate))),
6770
6745
  });
6771
6746
  }
6772
6747
  _onInputInteraction(event) {
@@ -6874,16 +6849,8 @@ class CheckboxGroupControlDirective {
6874
6849
  this.checkbox = inject(CHECKBOX_TOKEN);
6875
6850
  this.input = inject(INPUT_TOKEN);
6876
6851
  this.group = inject(CHECKBOX_GROUP_TOKEN);
6877
- this._bindings = createReactiveBindings();
6878
- }
6879
- ngAfterContentInit() {
6880
- this._bindings.push({
6881
- attribute: ['aria-controls'],
6882
- elementRef: this.input.nativeInputRef?.element,
6883
- observable: this.group.checkboxesWithoutGroupCtrl$.pipe(map((checkboxes) => ({
6884
- render: true,
6885
- value: checkboxes.map((checkbox) => checkbox.input.id).join(' '),
6886
- }))) ?? of(false),
6852
+ this.inputAttributeBindings = signalAttributes(this.input.nativeInputRef$.pipe(map((el) => el?.element)), {
6853
+ 'aria-controls': toSignal(this.group.checkboxesWithoutGroupCtrl$.pipe(map((checkboxes) => checkboxes.map((checkbox) => checkbox.input.id).join(' ')))),
6887
6854
  });
6888
6855
  }
6889
6856
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: CheckboxGroupControlDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
@@ -6947,12 +6914,9 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
6947
6914
  class DecoratedFormFieldBase {
6948
6915
  constructor() {
6949
6916
  this._formFieldStateService = inject(FormFieldStateService);
6950
- this._bindings = createReactiveBindings({
6951
- attribute: 'class.et-form-field--has-prefix',
6952
- observable: this._formFieldStateService.hasPrefix$,
6953
- }, {
6954
- attribute: 'class.et-form-field--has-suffix',
6955
- observable: this._formFieldStateService.hasSuffix$,
6917
+ this.hostClassBindings = signalHostClasses({
6918
+ 'et-form-field--has-prefix': this._formFieldStateService.hasPrefix,
6919
+ 'et-form-field--has-suffix': this._formFieldStateService.hasSuffix,
6956
6920
  });
6957
6921
  }
6958
6922
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: DecoratedFormFieldBase, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
@@ -6980,35 +6944,37 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
6980
6944
  }] } });
6981
6945
 
6982
6946
  class DecoratedInputBase extends InputBase {
6947
+ set inputPrefix(inputPrefix) {
6948
+ this.inputPrefix$.next(inputPrefix);
6949
+ }
6950
+ set inputSuffix(inputSuffix) {
6951
+ this.inputSuffix$.next(inputSuffix);
6952
+ }
6983
6953
  constructor() {
6984
- super(...arguments);
6954
+ super();
6985
6955
  this._formFieldStateService = inject(FormFieldStateService);
6986
6956
  this._destroy$ = createDestroy();
6987
- this._bindings = createReactiveBindings({
6988
- attribute: 'class.et-input--has-prefix',
6989
- observable: this._formFieldStateService.hasPrefix$,
6990
- }, {
6991
- attribute: 'class.et-input--has-suffix',
6992
- observable: this._formFieldStateService.hasSuffix$,
6957
+ this.inputPrefix$ = new BehaviorSubject(null);
6958
+ this.inputSuffix$ = new BehaviorSubject(null);
6959
+ this.hasPrefix$ = this.inputPrefix$.pipe(switchQueryListChanges(), map((list) => !!list && list?.length > 0));
6960
+ this.hasSuffix$ = this.inputSuffix$.pipe(switchQueryListChanges(), map((list) => !!list && list?.length > 0));
6961
+ this.hostClassBindings = signalHostClasses({
6962
+ 'et-input--has-prefix': toSignal(this.hasPrefix$),
6963
+ 'et-input--has-suffix': toSignal(this.hasSuffix$),
6993
6964
  });
6965
+ this.hasPrefix$
6966
+ .pipe(takeUntilDestroyed(), tap((hasPrefix) => this._formFieldStateService.hasPrefix$.next(hasPrefix)))
6967
+ .subscribe();
6968
+ this.hasSuffix$
6969
+ .pipe(takeUntilDestroyed(), tap((hasSuffix) => this._formFieldStateService.hasSuffix$.next(hasSuffix)))
6970
+ .subscribe();
6994
6971
  }
6995
- ngAfterContentInit() {
6996
- if (!this.inputPrefix || !this.inputSuffix) {
6997
- return;
6998
- }
6999
- this.inputPrefix.changes
7000
- .pipe(takeUntil(this._destroy$), startWith(this.inputPrefix), map((list) => list.length > 0))
7001
- .subscribe(this._formFieldStateService.hasPrefix$);
7002
- this.inputSuffix.changes
7003
- .pipe(takeUntil(this._destroy$), startWith(this.inputSuffix), map((list) => list.length > 0))
7004
- .subscribe(this._formFieldStateService.hasSuffix$);
7005
- }
7006
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: DecoratedInputBase, deps: null, target: i0.ɵɵFactoryTarget.Directive }); }
6972
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: DecoratedInputBase, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
7007
6973
  static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: DecoratedInputBase, queries: [{ propertyName: "inputPrefix", predicate: INPUT_PREFIX_TOKEN }, { propertyName: "inputSuffix", predicate: INPUT_SUFFIX_TOKEN }], usesInheritance: true, ngImport: i0 }); }
7008
6974
  }
7009
6975
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: DecoratedInputBase, decorators: [{
7010
6976
  type: Directive
7011
- }], propDecorators: { inputPrefix: [{
6977
+ }], ctorParameters: function () { return []; }, propDecorators: { inputPrefix: [{
7012
6978
  type: ContentChildren,
7013
6979
  args: [INPUT_PREFIX_TOKEN]
7014
6980
  }], inputSuffix: [{
@@ -7639,12 +7605,9 @@ class RadioDirective {
7639
7605
  this._disabled$ = new BehaviorSubject(false);
7640
7606
  this.checked$ = combineLatest([this.input.value$, this._value$]).pipe(map(([inputValue, value]) => inputValue === value));
7641
7607
  this.disabled$ = combineLatest([this.input.disabled$, this._disabled$]).pipe(map(([inputDisabled, disabled]) => inputDisabled || disabled));
7642
- this._bindings = createReactiveBindings({
7643
- attribute: ['class.et-radio--checked'],
7644
- observable: this.checked$,
7645
- }, {
7646
- attribute: ['class.et-radio--disabled'],
7647
- observable: this.disabled$,
7608
+ this.hostClassBindings = signalHostClasses({
7609
+ 'et-radio--checked': toSignal(this.disabled$),
7610
+ 'et-radio--disabled': toSignal(this.disabled$),
7648
7611
  });
7649
7612
  }
7650
7613
  get value() {
@@ -7692,23 +7655,18 @@ const RADIO_FIELD_TOKEN = new InjectionToken('ET_RADIO_FIELD_DIRECTIVE_TOKEN');
7692
7655
  class RadioFieldDirective {
7693
7656
  constructor() {
7694
7657
  this.inputState = inject(InputStateService);
7695
- this._bindings = createReactiveBindings();
7696
- }
7697
- ngAfterContentInit() {
7698
- if (!this._radio) {
7699
- return;
7700
- }
7701
- this._bindings.push({
7702
- attribute: 'class.et-radio-field--checked',
7703
- observable: this._radio.changes.pipe(startWith(this._radio)).pipe(switchMap((radios) => combineLatest(radios.filter((radio) => !!radio).map((radio) => radio.checked$))), map((checked) => checked.some((value) => value))),
7704
- });
7705
- this._bindings.push({
7706
- attribute: 'class.et-radio-field--disabled',
7707
- observable: this._radio.changes.pipe(startWith(this._radio)).pipe(switchMap((radios) => combineLatest(radios.filter((radio) => !!radio).map((radio) => radio.disabled$))), map((disabled) => disabled.some((value) => value))),
7658
+ this._radio$ = new BehaviorSubject(null);
7659
+ this.radioQueryList$ = this._radio$.pipe(switchQueryListChanges());
7660
+ this.hostClassBindings = signalHostClasses({
7661
+ 'et-radio-field--checked': toSignal(this.radioQueryList$.pipe(switchMap((radios) => (radios?.length ? combineLatest(radios.map((radio) => radio.disabled$)) : of([]))), map((checked) => checked.some((value) => value)))),
7662
+ 'et-radio-field--disabled': toSignal(this.radioQueryList$.pipe(switchMap((radios) => (radios?.length ? combineLatest(radios.map((radio) => radio.disabled$)) : of([]))), map((disabled) => disabled.some((value) => value)))),
7708
7663
  });
7709
7664
  }
7665
+ set radio(radio) {
7666
+ this._radio$.next(radio);
7667
+ }
7710
7668
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: RadioFieldDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
7711
- static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: RadioFieldDirective, isStandalone: true, providers: [{ provide: RADIO_FIELD_TOKEN, useExisting: RadioFieldDirective }], queries: [{ propertyName: "_radio", predicate: i0.forwardRef(function () { return RADIO_TOKEN; }), descendants: true }], exportAs: ["etRadioField"], ngImport: i0 }); }
7669
+ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: RadioFieldDirective, isStandalone: true, providers: [{ provide: RADIO_FIELD_TOKEN, useExisting: RadioFieldDirective }], queries: [{ propertyName: "radio", predicate: i0.forwardRef(function () { return RADIO_TOKEN; }), descendants: true }], exportAs: ["etRadioField"], ngImport: i0 }); }
7712
7670
  }
7713
7671
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: RadioFieldDirective, decorators: [{
7714
7672
  type: Directive,
@@ -7717,7 +7675,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
7717
7675
  providers: [{ provide: RADIO_FIELD_TOKEN, useExisting: RadioFieldDirective }],
7718
7676
  exportAs: 'etRadioField',
7719
7677
  }]
7720
- }], propDecorators: { _radio: [{
7678
+ }], propDecorators: { radio: [{
7721
7679
  type: ContentChildren,
7722
7680
  args: [forwardRef(() => RADIO_TOKEN), { descendants: true }]
7723
7681
  }] } });
@@ -7728,14 +7686,8 @@ class RadioGroupDirective {
7728
7686
  constructor() {
7729
7687
  this._formGroupStateService = inject(FormGroupStateService);
7730
7688
  this.name = `et-radio-group-${++nextUniqueId$3}`;
7731
- this._bindings = createReactiveBindings({
7732
- attribute: 'aria-labelledby',
7733
- observable: this._formGroupStateService.describedBy$.pipe(map((describedBy) => {
7734
- return {
7735
- render: !!describedBy,
7736
- value: `${describedBy}`,
7737
- };
7738
- })),
7689
+ this.hostAttributeBindings = signalHostAttributes({
7690
+ 'aria-labelledby': toSignal(this._formGroupStateService.describedBy$),
7739
7691
  });
7740
7692
  }
7741
7693
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: RadioGroupDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
@@ -7836,12 +7788,9 @@ class SegmentedButtonDirective {
7836
7788
  this._disabled$ = new BehaviorSubject(false);
7837
7789
  this.checked$ = combineLatest([this.input.value$, this._value$]).pipe(map(([inputValue, value]) => inputValue === value));
7838
7790
  this.disabled$ = combineLatest([this.input.disabled$, this._disabled$]).pipe(map(([inputDisabled, disabled]) => inputDisabled || disabled));
7839
- this._bindings = createReactiveBindings({
7840
- attribute: ['class.et-segmented-button--checked'],
7841
- observable: this.checked$,
7842
- }, {
7843
- attribute: ['class.et-segmented-button--disabled'],
7844
- observable: this.disabled$,
7791
+ this.hostClassBindings = signalHostClasses({
7792
+ 'et-segmented-button--checked': toSignal(this.checked$),
7793
+ 'et-segmented-button--disabled': toSignal(this.disabled$),
7845
7794
  });
7846
7795
  }
7847
7796
  get value() {
@@ -7898,23 +7847,18 @@ const SEGMENTED_BUTTON_FIELD_TOKEN = new InjectionToken('ET_SEGMENTED_BUTTON_FIE
7898
7847
  class SegmentedButtonFieldDirective {
7899
7848
  constructor() {
7900
7849
  this.inputState = inject(InputStateService);
7901
- this._bindings = createReactiveBindings();
7902
- }
7903
- ngAfterContentInit() {
7904
- if (!this._segmentedButton) {
7905
- return;
7906
- }
7907
- this._bindings.push({
7908
- attribute: 'class.et-segmented-button-field--checked',
7909
- observable: this._segmentedButton.changes.pipe(startWith(this._segmentedButton)).pipe(switchMap((buttons) => combineLatest(buttons.filter((radio) => !!radio).map((button) => button.checked$))), map((checked) => checked.some((value) => value))),
7910
- });
7911
- this._bindings.push({
7912
- attribute: 'class.et-segmented-button-field--disabled',
7913
- observable: this._segmentedButton.changes.pipe(startWith(this._segmentedButton)).pipe(switchMap((buttons) => combineLatest(buttons.filter((radio) => !!radio).map((button) => button.disabled$))), map((disabled) => disabled.some((value) => value))),
7850
+ this._segmentedButton$ = new BehaviorSubject(null);
7851
+ this.segmentedButtonQueryList$ = this._segmentedButton$.pipe(switchQueryListChanges());
7852
+ this.hostClassBindings = signalHostClasses({
7853
+ 'et-segmented-button-field--checked': toSignal(this.segmentedButtonQueryList$.pipe(switchMap((buttons) => (buttons?.length ? combineLatest(buttons.map((radio) => radio.disabled$)) : of([]))), map((checked) => checked.some((value) => value)))),
7854
+ 'et-segmented-button-field--disabled': toSignal(this.segmentedButtonQueryList$.pipe(switchMap((buttons) => (buttons?.length ? combineLatest(buttons.map((radio) => radio.disabled$)) : of([]))), map((disabled) => disabled.some((value) => value)))),
7914
7855
  });
7915
7856
  }
7857
+ set segmentedButton(segmentedButton) {
7858
+ this._segmentedButton$.next(segmentedButton);
7859
+ }
7916
7860
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: SegmentedButtonFieldDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
7917
- static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: SegmentedButtonFieldDirective, isStandalone: true, providers: [{ provide: SEGMENTED_BUTTON_FIELD_TOKEN, useExisting: SegmentedButtonFieldDirective }], queries: [{ propertyName: "_segmentedButton", predicate: i0.forwardRef(function () { return SEGMENTED_BUTTON_TOKEN; }), descendants: true }], exportAs: ["etSegmentedButtonField"], ngImport: i0 }); }
7861
+ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: SegmentedButtonFieldDirective, isStandalone: true, providers: [{ provide: SEGMENTED_BUTTON_FIELD_TOKEN, useExisting: SegmentedButtonFieldDirective }], queries: [{ propertyName: "segmentedButton", predicate: i0.forwardRef(function () { return SEGMENTED_BUTTON_TOKEN; }), descendants: true }], exportAs: ["etSegmentedButtonField"], ngImport: i0 }); }
7918
7862
  }
7919
7863
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: SegmentedButtonFieldDirective, decorators: [{
7920
7864
  type: Directive,
@@ -7923,7 +7867,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
7923
7867
  providers: [{ provide: SEGMENTED_BUTTON_FIELD_TOKEN, useExisting: SegmentedButtonFieldDirective }],
7924
7868
  exportAs: 'etSegmentedButtonField',
7925
7869
  }]
7926
- }], propDecorators: { _segmentedButton: [{
7870
+ }], propDecorators: { segmentedButton: [{
7927
7871
  type: ContentChildren,
7928
7872
  args: [forwardRef(() => SEGMENTED_BUTTON_TOKEN), { descendants: true }]
7929
7873
  }] } });
@@ -7936,14 +7880,8 @@ class SegmentedButtonGroupDirective {
7936
7880
  this._inputStateService = inject(InputStateService);
7937
7881
  this._destroy$ = createDestroy();
7938
7882
  this.name = `et-segmented-button-group-${++nextUniqueId$2}`;
7939
- this._bindings = createReactiveBindings({
7940
- attribute: 'aria-labelledby',
7941
- observable: this._formGroupStateService.describedBy$.pipe(map((describedBy) => {
7942
- return {
7943
- render: !!describedBy,
7944
- value: `${describedBy}`,
7945
- };
7946
- })),
7883
+ this.hostAttributeBindings = signalHostAttributes({
7884
+ 'aria-labelledby': toSignal(this._formGroupStateService.describedBy$),
7947
7885
  });
7948
7886
  }
7949
7887
  ngAfterContentInit() {
@@ -8078,7 +8016,7 @@ const SegmentedButtonImports = [
8078
8016
  const SELECT_FIELD_TOKEN = new InjectionToken('ET_SELECT_FIELD_DIRECTIVE_TOKEN');
8079
8017
  class SelectFieldDirective {
8080
8018
  constructor() {
8081
- this._bindings = createReactiveBindings();
8019
+ this.elementRef = inject(ElementRef);
8082
8020
  }
8083
8021
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: SelectFieldDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
8084
8022
  static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.5", type: SelectFieldDirective, isStandalone: true, providers: [{ provide: SELECT_FIELD_TOKEN, useExisting: SelectFieldDirective }], exportAs: ["etSelectField"], ngImport: i0 }); }
@@ -8526,6 +8464,7 @@ class ComboboxDirective {
8526
8464
  this.activeOptionId$ = new BehaviorSubject(null);
8527
8465
  this._currentFilter$ = new BehaviorSubject('');
8528
8466
  this.isOpen$ = this._animatedOverlay.isMounted$;
8467
+ this.isOpen = toSignal(this.isOpen$);
8529
8468
  this._selectionModel = new SelectionModel();
8530
8469
  this._activeSelectionModel = new ActiveSelectionModel();
8531
8470
  this._backspaceKeyPressManager = new KeyPressManager(BACKSPACE);
@@ -8540,21 +8479,16 @@ class ComboboxDirective {
8540
8479
  this._bodyErrorTemplate$ = new BehaviorSubject(null);
8541
8480
  this._bodyEmptyTemplate$ = new BehaviorSubject(null);
8542
8481
  this._bodyMoreItemsHintTemplate$ = new BehaviorSubject(null);
8543
- this._bindings = createReactiveBindings({
8544
- attribute: 'class.et-combobox--loading',
8545
- observable: this._loading$,
8546
- }, {
8547
- attribute: 'class.et-combobox--error',
8548
- observable: this._error$.pipe(map((v) => !!v)),
8549
- }, {
8550
- attribute: 'class.et-combobox--open',
8551
- observable: this.isOpen$,
8552
- }, {
8553
- attribute: 'class.et-select-field--multiple',
8554
- observable: this.multiple$,
8555
- }, {
8556
- attribute: 'class.et-select-field--open',
8557
- observable: this.isOpen$,
8482
+ this.hostClassBindings = signalHostClasses({
8483
+ 'et-combobox--loading': toSignal(this._loading$),
8484
+ 'et-combobox--error': toSignal(this._error$.pipe(map((v) => !!v))),
8485
+ 'et-combobox--open': toSignal(this.isOpen$),
8486
+ 'et-select-field--multiple': toSignal(this.multiple$),
8487
+ 'et-select-field--open': this.isOpen,
8488
+ });
8489
+ this.fieldHostClassBindings = signalClasses(this._selectField.elementRef, {
8490
+ 'et-select-field--open': toSignal(this.isOpen$),
8491
+ 'et-select-field--multiple': toSignal(this.multiple$),
8558
8492
  });
8559
8493
  this._comboboxBodyComponent = null;
8560
8494
  //#endregion
@@ -8576,14 +8510,7 @@ class ComboboxDirective {
8576
8510
  this._animatedOverlay.placement = 'bottom';
8577
8511
  this._animatedOverlay.fallbackPlacements = ['bottom', 'top'];
8578
8512
  this._animatedOverlay.autoResize = true;
8579
- this._selectField._bindings.push({
8580
- attribute: 'class.et-select-field--open',
8581
- observable: this.isOpen$,
8582
- });
8583
- this._selectField._bindings.push({
8584
- attribute: 'class.et-select-field--multiple',
8585
- observable: this.multiple$,
8586
- });
8513
+ this._input._setEmptyHelper(this._currentFilter$);
8587
8514
  }
8588
8515
  ngOnInit() {
8589
8516
  this._initDispatchFilterChanges();
@@ -9026,27 +8953,14 @@ class ComboboxOptionComponent {
9026
8953
  this.disabled$ = this._option$.pipe(map((opt) => isOptionDisabled(opt)));
9027
8954
  this.selected$ = this._option$.pipe(switchMap((opt) => this.combobox.isOptionSelected(opt)));
9028
8955
  this.active$ = this._option$.pipe(switchMap((opt) => this.combobox.isOptionActive(opt)));
9029
- this._bindings = createReactiveBindings({
9030
- attribute: 'class.et-combobox-option--selected',
9031
- observable: this.selected$,
9032
- }, {
9033
- attribute: 'class.et-combobox-option--disabled',
9034
- observable: this.disabled$,
9035
- }, {
9036
- attribute: 'class.et-combobox-option--active',
9037
- observable: this.active$,
9038
- }, {
9039
- attribute: 'aria-selected',
9040
- observable: this.selected$.pipe(map((selected) => ({
9041
- render: true,
9042
- value: selected,
9043
- }))),
9044
- }, {
9045
- attribute: 'aria-diabled',
9046
- observable: this.disabled$.pipe(map((selected) => ({
9047
- render: true,
9048
- value: selected,
9049
- }))),
8956
+ this.hostClassBindings = signalHostClasses({
8957
+ 'et-combobox-option--selected': toSignal(this.selected$),
8958
+ 'et-combobox-option--disabled': toSignal(this.disabled$),
8959
+ 'et-combobox-option--active': toSignal(this.active$),
8960
+ });
8961
+ this.hostAttributeBindings = signalHostAttributes({
8962
+ 'aria-selected': toSignal(this.selected$),
8963
+ 'aria-disabled': toSignal(this.disabled$),
9050
8964
  });
9051
8965
  }
9052
8966
  get option() {
@@ -9101,24 +9015,13 @@ class ComboboxBodyComponent {
9101
9015
  this._clickOutside = inject(ClickOutsideDirective);
9102
9016
  this.combobox = inject(COMBOBOX_TOKEN);
9103
9017
  this._options$ = new BehaviorSubject(null);
9104
- this._bindings = createReactiveBindings({
9105
- attribute: 'class.et-combobox-body--loading',
9106
- observable: this.combobox.loading$,
9107
- }, {
9108
- attribute: 'class.et-combobox-body--multiple',
9109
- observable: this.combobox.multiple$,
9110
- }, {
9111
- attribute: 'aria-multiselectable',
9112
- observable: this.combobox.multiple$.pipe(map((multiple) => ({
9113
- render: true,
9114
- value: multiple,
9115
- }))),
9116
- }, {
9117
- attribute: 'aria-labelledby',
9118
- observable: this.combobox._input.labelId$.pipe(map((labelId) => ({
9119
- render: !!labelId,
9120
- value: labelId,
9121
- }))),
9018
+ this.hostClassBindings = signalHostClasses({
9019
+ 'et-combobox-body--loading': toSignal(this.combobox.loading$),
9020
+ 'et-combobox-body--multiple': toSignal(this.combobox.multiple$),
9021
+ });
9022
+ this.hostAttributeBindings = signalHostAttributes({
9023
+ 'aria-multiselectable': toSignal(this.combobox.multiple$),
9024
+ 'aria-labelledby': toSignal(this.combobox._input.labelId$),
9122
9025
  });
9123
9026
  this._bodyTemplate = null;
9124
9027
  this.trackByFn = (index, item) => this.combobox._selectionModel.getKey(item);
@@ -9137,7 +9040,7 @@ class ComboboxBodyComponent {
9137
9040
  provide: COMBOBOX_BODY_TOKEN,
9138
9041
  useExisting: ComboboxBodyComponent,
9139
9042
  },
9140
- ], viewQueries: [{ propertyName: "_containerElementRef", first: true, predicate: ["containerElement"], descendants: true, read: ElementRef, static: true }, { propertyName: "_animatedLifecycle", first: true, predicate: ANIMATED_LIFECYCLE_TOKEN, descendants: true, static: true }, { propertyName: "_options", predicate: ComboboxOptionComponent, descendants: true }], hostDirectives: [{ directive: i1$2.ClickOutsideDirective }], ngImport: i0, template: "<div #containerElement class=\"et-combobox-body-container\" etAnimatedLifecycle>\n <ng-container *etLet=\"combobox.options$ | async as options\">\n <ng-container *ngIf=\"!options?.length && !combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyEmptyTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyEmptyComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p class=\"et-combobox-body--empty\">{{ combobox._tempEmptyText }}</p>\n </ng-template>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyErrorTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl; context: { error: combobox.error }\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyErrorComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp; inputs: { error: combobox.error }\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyLoadingTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyLoadingComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <et-combobox-option *ngFor=\"let option of options; trackBy: trackByFn\" [option]=\"option\" />\n\n <ng-container *ngIf=\"options?.length && combobox.showBodyMoreItemsHint\">\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p *ngIf=\"combobox.bodyMoreItemsHintText\" class=\"et-combobox-body--more-items-hint\">\n {{ combobox.bodyMoreItemsHintText }}\n </p>\n </ng-template>\n </ng-template>\n </ng-container>\n </ng-container>\n</div>\n", dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletContent", "ngComponentOutletNgModule", "ngComponentOutletNgModuleFactory"] }, { kind: "directive", type: NgFor, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "component", type: ComboboxOptionComponent, selector: "et-combobox-option", inputs: ["option"] }, { kind: "directive", type: LetDirective, selector: "[etLet]", inputs: ["etLet"] }, { kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "directive", type: AnimatedLifecycleDirective, selector: "[etAnimatedLifecycle]", exportAs: ["etAnimatedLifecycle"] }, { kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
9043
+ ], viewQueries: [{ propertyName: "_containerElementRef", first: true, predicate: ["containerElement"], descendants: true, read: ElementRef, static: true }, { propertyName: "_animatedLifecycle", first: true, predicate: ANIMATED_LIFECYCLE_TOKEN, descendants: true, static: true }, { propertyName: "_options", predicate: ComboboxOptionComponent, descendants: true }], hostDirectives: [{ directive: i1$2.ClickOutsideDirective }], ngImport: i0, template: "<div #containerElement class=\"et-combobox-body-container\" etAnimatedLifecycle>\n <ng-container *etLet=\"combobox.options$ | async as options\">\n <ng-container *ngIf=\"!options?.length && !combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyEmptyTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyEmptyComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p class=\"et-combobox-body--empty\">{{ combobox._tempEmptyText }}</p>\n </ng-template>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyErrorTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl; context: { error: combobox.error }\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyErrorComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp; inputs: { error: combobox.error }\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.loading$ | async\">\n <ng-container *ngIf=\"combobox.customBodyLoadingTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyLoadingComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <et-combobox-option *ngFor=\"let option of options; trackBy: trackByFn\" [option]=\"option\" />\n\n <ng-container *ngIf=\"options?.length && combobox.showBodyMoreItemsHint\">\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p *ngIf=\"combobox.bodyMoreItemsHintText\" class=\"et-combobox-body--more-items-hint\">\n {{ combobox.bodyMoreItemsHintText }}\n </p>\n </ng-template>\n </ng-template>\n </ng-container>\n </ng-container>\n</div>\n", dependencies: [{ kind: "directive", type: NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletContent", "ngComponentOutletNgModule", "ngComponentOutletNgModuleFactory"] }, { kind: "directive", type: NgFor, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "component", type: ComboboxOptionComponent, selector: "et-combobox-option", inputs: ["option"] }, { kind: "directive", type: LetDirective, selector: "[etLet]", inputs: ["etLet"] }, { kind: "pipe", type: AsyncPipe, name: "async" }, { kind: "directive", type: AnimatedLifecycleDirective, selector: "[etAnimatedLifecycle]", exportAs: ["etAnimatedLifecycle"] }, { kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None }); }
9141
9044
  }
9142
9045
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImport: i0, type: ComboboxBodyComponent, decorators: [{
9143
9046
  type: Component,
@@ -9160,7 +9063,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.5", ngImpor
9160
9063
  provide: COMBOBOX_BODY_TOKEN,
9161
9064
  useExisting: ComboboxBodyComponent,
9162
9065
  },
9163
- ], template: "<div #containerElement class=\"et-combobox-body-container\" etAnimatedLifecycle>\n <ng-container *etLet=\"combobox.options$ | async as options\">\n <ng-container *ngIf=\"!options?.length && !combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyEmptyTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyEmptyComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p class=\"et-combobox-body--empty\">{{ combobox._tempEmptyText }}</p>\n </ng-template>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyErrorTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl; context: { error: combobox.error }\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyErrorComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp; inputs: { error: combobox.error }\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyLoadingTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyLoadingComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <et-combobox-option *ngFor=\"let option of options; trackBy: trackByFn\" [option]=\"option\" />\n\n <ng-container *ngIf=\"options?.length && combobox.showBodyMoreItemsHint\">\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p *ngIf=\"combobox.bodyMoreItemsHintText\" class=\"et-combobox-body--more-items-hint\">\n {{ combobox.bodyMoreItemsHintText }}\n </p>\n </ng-template>\n </ng-template>\n </ng-container>\n </ng-container>\n</div>\n" }]
9066
+ ], template: "<div #containerElement class=\"et-combobox-body-container\" etAnimatedLifecycle>\n <ng-container *etLet=\"combobox.options$ | async as options\">\n <ng-container *ngIf=\"!options?.length && !combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyEmptyTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyEmptyComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p class=\"et-combobox-body--empty\">{{ combobox._tempEmptyText }}</p>\n </ng-template>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.error && !combobox.loading\">\n <ng-container *ngIf=\"combobox.customBodyErrorTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl; context: { error: combobox.error }\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyErrorComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp; inputs: { error: combobox.error }\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <ng-container *ngIf=\"combobox.loading$ | async\">\n <ng-container *ngIf=\"combobox.customBodyLoadingTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyLoadingComponent$ | async as comp\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n </ng-template>\n </ng-container>\n\n <et-combobox-option *ngFor=\"let option of options; trackBy: trackByFn\" [option]=\"option\" />\n\n <ng-container *ngIf=\"options?.length && combobox.showBodyMoreItemsHint\">\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintTpl$ | async as tpl; else componentOrNone\">\n <ng-container *ngTemplateOutlet=\"tpl\" />\n </ng-container>\n <ng-template #componentOrNone>\n <ng-container *ngIf=\"combobox.customBodyMoreItemsHintComponent$ | async as comp; else default\">\n <ng-container *ngComponentOutlet=\"comp\" />\n </ng-container>\n <ng-template #default>\n <p *ngIf=\"combobox.bodyMoreItemsHintText\" class=\"et-combobox-body--more-items-hint\">\n {{ combobox.bodyMoreItemsHintText }}\n </p>\n </ng-template>\n </ng-template>\n </ng-container>\n </ng-container>\n</div>\n" }]
9164
9067
  }], propDecorators: { _containerElementRef: [{
9165
9068
  type: ViewChild,
9166
9069
  args: ['containerElement', { static: true, read: ElementRef }]
@@ -9406,21 +9309,16 @@ class SelectOptionDirective {
9406
9309
  }
9407
9310
  return selectValue === optionValue;
9408
9311
  }));
9312
+ this.isSelected = toSignal(this.isSelected$);
9409
9313
  this.viewValue$ = this._viewValue$.asObservable();
9410
9314
  this.disabled$ = this._disabled$.asObservable();
9411
9315
  this.isActive$ = this._isActive$.asObservable();
9412
- this._bindings = createReactiveBindings({
9413
- attribute: 'class.et-select-option--selected',
9414
- observable: this.isSelected$,
9415
- }, {
9416
- attribute: 'class.et-select-option--active',
9417
- observable: this._isActive$,
9418
- }, {
9419
- attribute: 'aria-selected',
9420
- observable: this.isSelected$.pipe(map((selected) => ({
9421
- render: true,
9422
- value: selected,
9423
- }))),
9316
+ this.hostClassBindings = signalHostClasses({
9317
+ 'et-select-option--selected': this.isSelected,
9318
+ 'et-select-option--active': toSignal(this._isActive$),
9319
+ });
9320
+ this.hostAttributeBindings = signalHostAttributes({
9321
+ 'aria-selected': this.isSelected,
9424
9322
  });
9425
9323
  }
9426
9324
  get value() {
@@ -9435,6 +9333,9 @@ class SelectOptionDirective {
9435
9333
  set disabled(value) {
9436
9334
  this._disabled$.next(booleanAttribute(value));
9437
9335
  }
9336
+ get viewValue() {
9337
+ return this._viewValue$.value;
9338
+ }
9438
9339
  ngAfterContentInit() {
9439
9340
  this._updateViewValue();
9440
9341
  }
@@ -9525,14 +9426,15 @@ class SelectDirective {
9525
9426
  this.input = inject(INPUT_TOKEN);
9526
9427
  this._selectBodyId$ = new BehaviorSubject(null);
9527
9428
  this._isOpen$ = new BehaviorSubject(false);
9429
+ this.elementRef = inject(ElementRef);
9430
+ this._selectionModel = new SelectionModel();
9431
+ this._activeSelectionModel = new ActiveSelectionModel();
9528
9432
  this._multiple$ = new BehaviorSubject(false);
9529
9433
  this._selectOptionsQueryList$ = new BehaviorSubject(null);
9530
- this.selectOptions$ = this._selectOptionsQueryList$.pipe(switchMap((queryList) => queryList?.changes.pipe(startWith(queryList)) ?? of(null)), switchMap((queryList) => {
9434
+ this.selectOptions$ = this._selectOptionsQueryList$.pipe(switchQueryListChanges(), switchMap((queryList) => {
9531
9435
  if (!queryList)
9532
9436
  return of(null);
9533
- const items = queryList
9534
- .filter((i) => !!i)
9535
- .map((opt) => combineLatest([opt.isSelected$, opt.isActive$]).pipe(map(([selected, active]) => ({ opt, selected, active }))));
9437
+ const items = queryList.map((opt) => combineLatest([opt.isSelected$, opt.isActive$]).pipe(map(([selected, active]) => ({ opt, selected, active }))));
9536
9438
  return combineLatest(items ?? of(null));
9537
9439
  }));
9538
9440
  this.activeOption$ = this.selectOptions$.pipe(map((options) => {
@@ -9559,6 +9461,7 @@ class SelectDirective {
9559
9461
  this.selectedOption$ = this.selectedOptions$.pipe(map((options) => options?.[0] ?? null));
9560
9462
  this.selectBodyId$ = this._selectBodyId$.asObservable();
9561
9463
  this.isOpen$ = this._isOpen$.asObservable();
9464
+ this.isOpen = toSignal(this.isOpen$);
9562
9465
  this.multiple$ = this._multiple$.asObservable();
9563
9466
  this.selectCurrentValueId = `et-select-current-value-${uniqueId$1++}`;
9564
9467
  this.ariaViewValue$ = this.selectedOptions$.pipe(switchMap((options) => {
@@ -9586,25 +9489,26 @@ class SelectDirective {
9586
9489
  const ids = [labelId, this.selectCurrentValueId];
9587
9490
  return ids.filter((id) => !!id).join(' ');
9588
9491
  }));
9589
- this._bindings = createReactiveBindings({
9590
- attribute: 'class.et-select--is-open',
9591
- observable: this.isOpen$,
9592
- }, {
9593
- attribute: 'class.et-select--disabled',
9594
- observable: this.input.disabled$,
9492
+ this.hostClassBindings = signalHostClasses({
9493
+ 'et-select--is-open': this.isOpen,
9494
+ 'et-select--disabled': toSignal(this.input.disabled$),
9495
+ });
9496
+ this.fieldHostClassBindings = signalClasses(this._selectField.elementRef, {
9497
+ 'et-select-field--open': this.isOpen,
9498
+ 'et-select-field--multiple': toSignal(this.multiple$),
9595
9499
  });
9596
9500
  this.trackByFn = (_, item) => item.id;
9597
9501
  this._animatedOverlay.placement = 'bottom';
9598
9502
  this._animatedOverlay.fallbackPlacements = ['bottom', 'top'];
9599
9503
  this._animatedOverlay.autoResize = true;
9600
- this._selectField._bindings.push({
9601
- attribute: 'class.et-select-field--open',
9602
- observable: this._isOpen$,
9603
- });
9604
- this._selectField._bindings.push({
9605
- attribute: 'class.et-select-field--multiple',
9606
- observable: this.multiple$,
9607
- });
9504
+ this.input._setEmptyHelper(this.ariaViewValue$);
9505
+ this._selectionModel
9506
+ .setOptionsFromQueryList$(this._selectOptionsQueryList$)
9507
+ .setLabelBinding((v) => v.viewValue)
9508
+ .setValueBinding((v) => v.value)
9509
+ .setDisabledBinding((v) => v.disabled);
9510
+ this._activeSelectionModel.setSelectionModel(this._selectionModel);
9511
+ //TODO: TO BE CONTINUED...
9608
9512
  }
9609
9513
  ngOnInit() {
9610
9514
  this._unmountSelectBodyOnDisable();
@@ -9960,18 +9864,9 @@ class SelectBodyDirective {
9960
9864
  this._select = inject(SELECT_TOKEN);
9961
9865
  this._clickOutside = inject(ClickOutsideDirective);
9962
9866
  this.id = `et-select-body-${uniqueId++}`;
9963
- this._bindings = createReactiveBindings({
9964
- attribute: 'aria-multiselectable',
9965
- observable: this._select.multiple$.pipe(map((multiple) => ({
9966
- render: true,
9967
- value: multiple,
9968
- }))),
9969
- }, {
9970
- attribute: 'aria-labelledby',
9971
- observable: this._select.input.labelId$.pipe(map((labelId) => ({
9972
- render: !!labelId,
9973
- value: labelId,
9974
- }))),
9867
+ this.hostAttributeBindings = signalHostAttributes({
9868
+ 'aria-multiselectable': toSignal(this._select.multiple$),
9869
+ 'aria-labelledby': toSignal(this._select.input.labelId$),
9975
9870
  });
9976
9871
  }
9977
9872
  ngOnInit() {
@@ -10414,12 +10309,9 @@ class SlideToggleDirective {
10414
10309
  constructor() {
10415
10310
  this.input = inject(INPUT_TOKEN);
10416
10311
  this.checked$ = this.input.value$.pipe(map((value) => !!value));
10417
- this._bindings = createReactiveBindings({
10418
- attribute: ['class.et-slide-toggle--checked'],
10419
- observable: this.checked$,
10420
- }, {
10421
- attribute: ['class.et-slide-toggle--disabled'],
10422
- observable: this.input.disabled$,
10312
+ this.hostClassBindings = signalHostClasses({
10313
+ 'et-slide-toggle--checked': toSignal(this.checked$),
10314
+ 'et-slide-toggle--disabled': toSignal(this.input.disabled$),
10423
10315
  });
10424
10316
  }
10425
10317
  _onInputInteraction(event) {
@@ -10604,45 +10496,21 @@ class SliderComponent {
10604
10496
  this.disableAnimations$ = new BehaviorSubject(false);
10605
10497
  this.touchId$ = new BehaviorSubject(null);
10606
10498
  this.lastPointerEvent$ = new BehaviorSubject(null);
10607
- this._bindings = createReactiveBindings({
10608
- attribute: 'aria-orientation',
10609
- observable: this._vertical$.pipe(map((vertical) => ({
10610
- render: true,
10611
- value: vertical ? 'vertical' : 'horizontal',
10612
- }))),
10613
- }, {
10614
- attribute: 'aria-disabled',
10615
- observable: this._input.disabled$,
10616
- }, {
10617
- attribute: 'aria-valuenow',
10618
- observable: this._value$.pipe(map((value) => ({ render: true, value }))),
10619
- }, {
10620
- attribute: 'aria-valuemin',
10621
- observable: this._min$.pipe(map((value) => ({ render: true, value }))),
10622
- }, {
10623
- attribute: 'aria-valuemax',
10624
- observable: this._max$.pipe(map((value) => ({ render: true, value }))),
10625
- }, {
10626
- attribute: 'aria-valuetext',
10627
- observable: this.valueText$.pipe(map((value) => ({ render: true, value }))),
10628
- }, {
10629
- attribute: 'tabindex',
10630
- observable: this._input.disabled$.pipe(map((disabled) => ({ render: true, value: disabled ? -1 : 0 }))),
10631
- }, {
10632
- attribute: 'class.et-slider--is-sliding',
10633
- observable: this.isSlidingVia$.pipe(map((isSlidingVia) => !!isSlidingVia)),
10634
- }, {
10635
- attribute: 'class.et-slider--inverted',
10636
- observable: this._inverted$,
10637
- }, {
10638
- attribute: 'class.et-slider--disable-animations',
10639
- observable: this.disableAnimations$,
10640
- }, {
10641
- attribute: 'aria-labeledby',
10642
- observable: this._formFieldStateService.labelId$.pipe(map((labelId) => ({ render: !!labelId, value: labelId ?? '' }))),
10643
- }, {
10644
- attribute: 'aria-describedby',
10645
- observable: this._formFieldStateService.describedBy$.pipe(map((describedBy) => ({ render: !!describedBy, value: describedBy ?? '' }))),
10499
+ this.hostClassBindings = signalHostClasses({
10500
+ 'et-slider--is-sliding': toSignal(this.isSlidingVia$),
10501
+ 'et-slider--inverted': toSignal(this._inverted$),
10502
+ 'et-slider--disable-animations': toSignal(this.disableAnimations$),
10503
+ });
10504
+ this.hostAttributeBindings = signalHostAttributes({
10505
+ 'aria-orientation': toSignal(this._vertical$.pipe(map((vertical) => (vertical ? 'vertical' : 'horizontal')))),
10506
+ 'aria-disabled': toSignal(this._input.disabled$),
10507
+ 'aria-valuenow': toSignal(this._value$),
10508
+ 'aria-valuemin': toSignal(this._min$),
10509
+ 'aria-valuemax': toSignal(this._max$),
10510
+ 'aria-valuetext': toSignal(this.valueText$),
10511
+ tabindex: toSignal(this._input.disabled$.pipe(map((disabled) => (disabled ? -1 : 0)))),
10512
+ 'aria-labeledby': this._formFieldStateService.labelId,
10513
+ 'aria-describedby': this._formFieldStateService.describedBy,
10646
10514
  });
10647
10515
  this._updateValueFromPosition = (pos, sliderDimensions, shouldInvertMouseCoords) => {
10648
10516
  const offset = this.vertical ? sliderDimensions.top : sliderDimensions.left;
@@ -10932,12 +10800,9 @@ class MasonryComponent {
10932
10800
  this._didResize$ = new BehaviorSubject(false);
10933
10801
  this._didInitialize$ = new BehaviorSubject(false);
10934
10802
  this._hideOverflow$ = new BehaviorSubject(false);
10935
- this._bindings = createReactiveBindings({
10936
- attribute: 'class.et-masonry--initialized',
10937
- observable: this._didInitialize$,
10938
- }, {
10939
- attribute: 'class.et-masonry--hide-overflow',
10940
- observable: this._hideOverflow$,
10803
+ this.hostClassBindings = signalHostClasses({
10804
+ 'et-masonry--initialized': toSignal(this._didInitialize$),
10805
+ 'et-masonry--hide-overflow': toSignal(this._hideOverflow$),
10941
10806
  });
10942
10807
  this._state = {
10943
10808
  preferredColumnWidth: 0,