ng-hub-ui-forms 22.1.1 → 22.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -84,7 +84,8 @@ The required `email` field reveals its error automatically on submit — no manu
84
84
  `ng-hub-ui-forms` unifies a set of accessible form fields behind one contract:
85
85
  bind them with **Reactive Forms** and the matching validation errors appear
86
86
  **automatically** at the control, group and form level. Fields are standalone,
87
- `OnPush` and signal-native; the select is a maintained fork of ng-select; the
87
+ `OnPush` and signal-native; the select is a maintained fork of
88
+ [ng-select](https://github.com/ng-select/ng-select) (see [Credits](#-credits)); the
88
89
  datepicker is built from scratch on native `Date` and the Angular CDK overlay.
89
90
  Everything is themed through canonical `--hub-*` CSS variables with runtime dark
90
91
  mode — no Bootstrap dependency.
@@ -98,6 +99,30 @@ mode — no Bootstrap dependency.
98
99
  - **Validators & helpers** — `hubAreEqual` cross-field validator, `hubValidationError` / `hubFormText` projection directives, and a set of utility pipes.
99
100
  - **Signal Forms ready** — an opt-in [`ng-hub-ui-forms/signals`](#-signal-forms-opt-in) secondary entry point integrates Angular Signal Forms; the core stays Reactive-Forms-based and Angular-21-safe.
100
101
  - **Theming** — every colour, border, radius and spacing is a `--hub-*` CSS custom property; ships shared SCSS tokens for consumers.
102
+ - **Cross-library adapter** — `hubFormControlAdapter` lets other libraries render `hub-input` / `hub-select` on demand without hard-depending on this package (see below).
103
+
104
+ ---
105
+
106
+ ## 🔌 Cross-library adapter (`hubFormControlAdapter`)
107
+
108
+ Other ng-hub-ui libraries can host the forms controls **without taking a hard
109
+ dependency** on `ng-hub-ui-forms`. They expose an optional token; you wire the
110
+ ready-made `hubFormControlAdapter` once and their primitive controls upgrade to
111
+ `hub-input` / `hub-select`. For example, the `ng-hub-ui-paginable` table:
112
+
113
+ ```ts
114
+ import { provideHubPaginableFormControls } from 'ng-hub-ui-paginable';
115
+ import { hubFormControlAdapter } from 'ng-hub-ui-forms';
116
+
117
+ export const appConfig: ApplicationConfig = {
118
+ providers: [provideHubPaginableFormControls(hubFormControlAdapter)]
119
+ };
120
+ ```
121
+
122
+ The adapter creates components dynamically and bridges value-in / change-out; it
123
+ needs `provideHubForms()` or the default config in the environment. See the
124
+ ecosystem-wide [Synergies & agnosticism](../../README.md#synergies--agnosticism)
125
+ section.
101
126
 
102
127
  ---
103
128
 
@@ -284,6 +309,14 @@ See [CHANGELOG.md](./CHANGELOG.md).
284
309
 
285
310
  ---
286
311
 
312
+ ## 🙏 Credits
313
+
314
+ `hub-select` is a maintained **fork of [ng-select](https://github.com/ng-select/ng-select)** by the ng-select contributors. The upstream `src/ng-select` sources are vendored in place and re-themed with `--hub-*` tokens — pinned to upstream **`v23.0.1`** (tracked in [`src/lib/select/UPSTREAM`](./src/lib/select/UPSTREAM); deviations documented in [`src/lib/select/PATCHES.md`](./src/lib/select/PATCHES.md)). ng-select is distributed under the [MIT License](https://github.com/ng-select/ng-select/blob/master/LICENSE.md), and the original copyright notices are retained in the vendored files.
315
+
316
+ The datepicker, inputs and validation layer are original to `ng-hub-ui-forms`.
317
+
318
+ ---
319
+
287
320
  ## 📄 License
288
321
 
289
322
  MIT © [Carlos Morcillo](https://www.carlosmorcillo.com)
@@ -5908,6 +5908,65 @@ function hubAreEqual(primaryControlName, secondaryControlName) {
5908
5908
  };
5909
5909
  }
5910
5910
 
5911
+ /**
5912
+ * Ready-made {@link HubFormControlAdapter} backed by `HubInputComponent` /
5913
+ * `HubSelectComponent`.
5914
+ *
5915
+ * Wire it into any ng-hub-ui primitive that exposes an optional form-controls
5916
+ * token, e.g. `provideHubPaginableFormControls(hubFormControlAdapter)`. The host
5917
+ * library keeps **zero hard dependency** on `ng-hub-ui-forms`; only an app that
5918
+ * opts in pulls these components.
5919
+ *
5920
+ * Requires `provideHubForms()` (or the default config) to be available in the
5921
+ * environment so the field components can resolve their configuration.
5922
+ */
5923
+ const hubFormControlAdapter = {
5924
+ create(container, config) {
5925
+ if (config.kind === 'select') {
5926
+ const ref = container.createComponent(HubSelectComponent);
5927
+ ref.setInput('items', (config.options ?? []).map((option) => ({ ...option })));
5928
+ ref.setInput('bindLabel', 'label');
5929
+ ref.setInput('bindValue', 'value');
5930
+ ref.setInput('clearable', false);
5931
+ ref.setInput('searchable', false);
5932
+ if (config.placeholder) {
5933
+ ref.setInput('placeholder', config.placeholder);
5934
+ }
5935
+ if (config.cssClass) {
5936
+ ref.setInput('classlist', config.cssClass);
5937
+ }
5938
+ ref.instance.writeValue(config.value);
5939
+ const subscription = ref.instance.valueChange.subscribe((value) => config.onValueChange(value));
5940
+ ref.changeDetectorRef.detectChanges();
5941
+ return {
5942
+ setValue: (value) => ref.instance.writeValue(value),
5943
+ destroy: () => {
5944
+ subscription.unsubscribe();
5945
+ ref.destroy();
5946
+ }
5947
+ };
5948
+ }
5949
+ const ref = container.createComponent(HubInputComponent);
5950
+ ref.setInput('type', config.type ?? 'text');
5951
+ if (config.placeholder) {
5952
+ ref.setInput('placeholder', config.placeholder);
5953
+ }
5954
+ if (config.cssClass) {
5955
+ ref.setInput('classlist', config.cssClass);
5956
+ }
5957
+ ref.instance.writeValue(config.value);
5958
+ const subscription = ref.instance.valueChange.subscribe((value) => config.onValueChange(value));
5959
+ ref.changeDetectorRef.detectChanges();
5960
+ return {
5961
+ setValue: (value) => ref.instance.writeValue(value),
5962
+ destroy: () => {
5963
+ subscription.unsubscribe();
5964
+ ref.destroy();
5965
+ }
5966
+ };
5967
+ }
5968
+ };
5969
+
5911
5970
  /*
5912
5971
  * Public API Surface of ng-hub-ui-forms
5913
5972
  */
@@ -5917,5 +5976,5 @@ function hubAreEqual(primaryControlName, secondaryControlName) {
5917
5976
  * Generated bundle index. Do not edit.
5918
5977
  */
5919
5978
 
5920
- export { FormTextTypes, HUB_FORMS_CONFIG, HubAutoresizeDirective, HubDatepickerComponent, HubFieldControl, HubFieldsetComponent, HubFormComponent, HubFormControl, HubFormTextDirective, HubGroupControl, HubInputComponent, HubInputFormats, HubInvertColorPipe, HubJoinButLastPipe, HubLabelTypes, HubLegendComponent, HubLegendDirective, HubMapPipe, HubOtpInputComponent, HubSafeUrlPipe, HubSelectComponent, HubSelectFormats, HubSliderComponent, HubSnakeUpperPipe, HubTextareaComponent, HubUcfirstPipe, HubValidationErrorDirective, NgClearButtonTemplateDirective, NgFooterTemplateDirective, NgHeaderTemplateDirective, NgLabelTemplateDirective, NgLoadingSpinnerTemplateDirective, NgLoadingTextTemplateDirective, NgMultiLabelTemplateDirective, NgNotFoundTemplateDirective, NgOptgroupTemplateDirective, NgOptionComponent, NgOptionTemplateDirective, NgSelectConfig, NgTagTemplateDirective, NgTypeToSearchTemplateDirective, applyMask, areEqual, camelToSnakeUpper, controlHasMinOrMaxValidator, defaultHubDatepickerConfig, defaultHubDatepickerLabels, defaultHubFormsConfig, defaultInvalidFeedback, get, getActiveElement, getMinOrMaxValueFromValidator, hubAreEqual, isDefined$1 as isDefined, isMaskActive, isString, joinButLast, provideHubForms, runInZone, uuid };
5979
+ export { FormTextTypes, HUB_FORMS_CONFIG, HubAutoresizeDirective, HubDatepickerComponent, HubFieldControl, HubFieldsetComponent, HubFormComponent, HubFormControl, HubFormTextDirective, HubGroupControl, HubInputComponent, HubInputFormats, HubInvertColorPipe, HubJoinButLastPipe, HubLabelTypes, HubLegendComponent, HubLegendDirective, HubMapPipe, HubOtpInputComponent, HubSafeUrlPipe, HubSelectComponent, HubSelectFormats, HubSliderComponent, HubSnakeUpperPipe, HubTextareaComponent, HubUcfirstPipe, HubValidationErrorDirective, NgClearButtonTemplateDirective, NgFooterTemplateDirective, NgHeaderTemplateDirective, NgLabelTemplateDirective, NgLoadingSpinnerTemplateDirective, NgLoadingTextTemplateDirective, NgMultiLabelTemplateDirective, NgNotFoundTemplateDirective, NgOptgroupTemplateDirective, NgOptionComponent, NgOptionTemplateDirective, NgSelectConfig, NgTagTemplateDirective, NgTypeToSearchTemplateDirective, applyMask, areEqual, camelToSnakeUpper, controlHasMinOrMaxValidator, defaultHubDatepickerConfig, defaultHubDatepickerLabels, defaultHubFormsConfig, defaultInvalidFeedback, get, getActiveElement, getMinOrMaxValueFromValidator, hubAreEqual, hubFormControlAdapter, isDefined$1 as isDefined, isMaskActive, isString, joinButLast, provideHubForms, runInZone, uuid };
5921
5980
  //# sourceMappingURL=ng-hub-ui-forms.mjs.map