@fuentis/phoenix-ui 0.0.9-alpha.550 → 0.0.9-alpha.552

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/index.d.ts CHANGED
@@ -1240,65 +1240,137 @@ interface MetaFormV2Config {
1240
1240
 
1241
1241
  type AccordionValue = string | number | string[] | number[] | null | undefined;
1242
1242
  declare class MetaFormV2Component implements OnChanges, OnDestroy {
1243
+ /** Form instance created/owned by the parent (dialog/page) */
1243
1244
  form: FormGroup;
1245
+ /**
1246
+ * V2 metadata/config:
1247
+ * - controls (grouped or flat)
1248
+ * - initialValues
1249
+ * - submitValidators (run on submit only)
1250
+ * - setupDependencies (optional runtime bindings)
1251
+ */
1244
1252
  config: MetaFormV2Config;
1245
- /** Page-level readOnly (parent toggles) */
1253
+ /**
1254
+ * Page-level readOnly state controlled by parent.
1255
+ * Used both for rendering and for "enter edit mode" behavior.
1256
+ */
1246
1257
  readOnly: boolean;
1247
- /** Optional layout props */
1258
+ /** Optional layout customization for inner content wrapper */
1248
1259
  contentStyle: Record<string, any> | null;
1260
+ /** Optional class name(s) applied to inner content wrapper */
1249
1261
  contentClass: string | null;
1262
+ /** Builds/ensures controls exist (ensures validators & default values are wired) */
1250
1263
  private fb;
1264
+ /** Registers and executes submit-only validators (async validation on submit) */
1251
1265
  private submitValidator;
1266
+ /** Used for validator localization (lang-dependent validators / messages) */
1252
1267
  private translate;
1268
+ /**
1269
+ * A lightweight signature of the current metadata structure.
1270
+ * Used to detect when the form schema changes (and avoid unnecessary resets).
1271
+ */
1253
1272
  private lastSignature;
1273
+ /**
1274
+ * Cleanup function returned by setupDependencies (if any).
1275
+ * Called only when metadata structure changes or on destroy.
1276
+ */
1254
1277
  private depCleanup?;
1255
- /** PrimeNG accordion active value(s) */
1278
+ /**
1279
+ * PrimeNG Accordion "value" for opened panels.
1280
+ * For multiple panels, PrimeNG expects an array of ids.
1281
+ */
1256
1282
  expandedGroupIds: string[];
1257
1283
  ngOnChanges(changes: SimpleChanges): void;
1284
+ /**
1285
+ * PrimeNG Accordion emits value as:
1286
+ * - single id (string/number)
1287
+ * - array of ids
1288
+ * We normalize everything into string[] for stable internal state.
1289
+ */
1258
1290
  onAccordionValueChange(v: AccordionValue): void;
1291
+ /** Normalizes Accordion value into a stable string[] representation */
1259
1292
  private normalizeAccordionValue;
1293
+ /** True when metadata contains at least one control definition */
1260
1294
  get hasControls(): boolean;
1295
+ /**
1296
+ * Heuristic: grouped config has "ctrl" on first element.
1297
+ * (Keeps template simple and avoids extra schema fields.)
1298
+ */
1261
1299
  get isGrouped(): boolean;
1300
+ /** Returns grouped schema structure (accordion groups) */
1262
1301
  get groupedControls(): any[];
1302
+ /** Returns flat schema structure (grid mode) */
1263
1303
  get flatControls(): any[];
1304
+ /** TrackBy for group rendering */
1264
1305
  groupTrack(g: any, idx: number): any;
1265
- /** PrimeNG panel value must match accordion value type */
1306
+ /**
1307
+ * PrimeNG accordion panel `value` must match accordion `value` type.
1308
+ * We always convert group id to string for consistent behavior.
1309
+ */
1266
1310
  panelValue(g: any): string;
1267
1311
  /**
1268
- * Mark & validate ONLY controls that already have a meaningful value.
1269
- * This prevents "required" errors from showing immediately on CREATE dialogs.
1312
+ * Marks & validates ONLY controls that already have meaningful values.
1313
+ * This is used when switching from readOnly -> edit mode to avoid:
1314
+ * - triggering "required" errors for empty fields
1315
+ * - expanding groups based on empty mandatory fields on CREATE dialogs
1270
1316
  */
1271
1317
  private touchAndValidateOnlyFilledControls;
1272
1318
  /**
1273
- * What counts as a "meaningful value"?
1319
+ * Defines what counts as a "meaningful" value:
1274
1320
  * - non-empty strings
1275
1321
  * - numbers / booleans
1276
1322
  * - non-empty arrays
1277
- * - objects with at least one key (or common "selected item" shapes)
1323
+ * - objects with common identifiers (key/uuid/id) or any own keys
1278
1324
  */
1279
1325
  private hasMeaningfulValue;
1280
1326
  /**
1281
- * Visible invalid = invalid AND (touched OR dirty).
1282
- * This aligns with the goal: don't expand groups due to empty required fields on create.
1327
+ * "Visible invalid" means:
1328
+ * - invalid
1329
+ * - AND user has interacted with it (touched or dirty)
1330
+ * This matches typical UI behavior: show errors only after interaction.
1283
1331
  */
1284
1332
  private isVisibleInvalid;
1333
+ /**
1334
+ * Checks if a group contains at least one visible invalid control.
1335
+ * Used to auto-expand groups when entering edit mode.
1336
+ */
1285
1337
  private groupHasVisibleInvalid;
1286
- /** Expand invalid groups but KEEP already opened ones */
1338
+ /**
1339
+ * Expands all groups that contain visible invalid controls,
1340
+ * while preserving any groups already expanded by the user.
1341
+ */
1287
1342
  private expandVisibleInvalidGroupsUnion;
1343
+ /** Cleanup dependency subscriptions when component is destroyed */
1288
1344
  ngOnDestroy(): void;
1289
1345
  static ɵfac: i0.ɵɵFactoryDeclaration<MetaFormV2Component, never>;
1290
1346
  static ɵcmp: i0.ɵɵComponentDeclaration<MetaFormV2Component, "phoenix-meta-form-v2", never, { "form": { "alias": "form"; "required": true; }; "config": { "alias": "config"; "required": true; }; "readOnly": { "alias": "readOnly"; "required": false; }; "contentStyle": { "alias": "contentStyle"; "required": false; }; "contentClass": { "alias": "contentClass"; "required": false; }; }, {}, never, never, true, never>;
1291
1347
  }
1292
1348
 
1293
1349
  declare class MetaFormFieldV2Component {
1350
+ /** Metadata definition of the field (type, key, options, styles, flags, etc.) */
1294
1351
  field: MetaFieldConfig;
1352
+ /** Parent FormGroup that contains the FormControl for this field */
1295
1353
  form: FormGroup;
1296
- /** External "page read-only" state; when true, we render read-only fields (like V1). */
1354
+ /**
1355
+ * Page-level read-only flag.
1356
+ * When true, the component renders ReadOnlyInputV2Component instead of editable controls.
1357
+ */
1297
1358
  readOnly: boolean;
1359
+ /**
1360
+ * Global disable flag (e.g. parent dialog toggles entire form disabled).
1361
+ * This is merged with field-level disable configuration.
1362
+ */
1298
1363
  disableForm: boolean;
1364
+ /** Used to manually trigger change detection for OnPush strategy */
1299
1365
  private cdr;
1366
+ /** Used to automatically unsubscribe from value/status streams on destroy */
1300
1367
  private dr;
1368
+ /** Translation service for validation and display labels */
1301
1369
  private translate;
1370
+ /**
1371
+ * Exposed enum-like mapping of MetaFieldType for template usage.
1372
+ * Keeps templates readable and avoids magic strings.
1373
+ */
1302
1374
  readonly MetaFieldType: Readonly<{
1303
1375
  TEXT: "TEXT";
1304
1376
  NUMBER: "NUMBER";
@@ -1324,22 +1396,56 @@ declare class MetaFormFieldV2Component {
1324
1396
  LINKS_DATA: "LINKS_DATA";
1325
1397
  SLOT: "SLOT";
1326
1398
  }>;
1399
+ /** Control key resolved from MetaFieldConfig */
1327
1400
  get key(): string;
1401
+ /** Field type resolved from MetaFieldConfig */
1328
1402
  get type(): MetaFieldType;
1403
+ /** Column width class for grid layout (falls back to default if not provided) */
1329
1404
  get colClass(): string;
1330
1405
  ngOnInit(): void;
1406
+ /** Human-friendly label defined in metadata (already localized key) */
1331
1407
  userFriendlyMessage(): string | null;
1408
+ /** Optional placeholder i18n key defined in metadata */
1332
1409
  placeholderKey(): string | null;
1410
+ /**
1411
+ * Resolves final read-only state for this field:
1412
+ * - page-level readOnly OR field-level readOnly
1413
+ */
1333
1414
  isReadOnly(): boolean;
1415
+ /**
1416
+ * Resolves final disabled state for this field:
1417
+ * - page-level disable OR field-level disable
1418
+ */
1334
1419
  isDisabled(): boolean;
1420
+ /** Shortcut to underlying FormControl */
1335
1421
  ctrl(): _angular_forms.AbstractControl<any, any, any> | null;
1336
- /** Used by read-only renderer. Keep it simple, same as V1 behavior. */
1422
+ /**
1423
+ * Minimal value formatter for legacy read-only rendering.
1424
+ * Kept intentionally simple to match V1 behavior.
1425
+ */
1337
1426
  displayValue(): any;
1427
+ /**
1428
+ * Determines whether validation error should be displayed.
1429
+ * Errors are shown only after user interaction (touched or dirty).
1430
+ */
1338
1431
  showError(): boolean;
1339
- /** mapira error key (sync + submit-only async) */
1432
+ /**
1433
+ * Maps control error object to a normalized error key.
1434
+ * Supports:
1435
+ * - Angular built-in validators
1436
+ * - Phoenix custom validators
1437
+ * - Submit-only async validators
1438
+ */
1340
1439
  errorKey(): string | null;
1341
- /** minimal: posle prevežeš na i18n ključeve */
1440
+ /**
1441
+ * Resolves translated error message based on errorKey().
1442
+ * This is the single place responsible for validation message UX.
1443
+ */
1342
1444
  errorText(): string;
1445
+ /**
1446
+ * Lightweight text formatter for simple read-only display use cases.
1447
+ * This is used mainly for inline displays and summary UIs.
1448
+ */
1343
1449
  valueText(): string;
1344
1450
  static ɵfac: i0.ɵɵFactoryDeclaration<MetaFormFieldV2Component, never>;
1345
1451
  static ɵcmp: i0.ɵɵComponentDeclaration<MetaFormFieldV2Component, "phoenix-meta-form-field-v2", never, { "field": { "alias": "field"; "required": true; }; "form": { "alias": "form"; "required": true; }; "readOnly": { "alias": "readOnly"; "required": false; }; "disableForm": { "alias": "disableForm"; "required": false; }; }, {}, never, never, true, never>;
@@ -1361,13 +1467,61 @@ type MetaAsyncExecutor = (url: string, body?: any) => Observable<any>;
1361
1467
  declare const META_FORM_ASYNC_EXECUTOR: InjectionToken<MetaAsyncExecutor>;
1362
1468
 
1363
1469
  declare class MetaSubmitValidatorService {
1470
+ /**
1471
+ * Optional async executor abstraction used to perform server-side validation
1472
+ * (e.g. uniqueness checks).
1473
+ *
1474
+ * If not provided, submit-only validators will be skipped gracefully.
1475
+ */
1364
1476
  private executor?;
1477
+ /** Used to automatically clean up subscriptions when the service is destroyed */
1365
1478
  private dr;
1366
- constructor(executor?: MetaAsyncExecutor | undefined);
1479
+ constructor(
1480
+ /**
1481
+ * Optional async executor abstraction used to perform server-side validation
1482
+ * (e.g. uniqueness checks).
1483
+ *
1484
+ * If not provided, submit-only validators will be skipped gracefully.
1485
+ */
1486
+ executor?: MetaAsyncExecutor | undefined);
1487
+ /**
1488
+ * Registers submit-only validators on the given form.
1489
+ *
1490
+ * - Attaches validator metadata to the form instance (via Symbols)
1491
+ * - Cleans up any previous subscriptions
1492
+ * - Subscribes to valueChanges in order to auto-clear submit-only errors
1493
+ * when the user modifies the field after a failed submit
1494
+ */
1367
1495
  register(form: FormGroup, validators: MetaSubmitValidatorConfig[] | null | undefined): void;
1496
+ /**
1497
+ * Executes submit-only validators.
1498
+ *
1499
+ * Flow:
1500
+ * 1) Mark all controls as touched/dirty so sync validation messages become visible
1501
+ * 2) If form is sync-invalid, skip async validation
1502
+ * 3) Clear previous submit-only errors
1503
+ * 4) Execute async validators sequentially
1504
+ * 5) Apply mapped errors back to controls
1505
+ *
1506
+ * Returns:
1507
+ * - true → form is valid (sync + submit-only async)
1508
+ * - false → at least one submit-only validator failed
1509
+ */
1368
1510
  run(form: FormGroup): Promise<boolean>;
1511
+ /**
1512
+ * Removes a specific submit-only error from the control without
1513
+ * touching other validation errors.
1514
+ */
1369
1515
  private removeError;
1516
+ /**
1517
+ * Clears submit-only errors for all controls involved in submit validators.
1518
+ * This does NOT trigger updateValueAndValidity to avoid unnecessary re-validation.
1519
+ */
1370
1520
  private clearSubmitErrors;
1521
+ /**
1522
+ * Marks all form controls as touched and dirty.
1523
+ * This is used on submit to make validation errors visible to the user.
1524
+ */
1371
1525
  private markAllTouchedOnSubmit;
1372
1526
  static ɵfac: i0.ɵɵFactoryDeclaration<MetaSubmitValidatorService, [{ optional: true; }]>;
1373
1527
  static ɵprov: i0.ɵɵInjectableDeclaration<MetaSubmitValidatorService>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fuentis/phoenix-ui",
3
- "version": "0.0.9-alpha.550",
3
+ "version": "0.0.9-alpha.552",
4
4
  "description": "Phoenix UI Angular component library",
5
5
  "license": "MIT",
6
6
  "peerDependencies": {