@acorex/modules 21.0.0-next.16 → 21.0.0-next.18

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 (63) hide show
  1. package/data-management/index.d.ts +153 -9
  2. package/document-management/index.d.ts +167 -374
  3. package/fesm2022/acorex-modules-common.mjs +11 -3
  4. package/fesm2022/acorex-modules-common.mjs.map +1 -1
  5. package/fesm2022/acorex-modules-content-management.mjs +15 -4
  6. package/fesm2022/acorex-modules-content-management.mjs.map +1 -1
  7. package/fesm2022/acorex-modules-data-management.mjs +1877 -1648
  8. package/fesm2022/acorex-modules-data-management.mjs.map +1 -1
  9. package/fesm2022/{acorex-modules-document-management-drive-choose.component-ovwhHP2n.mjs → acorex-modules-document-management-drive-choose.component-BOeZ9mpL.mjs} +3 -7
  10. package/fesm2022/acorex-modules-document-management-drive-choose.component-BOeZ9mpL.mjs.map +1 -0
  11. package/fesm2022/acorex-modules-document-management.mjs +655 -2995
  12. package/fesm2022/acorex-modules-document-management.mjs.map +1 -1
  13. package/fesm2022/{acorex-modules-human-capital-management-leave-request.entity-BDSyXKSF.mjs → acorex-modules-human-capital-management-leave-request.entity-CviI9xJC.mjs} +2 -2
  14. package/fesm2022/acorex-modules-human-capital-management-leave-request.entity-CviI9xJC.mjs.map +1 -0
  15. package/fesm2022/acorex-modules-human-capital-management.mjs +350 -695
  16. package/fesm2022/acorex-modules-human-capital-management.mjs.map +1 -1
  17. package/fesm2022/acorex-modules-person-core-education-level.entity-BiXdPA-Z.mjs +120 -0
  18. package/fesm2022/acorex-modules-person-core-education-level.entity-BiXdPA-Z.mjs.map +1 -0
  19. package/fesm2022/acorex-modules-person-core-marital-status.entity-j6sMTtTS.mjs +120 -0
  20. package/fesm2022/acorex-modules-person-core-marital-status.entity-j6sMTtTS.mjs.map +1 -0
  21. package/fesm2022/acorex-modules-person-core-person-identifier-type.entity-BIFiRZ2d.mjs +191 -0
  22. package/fesm2022/acorex-modules-person-core-person-identifier-type.entity-BIFiRZ2d.mjs.map +1 -0
  23. package/fesm2022/acorex-modules-person-core-person-relationship-type.entity-2qysKjU5.mjs +119 -0
  24. package/fesm2022/acorex-modules-person-core-person-relationship-type.entity-2qysKjU5.mjs.map +1 -0
  25. package/fesm2022/acorex-modules-person-core.mjs +290 -0
  26. package/fesm2022/acorex-modules-person-core.mjs.map +1 -0
  27. package/fesm2022/{acorex-modules-person-management-person-identifier.entity-CI8u0Ro6.mjs → acorex-modules-person-management-person-identifier.entity-HBmiUahC.mjs} +4 -3
  28. package/fesm2022/acorex-modules-person-management-person-identifier.entity-HBmiUahC.mjs.map +1 -0
  29. package/fesm2022/{acorex-modules-person-management-person-relationship.entity-DK3mYVFv.mjs → acorex-modules-person-management-person-relationship.entity-DbcXasEe.mjs} +4 -3
  30. package/fesm2022/acorex-modules-person-management-person-relationship.entity-DbcXasEe.mjs.map +1 -0
  31. package/fesm2022/acorex-modules-person-management.mjs +11 -259
  32. package/fesm2022/acorex-modules-person-management.mjs.map +1 -1
  33. package/fesm2022/{acorex-modules-task-management-task-board.page-CuP9U1h8.mjs → acorex-modules-task-management-task-board.page-BOOY3qla.mjs} +47 -54
  34. package/fesm2022/acorex-modules-task-management-task-board.page-BOOY3qla.mjs.map +1 -0
  35. package/fesm2022/acorex-modules-task-management.mjs +39 -11
  36. package/fesm2022/acorex-modules-task-management.mjs.map +1 -1
  37. package/fesm2022/acorex-modules-workflow-management-activity-definition.entity-BbBEPTBa.mjs +258 -0
  38. package/fesm2022/acorex-modules-workflow-management-activity-definition.entity-BbBEPTBa.mjs.map +1 -0
  39. package/fesm2022/acorex-modules-workflow-management-workflow-definition.entity-nJMBL0qt.mjs +371 -0
  40. package/fesm2022/acorex-modules-workflow-management-workflow-definition.entity-nJMBL0qt.mjs.map +1 -0
  41. package/fesm2022/acorex-modules-workflow-management-workflow-instance.entity-Pso0oRN5.mjs +313 -0
  42. package/fesm2022/acorex-modules-workflow-management-workflow-instance.entity-Pso0oRN5.mjs.map +1 -0
  43. package/fesm2022/acorex-modules-workflow-management.mjs +710 -2536
  44. package/fesm2022/acorex-modules-workflow-management.mjs.map +1 -1
  45. package/human-capital-management/index.d.ts +19 -79
  46. package/package.json +14 -10
  47. package/person-core/index.d.ts +117 -0
  48. package/person-management/index.d.ts +1 -25
  49. package/task-management/index.d.ts +12 -1
  50. package/workflow-management/index.d.ts +220 -265
  51. package/fesm2022/acorex-modules-document-management-drive-choose.component-ovwhHP2n.mjs.map +0 -1
  52. package/fesm2022/acorex-modules-human-capital-management-leave-request-task-popover.component-yGvT9kSL.mjs +0 -381
  53. package/fesm2022/acorex-modules-human-capital-management-leave-request-task-popover.component-yGvT9kSL.mjs.map +0 -1
  54. package/fesm2022/acorex-modules-human-capital-management-leave-request.entity-BDSyXKSF.mjs.map +0 -1
  55. package/fesm2022/acorex-modules-person-management-person-identifier-type.entity-VchCczk-.mjs +0 -498
  56. package/fesm2022/acorex-modules-person-management-person-identifier-type.entity-VchCczk-.mjs.map +0 -1
  57. package/fesm2022/acorex-modules-person-management-person-identifier.entity-CI8u0Ro6.mjs.map +0 -1
  58. package/fesm2022/acorex-modules-person-management-person-relationship.entity-DK3mYVFv.mjs.map +0 -1
  59. package/fesm2022/acorex-modules-task-management-task-board.page-CuP9U1h8.mjs.map +0 -1
  60. package/fesm2022/acorex-modules-workflow-management-cartable-page.component-Bso0XRkJ.mjs +0 -296
  61. package/fesm2022/acorex-modules-workflow-management-cartable-page.component-Bso0XRkJ.mjs.map +0 -1
  62. package/fesm2022/acorex-modules-workflow-management-index-xB36g4F1.mjs +0 -469
  63. package/fesm2022/acorex-modules-workflow-management-index-xB36g4F1.mjs.map +0 -1
@@ -39,9 +39,9 @@ import { AXSearchBoxModule } from '@acorex/components/search-box';
39
39
  import * as i4$2 from '@acorex/components/text-area';
40
40
  import { AXTextAreaModule } from '@acorex/components/text-area';
41
41
  import { AXFormModule } from '@acorex/components/form';
42
+ import { AXPLayoutRendererComponent, AXPLayoutBuilderService } from '@acorex/platform/layout/builder';
42
43
  import { moveItemInArray as moveItemInArray$1, transferArrayItem, CdkDropList, CdkDrag, CdkDragHandle } from '@angular/cdk/drag-drop';
43
44
  import { AXDialogService } from '@acorex/components/dialog';
44
- import { AXPLayoutBuilderService, AXPLayoutRendererComponent } from '@acorex/platform/layout/builder';
45
45
 
46
46
  const config = {
47
47
  i18n: 'data-management',
@@ -91,6 +91,19 @@ const RootConfig = {
91
91
  title: '@general:terms.common.tag',
92
92
  icon: 'fa-light fa-tags',
93
93
  },
94
+ equipmentCategory: {
95
+ name: 'EquipmentCategory',
96
+ title: '@data-management:equipments.entities.equipment-category.title',
97
+ titlePlural: '@data-management:equipments.entities.equipment-category.plural',
98
+ icon: 'fa-light fa-folder-tree',
99
+ },
100
+ equipment: {
101
+ name: 'Equipment',
102
+ source: 'DataManagement.Equipment',
103
+ title: '@data-management:equipments.entities.equipment.title',
104
+ titlePlural: '@data-management:equipments.entities.equipment.plural',
105
+ icon: 'fa-light fa-plug',
106
+ },
94
107
  },
95
108
  };
96
109
 
@@ -1384,6 +1397,7 @@ const AXMDataManagementFeatureKeys = {
1384
1397
  Queries: 'DataManagement:Feature:Queries',
1385
1398
  DataSources: 'DataManagement:Feature:DataSources',
1386
1399
  MetaDataDefinitions: 'DataManagement:Feature:MetaDataDefinitions',
1400
+ Equipments: 'DataManagement:Feature:Equipments',
1387
1401
  };
1388
1402
 
1389
1403
  //#region ---- Imports ----
@@ -1416,6 +1430,13 @@ class AXPDataManagementFeatureDefinitionProvider {
1416
1430
  defaultValue: true,
1417
1431
  type: 'boolean',
1418
1432
  });
1433
+ // Equipments feature
1434
+ context.addFeature(AXMDataManagementFeatureKeys.Equipments, {
1435
+ title: '@data-management:features.equipments.title',
1436
+ description: '@data-management:features.equipments.description',
1437
+ defaultValue: true,
1438
+ type: 'boolean',
1439
+ });
1419
1440
  }
1420
1441
  }
1421
1442
  //#endregion
@@ -1431,6 +1452,9 @@ const AXMPermissionsKeys = {
1431
1452
  MetaDataDefinition: {
1432
1453
  Management: 'DataManagement:Permission:MetaDataDefinition.Management',
1433
1454
  },
1455
+ Equipment: {
1456
+ Management: 'DataManagement:Permission:Equipment.Management',
1457
+ },
1434
1458
  Tag: {
1435
1459
  Management: 'DataManagement:Permission:Tag.Management',
1436
1460
  },
@@ -1455,6 +1479,8 @@ class AXMPermissionDefinitionProvider {
1455
1479
  const transMetaData = async (key) => await this.translateService.translateAsync(`@data-management:metadata-definitions.permissions.metadata-definitions.${key}`);
1456
1480
  // Tag permissions
1457
1481
  const transTag = async (key) => await this.translateService.translateAsync(`@data-management:tags.permissions.tags.${key}`);
1482
+ // Equipment permissions
1483
+ const transEquipment = async (key) => await this.translateService.translateAsync(`@data-management:equipments.permissions.equipments.${key}`);
1458
1484
  context
1459
1485
  .addGroup(RootConfig.module.name, moduleTitle, moduleDescription)
1460
1486
  //
@@ -1467,6 +1493,9 @@ class AXMPermissionDefinitionProvider {
1467
1493
  .addPermission(keys.MetaDataDefinition.Management, await transMetaData('actions.manage.title'), await transMetaData('actions.manage.description'))
1468
1494
  .endPermission()
1469
1495
  //
1496
+ .addPermission(keys.Equipment.Management, await transEquipment('actions.manage.title'), await transEquipment('actions.manage.description'))
1497
+ .endPermission()
1498
+ //
1470
1499
  .addPermission(keys.Tag.Management, await transTag('actions.manage.title'), await transTag('actions.manage.description'))
1471
1500
  .endPermission()
1472
1501
  //
@@ -1484,6 +1513,8 @@ const AXPDataManagementMenuKeys = {
1484
1513
  Queries: 'DataManagement:Menu:Queries',
1485
1514
  DataSources: 'DataManagement:Menu:DataSources',
1486
1515
  MetaDataDefinitions: 'DataManagement:Menu:MetaDataDefinitions',
1516
+ Equipments: 'DataManagement:Menu:Equipments',
1517
+ EquipmentCategories: 'DataManagement:Menu:EquipmentCategories',
1487
1518
  Tags: 'DataManagement:Menu:Tags',
1488
1519
  };
1489
1520
 
@@ -1536,12 +1567,35 @@ class AXMMenuProvider {
1536
1567
  permissions: [AXMPermissionsKeys.DataManagement.MetaDataDefinition.Management],
1537
1568
  },
1538
1569
  },
1570
+ // Equipments & Equipment Categories (commented out)
1571
+ // {
1572
+ // name: AXPDataManagementMenuKeys.Equipments,
1573
+ // text: '@data-management:equipments.menus.equipments.title',
1574
+ // path: this.entityService.createPath(RootConfig.module.name, RootConfig.entities.equipment.name),
1575
+ // icon: RootConfig.entities.equipment.icon,
1576
+ // priority: 9006,
1577
+ // policy: {
1578
+ // features: [AXMDataManagementFeatureKeys.Equipments],
1579
+ // permissions: [AXMPermissionsKeys.DataManagement.Equipment.Management],
1580
+ // },
1581
+ // },
1582
+ // {
1583
+ // name: AXPDataManagementMenuKeys.EquipmentCategories,
1584
+ // text: '@data-management:equipments.menus.equipment-categories.title',
1585
+ // path: this.entityService.createPath(RootConfig.module.name, RootConfig.entities.equipmentCategory.name),
1586
+ // icon: RootConfig.entities.equipmentCategory.icon,
1587
+ // priority: 9007,
1588
+ // policy: {
1589
+ // features: [AXMDataManagementFeatureKeys.Equipments],
1590
+ // permissions: [AXMPermissionsKeys.DataManagement.Equipment.Management],
1591
+ // },
1592
+ // },
1539
1593
  {
1540
1594
  name: AXPDataManagementMenuKeys.Tags,
1541
1595
  text: '@general:terms.common.tags',
1542
1596
  icon: RootConfig.entities.tag.icon,
1543
1597
  path: this.entityService.createPath(RootConfig.module.name, RootConfig.entities.tag.name),
1544
- priority: 9006,
1598
+ priority: 9008,
1545
1599
  policy: {
1546
1600
  permissions: [AXMPermissionsKeys.DataManagement.Tag.Management],
1547
1601
  },
@@ -1574,6 +1628,8 @@ class AXMEntityProvider {
1574
1628
  return (await Promise.resolve().then(function () { return metaDataDefinition_entity; })).metaDataDefinitionFactory(this.injector);
1575
1629
  case RootConfig.entities.tag.name:
1576
1630
  return (await Promise.resolve().then(function () { return tag_entity; })).factory(this.injector);
1631
+ case RootConfig.entities.equipment.name:
1632
+ return (await Promise.resolve().then(function () { return equipment_entity; })).equipmentFactory(this.injector);
1577
1633
  }
1578
1634
  }
1579
1635
  return null;
@@ -4299,6 +4355,179 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
4299
4355
  //#region ---- Tag Entity Types ----
4300
4356
  //#endregion
4301
4357
 
4358
+ //#region ---- Imports ----
4359
+ //#endregion
4360
+ async function equipmentFactory(injector) {
4361
+ const entityDef = {
4362
+ module: RootConfig.module.name,
4363
+ name: RootConfig.entities.equipment.name,
4364
+ title: RootConfig.entities.equipment.title,
4365
+ icon: RootConfig.entities.equipment.icon,
4366
+ formats: {
4367
+ individual: RootConfig.entities.equipment.title,
4368
+ plural: RootConfig.entities.equipment.titlePlural,
4369
+ displayName: RootConfig.entities.equipment.title,
4370
+ searchResult: {
4371
+ title: '{{ title }} ({{ code }})',
4372
+ description: RootConfig.module.title,
4373
+ },
4374
+ },
4375
+ plugins: [
4376
+ { name: 'history' },
4377
+ { name: 'lock' },
4378
+ { name: 'compare' },
4379
+ { name: 'clone' },
4380
+ {
4381
+ name: 'category',
4382
+ options: {
4383
+ appearance: { icon: true, color: true },
4384
+ metaData: { enabled: true },
4385
+ },
4386
+ },
4387
+ {
4388
+ name: 'meta-data-form',
4389
+ options: {
4390
+ path: 'categoryIds',
4391
+ title: '@data-management:equipments.entities.equipment.components.meta-data-form.title',
4392
+ },
4393
+ },
4394
+ { name: 'tags' },
4395
+ { name: 'notes' },
4396
+ ],
4397
+ relatedEntities: [],
4398
+ groups: [
4399
+ {
4400
+ id: 'basic-info',
4401
+ title: '@general:terms.interface.basic-info',
4402
+ },
4403
+ ],
4404
+ properties: [
4405
+ {
4406
+ name: 'code',
4407
+ title: '@general:terms.common.code',
4408
+ groupId: 'basic-info',
4409
+ options: {
4410
+ sort: { enabled: true },
4411
+ filter: {
4412
+ advance: { enabled: true },
4413
+ inline: { enabled: true },
4414
+ },
4415
+ },
4416
+ schema: {
4417
+ dataType: 'string',
4418
+ interface: {
4419
+ type: AXPWidgetsCatalog.text,
4420
+ options: {
4421
+ placeholder: 'e.g., EQ-001',
4422
+ },
4423
+ },
4424
+ },
4425
+ validations: [
4426
+ {
4427
+ rule: 'required',
4428
+ },
4429
+ ],
4430
+ },
4431
+ {
4432
+ name: 'title',
4433
+ title: '@general:terms.common.title',
4434
+ groupId: 'basic-info',
4435
+ options: {
4436
+ sort: { enabled: true },
4437
+ filter: {
4438
+ advance: { enabled: true },
4439
+ inline: { enabled: true },
4440
+ },
4441
+ },
4442
+ schema: {
4443
+ dataType: 'string',
4444
+ interface: {
4445
+ type: AXPWidgetsCatalog.text,
4446
+ },
4447
+ },
4448
+ validations: [
4449
+ {
4450
+ rule: 'required',
4451
+ },
4452
+ ],
4453
+ },
4454
+ {
4455
+ name: 'description',
4456
+ title: '@general:terms.common.description',
4457
+ groupId: 'basic-info',
4458
+ options: {
4459
+ sort: { enabled: false },
4460
+ filter: {
4461
+ advance: { enabled: true },
4462
+ inline: { enabled: false },
4463
+ },
4464
+ },
4465
+ schema: {
4466
+ dataType: 'string',
4467
+ interface: {
4468
+ type: AXPWidgetsCatalog.largeText,
4469
+ options: {
4470
+ rows: 3,
4471
+ },
4472
+ },
4473
+ },
4474
+ },
4475
+ ],
4476
+ columns: [
4477
+ { name: 'code' },
4478
+ { name: 'title' },
4479
+ { name: 'categoryIds', options: { dataPath: 'categories' } },
4480
+ ],
4481
+ interfaces: {
4482
+ master: {
4483
+ create: {
4484
+ sections: [{ id: 'basic-info' }, { id: 'classification' }],
4485
+ properties: [
4486
+ { name: 'code', layout: { positions: { lg: { colSpan: 6, order: 1 } } } },
4487
+ { name: 'title', layout: { positions: { lg: { colSpan: 6, order: 2 } } } },
4488
+ { name: 'description', layout: { positions: { lg: { colSpan: 12, order: 3 } } } },
4489
+ { name: 'categoryIds', layout: { positions: { lg: { colSpan: 12, order: 12 } } } },
4490
+ ],
4491
+ },
4492
+ update: {
4493
+ sections: [{ id: 'basic-info' }, { id: 'classification' }],
4494
+ properties: [
4495
+ { name: 'code', layout: { positions: { lg: { colSpan: 6, order: 1 } } } },
4496
+ { name: 'title', layout: { positions: { lg: { colSpan: 6, order: 2 } } } },
4497
+ { name: 'description', layout: { positions: { lg: { colSpan: 12, order: 3 } } } },
4498
+ { name: 'categoryIds', layout: { positions: { lg: { colSpan: 12, order: 12 } } } },
4499
+ ],
4500
+ },
4501
+ single: {
4502
+ title: '{{title}}',
4503
+ sections: [{ id: 'basic-info' }, { id: 'classification' }],
4504
+ properties: [
4505
+ { name: 'code', layout: { positions: { lg: { colSpan: 6, order: 1 } } } },
4506
+ { name: 'title', layout: { positions: { lg: { colSpan: 6, order: 2 } } } },
4507
+ { name: 'description', layout: { positions: { lg: { colSpan: 12, order: 3 } } } },
4508
+ { name: 'categoryIds', layout: { label: { visible: true }, positions: { lg: { colSpan: 12, order: 12 } } } },
4509
+ ],
4510
+ actions: [...entityMasterRecordActions()],
4511
+ },
4512
+ list: {
4513
+ actions: [...entityMasterCrudActions()],
4514
+ views: [
4515
+ createAllQueryView({
4516
+ sorts: [{ name: 'title', dir: 'asc' }],
4517
+ }),
4518
+ ],
4519
+ },
4520
+ },
4521
+ },
4522
+ };
4523
+ return entityDef;
4524
+ }
4525
+
4526
+ var equipment_entity = /*#__PURE__*/Object.freeze({
4527
+ __proto__: null,
4528
+ equipmentFactory: equipmentFactory
4529
+ });
4530
+
4302
4531
  class AXMQueryEntityModule {
4303
4532
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXMQueryEntityModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); }
4304
4533
  static { this.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.3.16", ngImport: i0, type: AXMQueryEntityModule }); }
@@ -7774,12 +8003,12 @@ var queryBuilderWidgetDesigner_component = /*#__PURE__*/Object.freeze({
7774
8003
  //#region ---- Re-exports from Entity Types ----
7775
8004
  //#endregion
7776
8005
 
7777
- const AXPMetaDataSelectorWidget = {
7778
- name: 'meta-data-selector-editor',
7779
- title: '@data-management:metadata-definitions.components.meta-data-selector.title',
8006
+ const AXPMetaDataFormWidget = {
8007
+ name: 'meta-data-form-editor',
8008
+ title: '@data-management:metadata-definitions.components.meta-data-form.title',
7780
8009
  categories: AXP_WIDGETS_EDITOR_CATEGORY,
7781
8010
  groups: [AXPWidgetGroupEnum.UtilityWidget],
7782
- description: '@data-management:metadata-definitions.components.meta-data-selector.description',
8011
+ description: '@data-management:metadata-definitions.components.meta-data-form.description',
7783
8012
  icon: 'fa-light fa-list-check',
7784
8013
  defaultFilterWidgetName: 'string-filter',
7785
8014
  type: 'editor',
@@ -7789,1753 +8018,1802 @@ const AXPMetaDataSelectorWidget = {
7789
8018
  properties: [
7790
8019
  AXP_NAME_PROPERTY,
7791
8020
  AXP_DATA_PATH_PROPERTY,
8021
+ AXP_READONLY_PROPERTY,
8022
+ AXP_DISABLED_PROPERTY,
7792
8023
  ],
7793
8024
  components: {
7794
8025
  view: {
7795
- component: () => Promise.resolve().then(function () { return metaDataSelectorView_component; }).then((c) => c.AXPMetaDataSelectorWidgetViewComponent),
8026
+ component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
7796
8027
  },
7797
8028
  edit: {
7798
- component: () => Promise.resolve().then(function () { return metaDataSelectorEdit_component; }).then((c) => c.AXPMetaDataSelectorWidgetEditComponent),
8029
+ component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
7799
8030
  },
7800
8031
  print: {
7801
- component: () => Promise.resolve().then(function () { return metaDataSelectorEdit_component; }).then((c) => c.AXPMetaDataSelectorWidgetEditComponent),
8032
+ component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
7802
8033
  },
7803
8034
  },
7804
8035
  };
7805
8036
 
7806
- //#region ---- Meta-Data Selector Field Types ----
7807
- //#endregion
7808
- //#region ---- Utility Functions ----
7809
- /**
7810
- * Convert raw value to designer state
7811
- */
7812
- function convertValueToState(value) {
7813
- // Handle null/undefined
7814
- if (!value) {
7815
- return {
7816
- groups: [createDefaultGroup()],
7817
- mode: 'designer',
7818
- };
8037
+ class AXPMetaDataFormWidgetEditComponent extends AXPValueWidgetComponent {
8038
+ constructor() {
8039
+ super(...arguments);
8040
+ //#region ---- Inputs ----
8041
+ /**
8042
+ * Groups structure from meta-data-selector or evaluated expression
8043
+ */
8044
+ this.groups = computed(() => {
8045
+ const options = this.options();
8046
+ const groupsOption = options['groups'];
8047
+ // Handle evaluated expression result (array of groups) or direct groups array
8048
+ if (Array.isArray(groupsOption) && groupsOption.length > 0) {
8049
+ return groupsOption;
8050
+ }
8051
+ return [];
8052
+ }, ...(ngDevMode ? [{ debugName: "groups" }] : []));
8053
+ this.#effect = effect(() => {
8054
+ this.initializeFormDefinition();
8055
+ }, ...(ngDevMode ? [{ debugName: "#effect" }] : []));
8056
+ /**
8057
+ * Check if there are any valid metadata definitions available
8058
+ */
8059
+ this.hasDefinitions = computed(() => {
8060
+ const groups = this.groups();
8061
+ if (groups.length === 0) {
8062
+ return false;
8063
+ }
8064
+ return groups.some((group) => {
8065
+ const fields = group.fields || [];
8066
+ return fields.length > 0 && fields.some((field) => field != null);
8067
+ });
8068
+ }, ...(ngDevMode ? [{ debugName: "hasDefinitions" }] : []));
8069
+ //#endregion
8070
+ //#region ---- Outputs ----
8071
+ /**
8072
+ * Emitted when form context changes
8073
+ */
8074
+ this.contextChange = output();
8075
+ /**
8076
+ * Emitted when form validity changes
8077
+ */
8078
+ this.validityChange = output();
8079
+ //#endregion
8080
+ //#region ---- Properties ----
8081
+ this.layoutRenderer = viewChild(AXPLayoutRendererComponent, ...(ngDevMode ? [{ debugName: "layoutRenderer" }] : []));
8082
+ /**
8083
+ * Form definition signal that only updates when structure actually changes
8084
+ */
8085
+ this.formDefinition = signal({ groups: [] }, ...(ngDevMode ? [{ debugName: "formDefinition" }] : []));
7819
8086
  }
7820
- // Handle old structure (flat array) - no longer supported but graceful fallback
7821
- if (Array.isArray(value)) {
7822
- return {
7823
- groups: [
7824
- {
7825
- id: 'group-default',
7826
- name: 'default',
7827
- title: 'Default Section',
7828
- description: undefined,
7829
- order: 0,
7830
- fields: value.map((item, index) => ({
7831
- id: item.id || `field-${index}`,
7832
- name: item.name,
7833
- title: item.title,
7834
- description: item.description,
7835
- interface: item.interface,
7836
- configuration: item.configuration,
7837
- status: item.status || 'active',
7838
- order: item.order ?? index,
7839
- isNewlyAdded: item.isNewlyAdded,
7840
- })),
7841
- },
7842
- ],
7843
- mode: 'designer',
7844
- };
7845
- }
7846
- // Handle new structure (groups)
7847
- if (value.groups && Array.isArray(value.groups)) {
7848
- const groups = value.groups.map((group, groupIndex) => ({
7849
- id: group.id || `group-${group.name}`,
7850
- name: group.name,
7851
- title: group.title,
7852
- description: group.description,
7853
- order: group.order ?? groupIndex,
7854
- fields: (group.fields || []).map((field, fieldIndex) => ({
7855
- id: field.id || `field-${fieldIndex}`,
7856
- name: field.name,
7857
- title: field.title,
7858
- description: field.description,
7859
- interface: field.interface,
7860
- configuration: field.configuration,
7861
- status: field.status || 'active',
7862
- order: field.order ?? fieldIndex,
7863
- isNewlyAdded: field.isNewlyAdded,
7864
- })),
7865
- isNewlyAdded: group.isNewlyAdded,
7866
- }));
7867
- // Ensure at least 1 group exists
7868
- const finalGroups = groups.length > 0 ? groups : [createDefaultGroup()];
7869
- return {
7870
- groups: finalGroups,
7871
- mode: 'designer',
7872
- };
7873
- }
7874
- // Fallback to default
7875
- return {
7876
- groups: [createDefaultGroup()],
7877
- mode: 'designer',
7878
- };
7879
- }
7880
- /**
7881
- * Convert designer state to value for persistence
7882
- */
7883
- function convertStateToValue(state) {
7884
- return {
7885
- groups: state.groups.map((group) => {
7886
- // Filter deleted fields only
7887
- const activeFields = group.fields.filter((field) => field.status !== 'deleted');
7888
- // Explicitly include only the properties defined in AXMMetaDataSelectorValue
7889
- // This ensures isNewlyAdded and other internal properties are not included
7890
- return {
7891
- name: group.name,
7892
- title: group.title,
7893
- description: group.description,
7894
- order: group.order,
7895
- fields: activeFields.map((field) => {
7896
- // Explicitly include only the properties defined in AXMMetaDataSelectorValue
7897
- // This ensures isNewlyAdded, status, and other internal properties are not included
7898
- return {
7899
- id: field.id,
7900
- name: field.name,
7901
- title: field.title,
7902
- description: field.description,
7903
- interface: field.interface,
7904
- configuration: field.configuration,
7905
- order: field.order,
7906
- };
7907
- }),
7908
- };
7909
- }),
7910
- };
7911
- }
7912
- /**
7913
- * Create a default group
7914
- */
7915
- function createDefaultGroup() {
7916
- return {
7917
- id: 'group-default',
7918
- name: 'default',
7919
- title: 'Default Section',
7920
- description: undefined,
7921
- order: 0,
7922
- fields: [],
7923
- isNewlyAdded: true,
7924
- };
7925
- }
7926
- //#endregion
7927
-
7928
- class AXPMetaDataSelectorWidgetEditComponent extends AXPValueWidgetComponent {
7929
- constructor() {
7930
- super(...arguments);
7931
- //#region ---- Services & Dependencies ----
7932
- this.dataSelectorService = inject(AXPDataSelectorService);
7933
- this.metaDataService = inject(AXMMetaDataDefinitionService);
7934
- this.entityResolver = inject(AXPEntityDefinitionRegistryService);
7935
- this.dialogService = inject(AXDialogService);
7936
- this.translationService = inject(AXTranslationService);
7937
- this.layoutBuilder = inject(AXPLayoutBuilderService);
7938
- this.widgetPropertyViewerService = inject(AXPWidgetPropertyViewerService);
7939
- //#endregion
7940
- //#region ---- Class Properties ----
7941
- this.DEFAULT_GROUP_NAME = 'default';
7942
- this.designerState = signal({
7943
- groups: [createDefaultGroup()],
7944
- mode: 'designer',
7945
- }, ...(ngDevMode ? [{ debugName: "designerState" }] : []));
7946
- //#endregion
7947
- //#region ---- Computed Properties ----
7948
- /**
7949
- * Check if the widget is in readonly mode
7950
- */
7951
- this.readonly = computed(() => this.options()['readonly'], ...(ngDevMode ? [{ debugName: "readonly" }] : []));
7952
- /**
7953
- * Check if a group is the default group
7954
- */
7955
- this.isDefaultGroup = (groupName) => {
7956
- return groupName === this.DEFAULT_GROUP_NAME;
7957
- };
7958
- /**
7959
- * Check if we can delete a group (more than 1 group exists)
7960
- */
7961
- this.canDeleteGroup = computed(() => {
7962
- return this.designerState().groups.length > 1;
7963
- }, ...(ngDevMode ? [{ debugName: "canDeleteGroup" }] : []));
7964
- /**
7965
- * Disable preview when no groups or all groups are empty
7966
- */
7967
- this.isPreviewDisabled = computed(() => {
7968
- const groups = this.designerState().groups || [];
7969
- if (groups.length === 0) {
7970
- return true;
7971
- }
7972
- // Check if all groups have no active fields
7973
- const hasAnyActiveFields = groups.some((group) => group.fields.some((field) => field.status === 'active'));
7974
- return !hasAnyActiveFields;
7975
- }, ...(ngDevMode ? [{ debugName: "isPreviewDisabled" }] : []));
7976
- /**
7977
- * Get all groups for rendering
7978
- */
7979
- this.groups = computed(() => this.designerState().groups, ...(ngDevMode ? [{ debugName: "groups" }] : []));
7980
- /**
7981
- * Get groups data formatted for meta-data-form component (only active fields)
7982
- */
7983
- this.previewGroups = computed(() => {
7984
- return this.groups()
7985
- .map((group) => ({
7986
- name: group.name,
7987
- title: group.title,
7988
- description: group.description,
7989
- fields: group.fields
7990
- .filter((field) => field.status === 'active')
7991
- .sort((a, b) => a.order - b.order)
7992
- .map((field) => ({
7993
- name: field.name,
7994
- title: field.title,
7995
- description: field.description,
7996
- interface: field.interface,
7997
- configuration: field.configuration,
7998
- defaultValue: field.configuration?.['defaultValue'],
7999
- })),
8000
- }))
8001
- .filter((group) => group.fields.length > 0);
8002
- }, ...(ngDevMode ? [{ debugName: "previewGroups" }] : []));
8003
- /**
8004
- * Convert preview groups to form definition for layout renderer
8005
- */
8006
- this.previewFormDefinition = computed(() => {
8007
- const groups = this.previewGroups();
8008
- const formGroups = [];
8009
- groups.forEach((group) => {
8010
- const fields = group.fields || [];
8011
- const validFields = fields.filter((field) => field != null);
8012
- if (validFields.length > 0) {
8013
- const parameters = validFields.map((field) => this.convertFieldToFormDefinition(field));
8014
- formGroups.push({
8015
- name: this.sanitizeGroupName(group.name || 'default'),
8016
- title: group.title || group.name,
8017
- description: group.description,
8018
- look: groups.length > 1 ? 'group' : 'container',
8019
- parameters,
8020
- });
8021
- }
8022
- });
8023
- return { groups: formGroups };
8024
- }, ...(ngDevMode ? [{ debugName: "previewFormDefinition" }] : []));
8025
- //#endregion
8026
- //#region ---- Lifecycle & Effects ----
8027
- /**
8028
- * Sync external value changes to internal state
8029
- */
8030
- this.#syncValueToState = effect(() => {
8031
- const value = this.getValue();
8032
- const newState = convertValueToState(value);
8033
- this.designerState.set(newState);
8034
- }, ...(ngDevMode ? [{ debugName: "#syncValueToState" }] : []));
8035
- /**
8036
- * Effect to handle status changes and cleanup before submission
8037
- */
8038
- this.#statusChanged = effect(() => {
8039
- if (this.layoutService.status() === AXPPageStatus.Submitting) {
8040
- const currentState = this.designerState();
8041
- const cleanedValue = convertStateToValue(currentState);
8042
- this.setValue(cleanedValue);
8043
- }
8044
- }, ...(ngDevMode ? [{ debugName: "#statusChanged" }] : []));
8087
+ #effect;
8088
+ //#endregion
8089
+ //#region ---- Event Handlers ----
8090
+ /**
8091
+ * Handle context change from dynamic form
8092
+ */
8093
+ onContextChange(context) {
8094
+ this.contextChange.emit(context);
8095
+ this.setValue(context);
8045
8096
  }
8046
8097
  /**
8047
- * Convert a field to form field definition
8098
+ * Handle validity change from dynamic form
8048
8099
  */
8049
- convertFieldToFormDefinition(field) {
8050
- const interfaceConfig = this.parseInterfaceConfig(field.interface);
8051
- const defaultValue = field.defaultValue ?? field.configuration?.defaultValue;
8052
- const description = field.description ?? field.configuration?.description;
8053
- return {
8054
- path: field.name || 'unnamed',
8055
- title: field.title || 'Untitled Field',
8056
- description: description,
8057
- widget: {
8058
- type: interfaceConfig.type || 'text-editor',
8059
- path: field.name || 'unnamed',
8060
- options: {
8061
- ...interfaceConfig.options,
8062
- defaultValue: defaultValue,
8063
- readonly: true,
8064
- validations: this.parseValidations(field.interface),
8065
- },
8066
- },
8067
- };
8100
+ onValidityChange(isValid) {
8101
+ this.validityChange.emit(isValid);
8068
8102
  }
8103
+ //#endregion
8104
+ //#region ---- Private Methods ----
8069
8105
  /**
8070
- * Parse interface configuration from metadata
8106
+ * Initialize form definition based on current inputs
8071
8107
  */
8072
- parseInterfaceConfig(interfaceValue) {
8073
- if (typeof interfaceValue === 'string') {
8074
- try {
8075
- return JSON.parse(interfaceValue || '{}');
8076
- }
8077
- catch (error) {
8078
- console.warn('Failed to parse interface config:', interfaceValue, error);
8079
- return {};
8080
- }
8108
+ initializeFormDefinition() {
8109
+ const groups = this.groups();
8110
+ if (groups.length > 0) {
8111
+ const newFormDefinition = this.convertGroupsToFormDefinition(groups);
8112
+ this.formDefinition.set(newFormDefinition);
8081
8113
  }
8082
- return interfaceValue || {};
8083
- }
8084
- /**
8085
- * Parse validations from interface configuration
8086
- */
8087
- parseValidations(interfaceValue) {
8088
- const config = this.parseInterfaceConfig(interfaceValue);
8089
- return config.options?.validations || [];
8090
8114
  }
8091
8115
  /**
8092
- * Sanitize group name for use as identifier
8116
+ * Convert groups structure from meta-data-selector to form definition
8117
+ * Each metadata group becomes a separate form group with visual separation (card look)
8093
8118
  */
8094
- sanitizeGroupName(name) {
8095
- return name.toLowerCase().replace(/[^a-z0-9]/g, '-');
8096
- }
8097
- //#endregion
8098
- //#region ---- Lifecycle & Effects ----
8099
- /**
8100
- * Sync external value changes to internal state
8119
+ convertGroupsToFormDefinition(groups) {
8120
+ const formGroups = [];
8121
+ groups.forEach((group) => {
8122
+ const fields = group.fields || [];
8123
+ const validFields = fields.filter((field) => field != null);
8124
+ if (validFields.length > 0) {
8125
+ const parameters = validFields.map((field) => this.convertMetadataToFieldDefinition(field));
8126
+ formGroups.push({
8127
+ name: this.sanitizeGroupName(group.name || 'default'),
8128
+ title: group.title || group.name,
8129
+ description: group.description,
8130
+ look: groups.length > 1 ? 'group' : 'container',
8131
+ parameters,
8132
+ });
8133
+ }
8134
+ });
8135
+ return { groups: formGroups };
8136
+ }
8137
+ /**
8138
+ * Convert single metadata definition to field definition
8101
8139
  */
8102
- #syncValueToState;
8140
+ convertMetadataToFieldDefinition(metadata) {
8141
+ // Handle null/undefined metadata
8142
+ if (!metadata) {
8143
+ console.warn('Undefined metadata definition encountered');
8144
+ return {
8145
+ path: 'undefined',
8146
+ title: 'Undefined Field',
8147
+ description: 'This field has undefined metadata',
8148
+ widget: {
8149
+ type: 'text-editor',
8150
+ path: 'undefined',
8151
+ options: {
8152
+ defaultValue: '',
8153
+ validations: [],
8154
+ },
8155
+ },
8156
+ };
8157
+ }
8158
+ const interfaceConfig = this.parseInterfaceConfig(metadata.interface);
8159
+ // Handle defaultValue: support both direct property and configuration.defaultValue
8160
+ // (meta-data-selector uses configuration.defaultValue, other sources may use defaultValue directly)
8161
+ const defaultValue = metadata.defaultValue ?? metadata.configuration?.defaultValue;
8162
+ // Handle description: support both direct property and from configuration
8163
+ const description = metadata.description ?? metadata.configuration?.description;
8164
+ const widget = {
8165
+ type: interfaceConfig.type || 'text-editor',
8166
+ path: metadata.name || 'unnamed',
8167
+ options: {
8168
+ ...interfaceConfig.options,
8169
+ defaultValue: defaultValue,
8170
+ validations: this.parseValidations(metadata.interface),
8171
+ },
8172
+ };
8173
+ if (interfaceConfig.triggers?.length) {
8174
+ widget.triggers = interfaceConfig.triggers;
8175
+ }
8176
+ return {
8177
+ path: metadata.name || 'unnamed',
8178
+ title: metadata.title || 'Untitled Field',
8179
+ description: description,
8180
+ widget,
8181
+ };
8182
+ }
8103
8183
  /**
8104
- * Effect to handle status changes and cleanup before submission
8184
+ * Parse interface configuration from metadata
8105
8185
  */
8106
- #statusChanged;
8107
- //#endregion
8108
- //#region ---- Group Management ----
8186
+ parseInterfaceConfig(interfaceValue) {
8187
+ if (typeof interfaceValue === 'string') {
8188
+ try {
8189
+ return JSON.parse(interfaceValue || '{}');
8190
+ }
8191
+ catch (error) {
8192
+ console.warn('Failed to parse interface config:', interfaceValue, error);
8193
+ return {};
8194
+ }
8195
+ }
8196
+ return interfaceValue || {};
8197
+ }
8109
8198
  /**
8110
- * Handle adding a new group
8199
+ * Parse validations from interface configuration
8111
8200
  */
8112
- async handleAddGroupClick() {
8113
- await this.layoutBuilder
8114
- .create()
8115
- .dialog((dialog) => {
8116
- dialog
8117
- .setTitle('@data-management:metadata-definitions.actions.add-group.title')
8118
- .setContext({ title: '', description: '' })
8119
- .content((flex) => {
8120
- flex
8121
- .setDirection('column')
8122
- .formField('@general:terms.common.title', (field) => {
8123
- field.path('title');
8124
- field.textBox({ validations: [{ rule: 'required' }] });
8125
- })
8126
- .formField('@general:terms.common.description', (field) => {
8127
- field.path('description');
8128
- field.largeTextBox({});
8129
- });
8130
- })
8131
- .setActions((actions) => {
8132
- actions.cancel('@general:actions.cancel.title').submit('@general:actions.save.title');
8133
- })
8134
- .onAction(async (dialogRef) => {
8135
- const context = dialogRef.context();
8136
- const action = dialogRef.action();
8137
- if (!context || action === 'cancel') {
8138
- return;
8139
- }
8140
- const form = context;
8141
- if (form.title?.trim()) {
8142
- const newGroup = {
8143
- id: AXPDataGenerator.uuid(),
8144
- name: generateKebabCase(form.title),
8145
- title: form.title,
8146
- description: form.description || undefined,
8147
- order: this.designerState().groups.length,
8148
- fields: [],
8149
- isNewlyAdded: true,
8150
- };
8151
- this.designerState.update((state) => ({
8152
- ...state,
8153
- groups: [...state.groups, newGroup],
8154
- }));
8155
- this.syncStateToValue();
8156
- }
8157
- });
8158
- })
8159
- .show();
8201
+ parseValidations(interfaceValue) {
8202
+ const config = this.parseInterfaceConfig(interfaceValue);
8203
+ return config.options?.validations || [];
8160
8204
  }
8161
8205
  /**
8162
- * Handle editing a group
8206
+ * Sanitize group name for use as identifier
8163
8207
  */
8164
- async handleGroupEdit(group) {
8165
- await this.layoutBuilder
8166
- .create()
8167
- .dialog((dialog) => {
8168
- dialog
8169
- .setTitle('@data-management:metadata-definitions.actions.edit-group.title')
8170
- .setContext({ title: group.title || group.name, description: group.description || '' })
8171
- .content((flex) => {
8172
- flex
8173
- .setDirection('column')
8174
- .formField('@general:terms.common.title', (field) => {
8175
- field.path('title');
8176
- field.textBox({ validations: [{ rule: 'required' }] });
8177
- })
8178
- .formField('@general:terms.common.description', (field) => {
8179
- field.path('description');
8180
- field.largeTextBox({});
8181
- });
8182
- })
8183
- .setActions((actions) => {
8184
- actions.cancel('@general:actions.cancel.title').submit('@general:actions.save.title');
8185
- })
8186
- .onAction(async (dialogRef) => {
8187
- const context = dialogRef.context();
8188
- const action = dialogRef.action();
8189
- if (!context || action === 'cancel') {
8190
- return;
8191
- }
8192
- const form = context;
8193
- if (form.title?.trim()) {
8194
- this.designerState.update((state) => ({
8195
- ...state,
8196
- groups: state.groups.map((g) => g.id === group.id
8197
- ? {
8198
- ...g,
8199
- name: generateKebabCase(form.title),
8200
- title: form.title,
8201
- description: form.description || undefined,
8202
- }
8203
- : g),
8204
- }));
8205
- this.syncStateToValue();
8206
- }
8207
- });
8208
- })
8209
- .show();
8208
+ sanitizeGroupName(name) {
8209
+ return name.toLowerCase().replace(/[^a-z0-9]/g, '-');
8210
8210
  }
8211
+ //#endregion
8212
+ //#region ---- Public Methods ----
8211
8213
  /**
8212
- * Handle removing a group
8213
- * Ensures at least 1 group always exists
8214
+ * Get the layout renderer component instance
8214
8215
  */
8215
- async handleGroupRemove(group) {
8216
- if (this.designerState().groups.length <= 1) {
8217
- return;
8218
- }
8219
- const confirmed = await this.dialogService.confirm(await this.translationService.translateAsync('@data-management:metadata-definitions.actions.delete-group.title'), await this.translationService.translateAsync('@data-management:metadata-definitions.components.meta-data-selector.dialogs.delete-group.message'), 'danger', 'horizontal', false);
8220
- if (confirmed) {
8221
- this.designerState.update((state) => {
8222
- const remainingGroups = state.groups.filter((g) => g.id !== group.id);
8223
- const finalGroups = remainingGroups.length > 0 ? remainingGroups : [createDefaultGroup()];
8224
- return {
8225
- ...state,
8226
- groups: finalGroups,
8227
- };
8228
- });
8229
- this.syncStateToValue();
8216
+ getLayoutRenderer() {
8217
+ return this.layoutRenderer();
8218
+ }
8219
+ /**
8220
+ * Validate the form
8221
+ */
8222
+ async validate() {
8223
+ const renderer = this.layoutRenderer();
8224
+ if (renderer) {
8225
+ const validation = await renderer.validate();
8226
+ return validation.result;
8230
8227
  }
8228
+ return false;
8231
8229
  }
8232
8230
  /**
8233
- * Handle group drag and drop
8231
+ * Get current form context
8234
8232
  */
8235
- handleGroupDrop(event) {
8236
- const groups = [...this.designerState().groups];
8237
- moveItemInArray$1(groups, event.previousIndex, event.currentIndex);
8238
- const updatedGroups = groups.map((group, index) => ({
8239
- ...group,
8240
- order: index,
8241
- }));
8242
- this.designerState.update((state) => ({
8243
- ...state,
8244
- groups: updatedGroups,
8245
- }));
8246
- this.syncStateToValue();
8233
+ getContext() {
8234
+ const renderer = this.layoutRenderer();
8235
+ return renderer ? renderer.getContext() : {};
8247
8236
  }
8248
- //#endregion
8249
- //#region ---- Field Management ----
8250
8237
  /**
8251
- * Handle adding fields to a group
8238
+ * Update form context programmatically
8252
8239
  */
8253
- async handleAddFieldToGroup(group) {
8254
- try {
8255
- const dataSource = new AXDataSource({
8256
- key: 'id',
8257
- pageSize: 20,
8258
- load: async (e) => {
8259
- const metaDataItems = await this.metaDataService.query(e);
8260
- return {
8261
- items: metaDataItems.items,
8262
- total: metaDataItems.total,
8263
- };
8264
- },
8265
- });
8266
- const categoryTreeDataSource = {
8267
- loadRootNodes: async () => {
8268
- const result = await this.metaDataService.getCategoriesList({
8269
- skip: 0,
8270
- take: 1000,
8271
- filter: {
8272
- field: 'parentId',
8273
- operator: { type: 'isEmpty' },
8274
- value: true,
8275
- },
8276
- });
8277
- return result.items.map((item) => ({
8278
- id: item.id,
8279
- title: item.title || item.name,
8280
- description: item.description || '',
8281
- parentId: item.parentId,
8282
- childrenCount: item.childrenCount || 0,
8283
- }));
8284
- },
8285
- loadChildNodes: async (parentId) => {
8286
- const result = await this.metaDataService.getCategoriesList({
8287
- skip: 0,
8288
- take: 1000,
8289
- filter: {
8290
- field: 'parentId',
8291
- operator: { type: 'equal' },
8292
- value: parentId,
8293
- },
8294
- });
8295
- return result.items.map((item) => ({
8296
- id: item.id,
8297
- title: item.title || item.name,
8298
- description: item.description || '',
8299
- parentId: item.parentId,
8300
- childrenCount: item.childrenCount || 0,
8301
- }));
8302
- },
8303
- searchNodes: async (searchValue) => {
8304
- const result = await this.metaDataService.getCategoriesList({
8305
- skip: 0,
8306
- take: 1000,
8307
- filter: {
8308
- filters: [
8309
- {
8310
- field: 'title',
8311
- operator: { type: 'contains' },
8312
- value: searchValue,
8313
- },
8314
- {
8315
- field: 'name',
8316
- operator: { type: 'contains' },
8317
- value: searchValue,
8318
- },
8319
- ],
8320
- logic: 'or',
8321
- },
8322
- });
8323
- return result.items.map((item) => ({
8324
- id: item.id,
8325
- title: item.title || item.name,
8326
- description: item.description || '',
8327
- parentId: item.parentId,
8328
- childrenCount: item.childrenCount || 0,
8329
- }));
8330
- },
8240
+ updateContext(context) {
8241
+ console.log('updateContext', context);
8242
+ const renderer = this.layoutRenderer();
8243
+ if (renderer) {
8244
+ renderer.updateContext(context);
8245
+ }
8246
+ }
8247
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataFormWidgetEditComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
8248
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: AXPMetaDataFormWidgetEditComponent, isStandalone: true, selector: "axp-meta-data-form-widget-edit", outputs: { contextChange: "contextChange", validityChange: "validityChange" }, viewQueries: [{ propertyName: "layoutRenderer", first: true, predicate: AXPLayoutRendererComponent, descendants: true, isSignal: true }], usesInheritance: true, ngImport: i0, template: `
8249
+ @if (hasDefinitions()) {
8250
+ <axp-layout-renderer
8251
+ [layout]="formDefinition()"
8252
+ [context]="getValue()"
8253
+ [look]="'container'"
8254
+ (contextChange)="onContextChange($event)"
8255
+ (validityChange)="onValidityChange($event)"
8256
+ >
8257
+ </axp-layout-renderer>
8258
+ } @else {
8259
+ <axp-state-message
8260
+ icon="fa-light fa-clipboard-list"
8261
+ [title]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.title'"
8262
+ [description]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.description'"
8263
+ >
8264
+ </axp-state-message>
8265
+ }
8266
+ `, isInline: true, dependencies: [{ kind: "component", type: AXPLayoutRendererComponent, selector: "axp-layout-renderer", inputs: ["layout", "context", "look", "mode"], outputs: ["contextChange", "contextInitiated", "validityChange"] }, { kind: "ngmodule", type: AXFormModule }, { kind: "ngmodule", type: AXLabelModule }, { kind: "ngmodule", type: AXPWidgetCoreModule }, { kind: "component", type: AXPStateMessageComponent, selector: "axp-state-message", inputs: ["mode", "icon", "title", "description", "variant"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
8267
+ }
8268
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataFormWidgetEditComponent, decorators: [{
8269
+ type: Component,
8270
+ args: [{ selector: 'axp-meta-data-form-widget-edit', template: `
8271
+ @if (hasDefinitions()) {
8272
+ <axp-layout-renderer
8273
+ [layout]="formDefinition()"
8274
+ [context]="getValue()"
8275
+ [look]="'container'"
8276
+ (contextChange)="onContextChange($event)"
8277
+ (validityChange)="onValidityChange($event)"
8278
+ >
8279
+ </axp-layout-renderer>
8280
+ } @else {
8281
+ <axp-state-message
8282
+ icon="fa-light fa-clipboard-list"
8283
+ [title]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.title'"
8284
+ [description]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.description'"
8285
+ >
8286
+ </axp-state-message>
8287
+ }
8288
+ `, changeDetection: ChangeDetectionStrategy.OnPush, imports: [AXPLayoutRendererComponent, AXFormModule, AXLabelModule, AXPWidgetCoreModule, AXPStateMessageComponent] }]
8289
+ }], propDecorators: { contextChange: [{ type: i0.Output, args: ["contextChange"] }], validityChange: [{ type: i0.Output, args: ["validityChange"] }], layoutRenderer: [{ type: i0.ViewChild, args: [i0.forwardRef(() => AXPLayoutRendererComponent), { isSignal: true }] }] } });
8290
+
8291
+ var metaDataFormEdit_component = /*#__PURE__*/Object.freeze({
8292
+ __proto__: null,
8293
+ AXPMetaDataFormWidgetEditComponent: AXPMetaDataFormWidgetEditComponent
8294
+ });
8295
+
8296
+ class ShowMetaDataFormPopupCommand {
8297
+ constructor() {
8298
+ this.layoutBuilder = inject(AXPLayoutBuilderService);
8299
+ this.translationService = inject(AXTranslationService);
8300
+ this.entityService = inject(AXPEntityService);
8301
+ this.entityRegistry = inject(AXPEntityDefinitionRegistryService);
8302
+ }
8303
+ async execute(input) {
8304
+ try {
8305
+ // Extract evaluated options from __context__ (private/controlled data)
8306
+ // The __context__.options contains evaluated expressions from entity actions
8307
+ const contextOptions = input.__context__?.options;
8308
+ // Merge root-level input with evaluated options from __context__
8309
+ // Root-level takes precedence if both exist
8310
+ const evaluatedInput = {
8311
+ ...contextOptions,
8312
+ ...input,
8313
+ // Ensure we use evaluated options from __context__ if available
8314
+ ...(contextOptions ? contextOptions : {}),
8331
8315
  };
8332
- const entity = await this.entityResolver.resolve(RootConfig.module.name, RootConfig.entities.metaDataDefinition.name);
8333
- if (!entity) {
8334
- throw new Error('Entity not found with name: ' + RootConfig.entities.metaDataDefinition.name);
8335
- }
8336
- const columns = entity.columns
8337
- ?.filter((column) => entity.properties.some((property) => property.name === column.name))
8338
- .map((column) => {
8339
- const property = entity.properties.find((prop) => prop.name === column.name);
8316
+ const { entity, id, field = META_DATA_FORM_FIELD, title, path } = evaluatedInput;
8317
+ if (!entity || !id) {
8340
8318
  return {
8341
- name: column.name,
8342
- title: property?.title ?? '',
8343
- visible: column.options?.visible !== false,
8344
- widget: {
8345
- type: column.showAs?.type ?? property?.schema?.interface?.type ?? 'text-editor',
8346
- options: column.showAs?.options ?? property?.schema?.interface?.options ?? {},
8319
+ success: false,
8320
+ message: {
8321
+ text: await this.translationService.translateAsync('@general:messages.entity.invalid-data'),
8347
8322
  },
8348
8323
  };
8349
- }) || [];
8350
- const result = await this.dataSelectorService.openWithCategoryFilter({
8351
- title: '@data-management:metadata-definitions.components.meta-data-selector.select-items',
8352
- dataSource: dataSource,
8353
- columns: columns,
8354
- selectionMode: 'multiple',
8355
- searchFields: [
8356
- { name: 'title', title: '@general:terms.common.title' },
8357
- { name: 'description', title: '@general:terms.common.description' },
8358
- ],
8359
- allowCreate: false,
8360
- }, {
8361
- title: '@data-management:metadata-definitions.components.meta-data-selector.categories',
8362
- dataSource: categoryTreeDataSource,
8363
- filterField: 'categoryIds',
8364
- filterOperator: 'contains',
8365
- width: '350px',
8366
- });
8367
- if (result?.items && result.items.length > 0) {
8368
- const newFields = result.items.map((item, index) => ({
8369
- id: AXPDataGenerator.uuid(),
8370
- name: item.name,
8371
- title: item.title,
8372
- description: item.description || '',
8373
- interface: typeof item.interface === 'string' ? item.interface : JSON.stringify(item.interface),
8374
- configuration: {
8375
- isRequired: false,
8376
- placeholder: '',
8377
- },
8378
- status: 'active',
8379
- order: group.fields.length + index,
8380
- isNewlyAdded: true,
8381
- }));
8382
- this.designerState.update((state) => ({
8383
- ...state,
8384
- groups: state.groups.map((g) => g.id === group.id
8385
- ? {
8386
- ...g,
8387
- fields: [...g.fields, ...newFields],
8388
- }
8389
- : g),
8390
- }));
8391
- this.syncStateToValue();
8392
8324
  }
8393
- }
8394
- catch (error) {
8395
- console.error('Error loading meta-data:', error);
8396
- }
8397
- }
8398
- /**
8399
- * Handle field editing - allows overriding the field's interface property
8400
- */
8401
- async handleFieldEdit(field) {
8402
- try {
8403
- let currentWidget;
8404
- if (typeof field.interface === 'string') {
8405
- if (!field.interface || field.interface.trim() === '') {
8406
- throw new Error('Field interface is empty');
8407
- }
8408
- try {
8409
- const parsed = JSON.parse(field.interface);
8410
- currentWidget = parsed;
8411
- }
8412
- catch (error) {
8413
- throw new Error(`Failed to parse field interface: ${error}`);
8325
+ // Ensure id is a string
8326
+ if (typeof id !== 'string' && id != null) {
8327
+ const stringId = String(id);
8328
+ if (stringId) {
8329
+ evaluatedInput.id = stringId;
8414
8330
  }
8415
8331
  }
8416
- else {
8417
- currentWidget = field.interface;
8418
- }
8419
- if (!currentWidget || !currentWidget.type) {
8420
- throw new Error('Invalid widget configuration: missing type');
8421
- }
8422
- const fieldName = field.title || field.name || 'Field';
8423
- const editTitle = await this.translationService.translateAsync('@general:actions.configure.title', {
8424
- params: { name: fieldName },
8425
- }) || `Configure ${fieldName}`;
8426
- const result = await this.widgetPropertyViewerService.open({
8427
- title: editTitle,
8428
- widget: cloneDeep(currentWidget),
8429
- mode: 'simple',
8430
- });
8431
- if (result && result.values) {
8432
- const updatedWidget = {
8433
- ...currentWidget,
8434
- ...result.values,
8435
- options: {
8436
- ...(currentWidget.options ?? {}),
8437
- ...(result.values.options ?? {}),
8332
+ if (!evaluatedInput.id || typeof evaluatedInput.id !== 'string') {
8333
+ return {
8334
+ success: false,
8335
+ message: {
8336
+ text: await this.translationService.translateAsync('@general:messages.entity.invalid-data'),
8438
8337
  },
8439
8338
  };
8440
- const updatedInterface = JSON.stringify(updatedWidget);
8441
- this.designerState.update((state) => ({
8442
- ...state,
8443
- groups: state.groups.map((group) => ({
8444
- ...group,
8445
- fields: group.fields.map((f) => f.id === field.id
8446
- ? {
8447
- ...f,
8448
- interface: updatedInterface,
8449
- }
8450
- : f),
8451
- })),
8452
- }));
8453
- this.syncStateToValue();
8454
8339
  }
8455
- }
8456
- catch (error) {
8457
- console.error('Error editing field interface:', error);
8458
- await this.dialogService.alert(await this.translationService.translateAsync('@general:messages.error.title') || 'Error', error instanceof Error ? error.message : 'Failed to edit field interface', 'danger');
8459
- }
8460
- }
8461
- /**
8462
- * Handle field removal
8463
- */
8464
- handleFieldRemove(field, groupId) {
8465
- this.designerState.update((state) => ({
8466
- ...state,
8467
- groups: state.groups.map((group) => {
8468
- if (group.id !== groupId)
8469
- return group;
8470
- if (field.isNewlyAdded) {
8471
- return {
8472
- ...group,
8473
- fields: group.fields.filter((f) => f.id !== field.id),
8474
- };
8475
- }
8476
- if (field.status === 'active') {
8477
- return {
8478
- ...group,
8479
- fields: group.fields.map((f) => (f.id === field.id ? { ...f, status: 'deleted' } : f)),
8480
- };
8481
- }
8340
+ const finalId = evaluatedInput.id;
8341
+ // Get current entity record to get the metadata expression value
8342
+ const [moduleName, entityName] = entity.split('.');
8343
+ const currentRecord = await this.findRecord(entity, finalId);
8344
+ if (!currentRecord) {
8482
8345
  return {
8483
- ...group,
8484
- fields: group.fields.filter((f) => f.id !== field.id),
8346
+ success: false,
8347
+ message: {
8348
+ text: await this.translationService.translateAsync('@general:messages.entity.not-found'),
8349
+ },
8485
8350
  };
8486
- }),
8487
- }));
8488
- this.syncStateToValue();
8489
- }
8490
- /**
8491
- * Handle field revert (undo deletion)
8492
- */
8493
- handleFieldRevert(field, groupId) {
8494
- this.designerState.update((state) => ({
8495
- ...state,
8496
- groups: state.groups.map((group) => group.id === groupId
8497
- ? {
8498
- ...group,
8499
- fields: group.fields.map((f) => (f.id === field.id ? { ...f, status: 'active' } : f)),
8500
- }
8501
- : group),
8502
- }));
8503
- this.syncStateToValue();
8504
- }
8505
- /**
8506
- * Handle field drag and drop (within and between groups)
8507
- */
8508
- handleFieldDrop(event, targetGroupName) {
8509
- const sourceGroupName = event.previousContainer.id.replace('group-', '').replace('-fields', '');
8510
- this.designerState.update((state) => {
8511
- const groups = [...state.groups];
8512
- const sourceGroup = groups.find((g) => g.name === sourceGroupName);
8513
- const targetGroup = groups.find((g) => g.name === targetGroupName);
8514
- if (!sourceGroup || !targetGroup)
8515
- return state;
8516
- if (event.previousContainer === event.container) {
8517
- const fields = [...sourceGroup.fields];
8518
- moveItemInArray$1(fields, event.previousIndex, event.currentIndex);
8519
- const updatedFields = fields.map((field, index) => ({
8520
- ...field,
8521
- order: index,
8522
- }));
8351
+ }
8352
+ // Note: pathValue might be null/undefined, but the metadata expression evaluator will handle it
8353
+ // The expression will return an empty array if pathValue is not available
8354
+ // Resolve entity to get metadata expression and determine if it's category or entity lookup
8355
+ const entityDef = await this.entityRegistry.resolve(moduleName, entityName);
8356
+ const metaDataFormExt = entityDef.extensions?.metaDataForm?.[field];
8357
+ if (!metaDataFormExt) {
8523
8358
  return {
8524
- ...state,
8525
- groups: groups.map((g) => (g.id === sourceGroup.id ? { ...g, fields: updatedFields } : g)),
8359
+ success: false,
8360
+ message: {
8361
+ text: await this.translationService.translateAsync('@data-management:metadata-definitions.messages.meta-data-form-not-configured'),
8362
+ },
8526
8363
  };
8527
8364
  }
8528
- else {
8529
- const sourceFields = [...sourceGroup.fields];
8530
- const targetFields = [...targetGroup.fields];
8531
- transferArrayItem(sourceFields, targetFields, event.previousIndex, event.currentIndex);
8532
- const updatedSourceFields = sourceFields.map((field, index) => ({
8533
- ...field,
8534
- order: index,
8535
- }));
8536
- const updatedTargetFields = targetFields.map((field, index) => ({
8537
- ...field,
8538
- order: index,
8539
- }));
8365
+ // Get path property to determine metadata source type
8366
+ const props = entityDef.properties || [];
8367
+ const pathProperty = props.find((p) => p.name === path);
8368
+ const targetEntity = pathProperty?.schema?.interface?.options?.['entity'];
8369
+ if (!targetEntity) {
8540
8370
  return {
8541
- ...state,
8542
- groups: groups.map((g) => {
8543
- if (g.id === sourceGroup.id)
8544
- return { ...g, fields: updatedSourceFields };
8545
- if (g.id === targetGroup.id)
8546
- return { ...g, fields: updatedTargetFields };
8547
- return g;
8548
- }),
8371
+ success: false,
8372
+ message: {
8373
+ text: await this.translationService.translateAsync('@data-management:metadata-definitions.messages.invalid-path-field'),
8374
+ },
8549
8375
  };
8550
8376
  }
8551
- });
8552
- this.syncStateToValue();
8553
- }
8554
- /**
8555
- * Get all group drop list IDs for connected drag & drop
8556
- */
8557
- getAllGroupDropLists() {
8558
- return this.groups().map((group) => `group-${group.name}-fields`);
8559
- }
8560
- //#endregion
8561
- //#region ---- Preview Mode ----
8562
- /**
8563
- * Handle preview button click - opens preview in a dialog using layout builder
8564
- */
8565
- async handlePreviewClick() {
8566
- if (this.isPreviewDisabled()) {
8567
- return;
8568
- }
8569
- try {
8570
- const previewTitle = await this.translationService.translateAsync('@data-management:metadata-definitions.actions.preview.title');
8571
- const formDef = this.previewFormDefinition();
8572
- if (!formDef.groups || formDef.groups.length === 0) {
8573
- const emptyDialogRef = await this.layoutBuilder
8574
- .create()
8575
- .dialog((dialog) => {
8576
- dialog
8577
- .setTitle(previewTitle)
8578
- .setSize('md')
8579
- .setCloseButton(true)
8580
- .setContext({})
8581
- .setActions((actions) => actions.cancel('@general:actions.close.title'));
8582
- })
8583
- .show();
8584
- emptyDialogRef.close();
8585
- return;
8377
+ // Build metadata expression based on target entity type
8378
+ let metadataExpression;
8379
+ if (targetEntity.endsWith('Category')) {
8380
+ // Category lookup - use fromCategory
8381
+ metadataExpression = `{{ metadata.fromCategory("${entity}", context.eval('${path}')) }}`;
8586
8382
  }
8587
- const dialogRef = await this.layoutBuilder
8383
+ else {
8384
+ // Relationship lookup - use fromEntity
8385
+ metadataExpression = `{{ metadata.fromEntity("${targetEntity}", context.eval('${path}')) }}`;
8386
+ }
8387
+ // Get current meta data form value
8388
+ const currentMetaDataValue = currentRecord[field] || {};
8389
+ // Build dialog title
8390
+ const dialogTitle = title || metaDataFormExt.title || await this.translationService.translateAsync('@data-management:metadata-definitions.components.meta-data-form.title');
8391
+ // Open dialog with meta-data-form-editor widget
8392
+ const result = await this.layoutBuilder
8588
8393
  .create()
8589
8394
  .dialog((dialog) => {
8590
8395
  dialog
8591
- .setTitle(previewTitle)
8396
+ .setTitle(dialogTitle)
8592
8397
  .setSize('lg')
8593
8398
  .setCloseButton(true)
8594
- .setContext(this.getValue() || {})
8595
- .content((layoutBuilder) => {
8596
- layoutBuilder.dynamicForm(formDef);
8399
+ .setContext({
8400
+ ...currentRecord,
8401
+ [field]: currentMetaDataValue,
8597
8402
  })
8598
- .setActions((actions) => actions.cancel('@general:actions.close.title'));
8403
+ .content((layout) => {
8404
+ layout.flex((flex) => {
8405
+ flex.setDirection('column').setGap('16px');
8406
+ // Add meta-data-form-editor widget with metadata expression
8407
+ flex.formField('', (fieldBuilder) => {
8408
+ fieldBuilder
8409
+ .path(field)
8410
+ .setShowLabel(false)
8411
+ .customWidget('meta-data-form-editor', {
8412
+ groups: metadataExpression,
8413
+ });
8414
+ });
8415
+ });
8416
+ })
8417
+ .setActions((actions) => {
8418
+ actions
8419
+ .cancel('@general:actions.cancel.title')
8420
+ .submit('@general:actions.save.title');
8421
+ })
8422
+ .onAction(async (dialogRef) => {
8423
+ const context = dialogRef.context();
8424
+ const action = dialogRef.action();
8425
+ if (!context || action === 'cancel') {
8426
+ return { success: false };
8427
+ }
8428
+ const updateData = {
8429
+ [field]: context[field],
8430
+ };
8431
+ const updated = await this.updateRecord(entity, finalId, updateData);
8432
+ return {
8433
+ success: true,
8434
+ data: updated,
8435
+ message: {
8436
+ text: await this.translationService.translateAsync('@general:messages.entity.updated'),
8437
+ },
8438
+ };
8439
+ });
8599
8440
  })
8600
8441
  .show();
8601
- await dialogRef.action();
8602
- dialogRef.close();
8442
+ return result;
8603
8443
  }
8604
8444
  catch (error) {
8605
- console.error('Error opening preview:', error);
8606
- await this.dialogService.alert((await this.translationService.translateAsync('@general:messages.error.title')) || 'Error', error instanceof Error ? error.message : 'Failed to open preview', 'danger');
8445
+ return {
8446
+ success: false,
8447
+ message: {
8448
+ text: error instanceof Error ? error.message : 'Failed to show meta data form popup',
8449
+ },
8450
+ };
8607
8451
  }
8608
8452
  }
8609
- //#endregion
8610
- //#region ---- Utility Methods ----
8453
+ //#region ---- Overridable Methods ----
8611
8454
  /**
8612
- * Sync internal state to external value
8613
- * Ensures at least 1 group always exists
8455
+ * Loads a record by entity and id. Override to use custom data sources or key handling.
8614
8456
  */
8615
- syncStateToValue() {
8616
- const currentState = this.designerState();
8617
- let groups = currentState.groups;
8618
- if (groups.length === 0) {
8619
- groups = [createDefaultGroup()];
8620
- this.designerState.update((state) => ({
8621
- ...state,
8622
- groups,
8623
- }));
8624
- }
8625
- const value = convertStateToValue({ ...currentState, groups });
8626
- this.setValue(value);
8457
+ findRecord(entity, id) {
8458
+ const dataAccessor = this.entityService.withEntity(entity).data();
8459
+ return dataAccessor.byKey(id);
8627
8460
  }
8628
8461
  /**
8629
- * Parse interface field to extract widget type
8462
+ * Persists meta-data form changes. Override to use custom persistence or validation.
8630
8463
  */
8631
- parseInterfaceType(interfaceValue) {
8632
- try {
8633
- if (!interfaceValue)
8634
- return 'text-editor';
8635
- // If it's already a string widget type
8636
- if (!interfaceValue.startsWith('{')) {
8637
- return interfaceValue;
8638
- }
8639
- // Try to parse as JSON
8640
- const parsed = JSON.parse(interfaceValue);
8641
- return parsed.type || 'text-editor';
8642
- }
8643
- catch {
8644
- return 'text-editor';
8645
- }
8646
- }
8647
- /**
8648
- * Get widget icon for a field
8649
- */
8650
- getWidgetIcon(interfaceValue) {
8651
- return 'fa-light fa-input-text';
8652
- }
8653
- /**
8654
- * Get widget title for a field
8655
- */
8656
- getWidgetTitle(interfaceValue) {
8657
- const widgetType = this.parseInterfaceType(interfaceValue);
8658
- return widgetType
8659
- .replace(/-/g, ' ')
8660
- .replace(/editor/gi, '')
8661
- .trim()
8662
- .split(' ')
8663
- .map((word) => word.charAt(0).toUpperCase() + word.slice(1))
8664
- .join(' ') || 'Text';
8464
+ updateRecord(entity, id, data) {
8465
+ const dataAccessor = this.entityService.withEntity(entity).data();
8466
+ return dataAccessor.update(id, data);
8665
8467
  }
8666
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetEditComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
8667
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: AXPMetaDataSelectorWidgetEditComponent, isStandalone: true, selector: "axp-meta-data-selector-widget-edit", usesInheritance: true, ngImport: i0, template: "<div class=\"axp-meta-data-selector-widget-edit\" *translate=\"let t\">\n @if (!readonly()) {\n <div class=\"__header\">\n <div class=\"__header-left\"></div>\n <div class=\"__header-right\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-group.title' | translate | async\" [color]=\"'primary'\"\n (onClick)=\"handleAddGroupClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-layer-group\"></ax-icon>\n </ax-prefix>\n </ax-button>\n\n <ax-button class=\"ax-sm\" [color]=\"'success'\" [disabled]=\"isPreviewDisabled()\"\n [text]=\"'@data-management:metadata-definitions.actions.preview.title' | translate | async\"\n (onClick)=\"handlePreviewClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-eye\"></ax-icon>\n </ax-prefix>\n </ax-button>\n </div>\n </div>\n }\n\n <div class=\"__content\">\n @if (groups().length === 0) {\n <axp-state-message icon=\"fa-light fa-layer-group\"\n [title]=\"'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.title'\"\n [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.description'\n \">\n </axp-state-message>\n } @else {\n <div class=\"__groups-container\" cdkDropList [cdkDropListData]=\"groups()\"\n (cdkDropListDropped)=\"handleGroupDrop($event)\">\n @for (group of groups(); track group.id) {\n <div class=\"__group\" cdkDrag [class.__default-group]=\"isDefaultGroup(group.name)\">\n <div class=\"__group-header\">\n @if (!readonly()) {\n <div class=\"__group-drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n }\n <div class=\"__group-info\">\n <h3 class=\"__group-title\">\n @if (group.title) {\n {{ group.title }}\n <span class=\"__group-name-prefix\">({{ group.name }})</span>\n } @else {\n {{ group.name }}\n }\n @if (isDefaultGroup(group.name) && !group.title) {\n <span class=\"__default-group-badge\">{{\n '@data-management:metadata-definitions.components.meta-data-selector.default-section-badge'\n | translate\n | async\n }}</span>\n }\n </h3>\n @if (group.description) {\n <p class=\"__group-description\">{{ group.description }}</p>\n }\n </div>\n @if (!readonly()) {\n <div class=\"__group-actions\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-field.title' | translate | async\"\n [color]=\"'accent2'\" (onClick)=\"handleAddFieldToGroup(group)\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-plus\"></ax-icon>\n </ax-prefix>\n </ax-button>\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleGroupEdit(group)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n @if (canDeleteGroup()) {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"danger\" (onClick)=\"handleGroupRemove(group)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n\n <div class=\"__fields-container\">\n <div class=\"__items-list\" cdkDropList [id]=\"'group-' + group.name + '-fields'\"\n [cdkDropListData]=\"group.fields\" [cdkDropListConnectedTo]=\"getAllGroupDropLists()\"\n (cdkDropListDropped)=\"handleFieldDrop($event, group.name)\">\n @if (group.fields.length === 0) {\n <axp-state-message icon=\"fa-light fa-inbox\" [title]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.title'\n \" [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.description'\n \">\n </axp-state-message>\n } @else { @for (field of group.fields; track field.id) {\n <div class=\"__field-item\" cdkDrag [class.__deleted]=\"field.status === 'deleted'\">\n <div class=\"__drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n\n <div class=\"__item-content\">\n <div class=\"__item-header\">\n <div class=\"__field-icon\">\n <ax-icon [icon]=\"getWidgetIcon(field.interface)\"></ax-icon>\n </div>\n <div class=\"__field-info\">\n <h4 class=\"__item-title\">{{ field.title }}</h4>\n <span class=\"__widget-type\">{{ getWidgetTitle(field.interface) }}</span>\n @if (field.description) {\n <p class=\"__field-description\">{{ field.description }}</p>\n }\n </div>\n </div>\n </div>\n\n @if (!readonly()) {\n <div class=\"__item-actions\">\n @if (field.status === 'deleted') {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"warning\"\n (onClick)=\"handleFieldRevert(field, group.id)\">\n <ax-icon class=\"fa-light fa-rotate-left\"></ax-icon>\n </ax-button>\n } @else {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleFieldEdit(field)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n\n <ax-button [look]=\"'blank'\" class=\"ax-sm\" color=\"danger\" (onClick)=\"handleFieldRemove(field, group.id)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n } }\n </div>\n </div>\n </div>\n }\n </div>\n }\n </div>\n</div>", styles: [".axp-meta-data-selector-widget-edit{display:flex;height:100%;width:100%;flex-direction:column}.axp-meta-data-selector-widget-edit .__header{display:flex;align-items:center;justify-content:space-between;gap:.75rem;border-bottom-width:1px;padding:.75rem}.axp-meta-data-selector-widget-edit .__header .__header-left,.axp-meta-data-selector-widget-edit .__header .__header-right{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__content{flex:1 1 0%;overflow:auto;padding:.75rem}.axp-meta-data-selector-widget-edit .__groups-container{display:flex;flex-direction:column;gap:1rem}.axp-meta-data-selector-widget-edit .__group{border-radius:.375rem;border-width:1px;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title{margin-bottom:.25rem;display:flex;align-items:center;gap:.5rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__group-name-prefix{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1));font-weight:300}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__default-group-badge{border-radius:.25rem;--tw-bg-opacity: 1;background-color:rgb(245 245 245 / var(--tw-bg-opacity, 1));padding:.25rem .5rem;font-size:.75rem;line-height:1rem;font-weight:400;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-actions{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__group .__fields-container{padding:1rem}.axp-meta-data-selector-widget-edit .__group .__fields-container .__items-list{gap:.75rem;min-height:3rem;display:flex;flex-direction:column}.axp-meta-data-selector-widget-edit .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));cursor:move;-webkit-user-select:none;user-select:none}.axp-meta-data-selector-widget-edit .__field-item:hover{--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__field-item.__deleted{opacity:.6;background-color:rgb(var(--ax-sys-color-danger-lightest-surface));color:rgb(var(--ax-sys-color-on-danger-lightest-surface));border-color:rgb(var(--ax-sys-color-border-danger-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item.__selected{--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab;transition:color .15s ease-in-out}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-actions{display:flex;gap:.5rem}.__group.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 10px 15px -3px rgb(0 0 0 / .1), 0 4px 6px -4px rgb(0 0 0 / .1);--tw-shadow-colored: 0 10px 15px -3px var(--tw-shadow-color), 0 4px 6px -4px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.__group.cdk-drag-preview .__group-info{flex:1 1 0%}.__group.cdk-drag-preview .__group-info .__group-title{margin-bottom:.25rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.__group.cdk-drag-preview .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-preview .__fields-container{padding:.75rem}.__group.cdk-drag-preview .__fields-container .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__field-icon{display:flex;height:2rem;width:2rem;align-items:center;justify-content:center;border-radius:.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content{flex:1 1 0%}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__item-title{margin-bottom:0;font-size:.875rem;line-height:1.25rem;font-weight:500}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__widget-type{font-size:.75rem;line-height:1rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-placeholder{border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));opacity:.5;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));margin-bottom:1rem;min-height:8rem}.__group.cdk-drag-dragging{opacity:.7}.__group:hover:not(.cdk-drag-dragging) .__group-drag-handle{--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 20px 25px -5px rgb(0 0 0 / .1), 0 8px 10px -6px rgb(0 0 0 / .1);--tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));display:flex;align-items:center;gap:.75rem;padding:.75rem;opacity:.9}.__field-item.cdk-drag-preview .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-placeholder{position:relative;border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));border-radius:.375rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));min-height:5rem;margin-bottom:.75rem;opacity:.5}.__field-item.cdk-drag-placeholder>*{opacity:0}.__field-item.cdk-drag-placeholder:before{content:\"\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));pointer-events:none}.__field-item.cdk-drag-animating{transition:transform .25s cubic-bezier(.4,0,.2,1)}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder){margin-bottom:.75rem}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__items-list.cdk-drop-list-dragging{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-dragging axp-state-message{display:none}.__items-list.cdk-drop-list-dragging:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__items-list.cdk-drop-list-receiving{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-receiving axp-state-message{display:none}.__items-list.cdk-drop-list-receiving:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder){margin-bottom:1rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__groups-container.cdk-drop-list-dragging:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__groups-container.cdk-drop-list-receiving:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: AXButtonModule }, { kind: "component", type: i2$1.AXButtonComponent, selector: "ax-button", inputs: ["disabled", "size", "tabIndex", "color", "look", "text", "toggleable", "selected", "iconOnly", "type", "loadingText"], outputs: ["onBlur", "onFocus", "onClick", "selectedChange", "toggleableChange", "lookChange", "colorChange", "disabledChange", "loadingTextChange"] }, { kind: "ngmodule", type: AXDecoratorModule }, { kind: "component", type: i5.AXDecoratorIconComponent, selector: "ax-icon", inputs: ["icon"] }, { kind: "component", type: i5.AXDecoratorGenericComponent, selector: "ax-footer, ax-header, ax-content, ax-divider, ax-form-hint, ax-prefix, ax-suffix, ax-text, ax-title, ax-subtitle, ax-placeholder, ax-overlay" }, { kind: "ngmodule", type: AXFormModule }, { kind: "ngmodule", type: AXTranslationModule }, { kind: "directive", type: i7.AXTranslatorDirective, selector: "[translate]" }, { kind: "component", type: AXPStateMessageComponent, selector: "axp-state-message", inputs: ["mode", "icon", "title", "description", "variant"] }, { kind: "directive", type: CdkDropList, selector: "[cdkDropList], cdk-drop-list", inputs: ["cdkDropListConnectedTo", "cdkDropListData", "cdkDropListOrientation", "id", "cdkDropListLockAxis", "cdkDropListDisabled", "cdkDropListSortingDisabled", "cdkDropListEnterPredicate", "cdkDropListSortPredicate", "cdkDropListAutoScrollDisabled", "cdkDropListAutoScrollStep", "cdkDropListElementContainer", "cdkDropListHasAnchor"], outputs: ["cdkDropListDropped", "cdkDropListEntered", "cdkDropListExited", "cdkDropListSorted"], exportAs: ["cdkDropList"] }, { kind: "directive", type: CdkDrag, selector: "[cdkDrag]", inputs: ["cdkDragData", "cdkDragLockAxis", "cdkDragRootElement", "cdkDragBoundary", "cdkDragStartDelay", "cdkDragFreeDragPosition", "cdkDragDisabled", "cdkDragConstrainPosition", "cdkDragPreviewClass", "cdkDragPreviewContainer", "cdkDragScale"], outputs: ["cdkDragStarted", "cdkDragReleased", "cdkDragEnded", "cdkDragEntered", "cdkDragExited", "cdkDragDropped", "cdkDragMoved"], exportAs: ["cdkDrag"] }, { kind: "directive", type: CdkDragHandle, selector: "[cdkDragHandle]", inputs: ["cdkDragHandleDisabled"] }, { kind: "pipe", type: i6.AsyncPipe, name: "async" }, { kind: "pipe", type: i7.AXTranslatorPipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
8468
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
8469
+ static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, providedIn: 'root' }); }
8668
8470
  }
8669
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetEditComponent, decorators: [{
8670
- type: Component,
8671
- args: [{ selector: 'axp-meta-data-selector-widget-edit', changeDetection: ChangeDetectionStrategy.OnPush, imports: [
8672
- CommonModule,
8673
- AXButtonModule,
8674
- AXDecoratorModule,
8675
- AXFormModule,
8676
- AXTranslationModule,
8677
- AXPStateMessageComponent,
8678
- CdkDropList,
8679
- CdkDrag,
8680
- CdkDragHandle,
8681
- ], template: "<div class=\"axp-meta-data-selector-widget-edit\" *translate=\"let t\">\n @if (!readonly()) {\n <div class=\"__header\">\n <div class=\"__header-left\"></div>\n <div class=\"__header-right\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-group.title' | translate | async\" [color]=\"'primary'\"\n (onClick)=\"handleAddGroupClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-layer-group\"></ax-icon>\n </ax-prefix>\n </ax-button>\n\n <ax-button class=\"ax-sm\" [color]=\"'success'\" [disabled]=\"isPreviewDisabled()\"\n [text]=\"'@data-management:metadata-definitions.actions.preview.title' | translate | async\"\n (onClick)=\"handlePreviewClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-eye\"></ax-icon>\n </ax-prefix>\n </ax-button>\n </div>\n </div>\n }\n\n <div class=\"__content\">\n @if (groups().length === 0) {\n <axp-state-message icon=\"fa-light fa-layer-group\"\n [title]=\"'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.title'\"\n [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.description'\n \">\n </axp-state-message>\n } @else {\n <div class=\"__groups-container\" cdkDropList [cdkDropListData]=\"groups()\"\n (cdkDropListDropped)=\"handleGroupDrop($event)\">\n @for (group of groups(); track group.id) {\n <div class=\"__group\" cdkDrag [class.__default-group]=\"isDefaultGroup(group.name)\">\n <div class=\"__group-header\">\n @if (!readonly()) {\n <div class=\"__group-drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n }\n <div class=\"__group-info\">\n <h3 class=\"__group-title\">\n @if (group.title) {\n {{ group.title }}\n <span class=\"__group-name-prefix\">({{ group.name }})</span>\n } @else {\n {{ group.name }}\n }\n @if (isDefaultGroup(group.name) && !group.title) {\n <span class=\"__default-group-badge\">{{\n '@data-management:metadata-definitions.components.meta-data-selector.default-section-badge'\n | translate\n | async\n }}</span>\n }\n </h3>\n @if (group.description) {\n <p class=\"__group-description\">{{ group.description }}</p>\n }\n </div>\n @if (!readonly()) {\n <div class=\"__group-actions\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-field.title' | translate | async\"\n [color]=\"'accent2'\" (onClick)=\"handleAddFieldToGroup(group)\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-plus\"></ax-icon>\n </ax-prefix>\n </ax-button>\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleGroupEdit(group)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n @if (canDeleteGroup()) {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"danger\" (onClick)=\"handleGroupRemove(group)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n\n <div class=\"__fields-container\">\n <div class=\"__items-list\" cdkDropList [id]=\"'group-' + group.name + '-fields'\"\n [cdkDropListData]=\"group.fields\" [cdkDropListConnectedTo]=\"getAllGroupDropLists()\"\n (cdkDropListDropped)=\"handleFieldDrop($event, group.name)\">\n @if (group.fields.length === 0) {\n <axp-state-message icon=\"fa-light fa-inbox\" [title]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.title'\n \" [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.description'\n \">\n </axp-state-message>\n } @else { @for (field of group.fields; track field.id) {\n <div class=\"__field-item\" cdkDrag [class.__deleted]=\"field.status === 'deleted'\">\n <div class=\"__drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n\n <div class=\"__item-content\">\n <div class=\"__item-header\">\n <div class=\"__field-icon\">\n <ax-icon [icon]=\"getWidgetIcon(field.interface)\"></ax-icon>\n </div>\n <div class=\"__field-info\">\n <h4 class=\"__item-title\">{{ field.title }}</h4>\n <span class=\"__widget-type\">{{ getWidgetTitle(field.interface) }}</span>\n @if (field.description) {\n <p class=\"__field-description\">{{ field.description }}</p>\n }\n </div>\n </div>\n </div>\n\n @if (!readonly()) {\n <div class=\"__item-actions\">\n @if (field.status === 'deleted') {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"warning\"\n (onClick)=\"handleFieldRevert(field, group.id)\">\n <ax-icon class=\"fa-light fa-rotate-left\"></ax-icon>\n </ax-button>\n } @else {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleFieldEdit(field)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n\n <ax-button [look]=\"'blank'\" class=\"ax-sm\" color=\"danger\" (onClick)=\"handleFieldRemove(field, group.id)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n } }\n </div>\n </div>\n </div>\n }\n </div>\n }\n </div>\n</div>", styles: [".axp-meta-data-selector-widget-edit{display:flex;height:100%;width:100%;flex-direction:column}.axp-meta-data-selector-widget-edit .__header{display:flex;align-items:center;justify-content:space-between;gap:.75rem;border-bottom-width:1px;padding:.75rem}.axp-meta-data-selector-widget-edit .__header .__header-left,.axp-meta-data-selector-widget-edit .__header .__header-right{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__content{flex:1 1 0%;overflow:auto;padding:.75rem}.axp-meta-data-selector-widget-edit .__groups-container{display:flex;flex-direction:column;gap:1rem}.axp-meta-data-selector-widget-edit .__group{border-radius:.375rem;border-width:1px;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title{margin-bottom:.25rem;display:flex;align-items:center;gap:.5rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__group-name-prefix{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1));font-weight:300}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__default-group-badge{border-radius:.25rem;--tw-bg-opacity: 1;background-color:rgb(245 245 245 / var(--tw-bg-opacity, 1));padding:.25rem .5rem;font-size:.75rem;line-height:1rem;font-weight:400;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-actions{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__group .__fields-container{padding:1rem}.axp-meta-data-selector-widget-edit .__group .__fields-container .__items-list{gap:.75rem;min-height:3rem;display:flex;flex-direction:column}.axp-meta-data-selector-widget-edit .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));cursor:move;-webkit-user-select:none;user-select:none}.axp-meta-data-selector-widget-edit .__field-item:hover{--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__field-item.__deleted{opacity:.6;background-color:rgb(var(--ax-sys-color-danger-lightest-surface));color:rgb(var(--ax-sys-color-on-danger-lightest-surface));border-color:rgb(var(--ax-sys-color-border-danger-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item.__selected{--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab;transition:color .15s ease-in-out}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-actions{display:flex;gap:.5rem}.__group.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 10px 15px -3px rgb(0 0 0 / .1), 0 4px 6px -4px rgb(0 0 0 / .1);--tw-shadow-colored: 0 10px 15px -3px var(--tw-shadow-color), 0 4px 6px -4px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.__group.cdk-drag-preview .__group-info{flex:1 1 0%}.__group.cdk-drag-preview .__group-info .__group-title{margin-bottom:.25rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.__group.cdk-drag-preview .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-preview .__fields-container{padding:.75rem}.__group.cdk-drag-preview .__fields-container .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__field-icon{display:flex;height:2rem;width:2rem;align-items:center;justify-content:center;border-radius:.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content{flex:1 1 0%}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__item-title{margin-bottom:0;font-size:.875rem;line-height:1.25rem;font-weight:500}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__widget-type{font-size:.75rem;line-height:1rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-placeholder{border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));opacity:.5;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));margin-bottom:1rem;min-height:8rem}.__group.cdk-drag-dragging{opacity:.7}.__group:hover:not(.cdk-drag-dragging) .__group-drag-handle{--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 20px 25px -5px rgb(0 0 0 / .1), 0 8px 10px -6px rgb(0 0 0 / .1);--tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));display:flex;align-items:center;gap:.75rem;padding:.75rem;opacity:.9}.__field-item.cdk-drag-preview .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-placeholder{position:relative;border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));border-radius:.375rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));min-height:5rem;margin-bottom:.75rem;opacity:.5}.__field-item.cdk-drag-placeholder>*{opacity:0}.__field-item.cdk-drag-placeholder:before{content:\"\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));pointer-events:none}.__field-item.cdk-drag-animating{transition:transform .25s cubic-bezier(.4,0,.2,1)}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder){margin-bottom:.75rem}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__items-list.cdk-drop-list-dragging{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-dragging axp-state-message{display:none}.__items-list.cdk-drop-list-dragging:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__items-list.cdk-drop-list-receiving{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-receiving axp-state-message{display:none}.__items-list.cdk-drop-list-receiving:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder){margin-bottom:1rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__groups-container.cdk-drop-list-dragging:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__groups-container.cdk-drop-list-receiving:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}\n"] }]
8471
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, decorators: [{
8472
+ type: Injectable,
8473
+ args: [{
8474
+ providedIn: 'root',
8475
+ }]
8682
8476
  }] });
8683
8477
 
8684
- var metaDataSelectorEdit_component = /*#__PURE__*/Object.freeze({
8478
+ var showMetaDataFormPopup_command = /*#__PURE__*/Object.freeze({
8685
8479
  __proto__: null,
8686
- AXPMetaDataSelectorWidgetEditComponent: AXPMetaDataSelectorWidgetEditComponent
8480
+ ShowMetaDataFormPopupCommand: ShowMetaDataFormPopupCommand
8687
8481
  });
8688
8482
 
8689
- function normalizeSelectorDisplayConfig(display, defaultTitle) {
8690
- if (!display)
8691
- return { section: { enabled: true } };
8692
- if (typeof display === 'object')
8693
- return display;
8694
- switch (display) {
8695
- case 'section':
8696
- return { section: { enabled: true, title: defaultTitle }, popup: { enabled: false } };
8697
- case 'popup':
8698
- return { section: { enabled: false }, popup: { enabled: true, title: defaultTitle } };
8699
- case 'both':
8700
- return { section: { enabled: true, title: defaultTitle }, popup: { enabled: true, title: defaultTitle } };
8701
- default:
8702
- return { section: { enabled: true } };
8483
+ const AXPMetaDataSelectorWidget = {
8484
+ name: 'meta-data-selector-editor',
8485
+ title: '@data-management:metadata-definitions.components.meta-data-selector.title',
8486
+ categories: AXP_WIDGETS_EDITOR_CATEGORY,
8487
+ groups: [AXPWidgetGroupEnum.UtilityWidget],
8488
+ description: '@data-management:metadata-definitions.components.meta-data-selector.description',
8489
+ icon: 'fa-light fa-list-check',
8490
+ defaultFilterWidgetName: 'string-filter',
8491
+ type: 'editor',
8492
+ options: {
8493
+ needLabel: false,
8494
+ },
8495
+ properties: [
8496
+ AXP_NAME_PROPERTY,
8497
+ AXP_DATA_PATH_PROPERTY,
8498
+ ],
8499
+ components: {
8500
+ view: {
8501
+ component: () => Promise.resolve().then(function () { return metaDataSelectorView_component; }).then((c) => c.AXPMetaDataSelectorWidgetViewComponent),
8502
+ },
8503
+ edit: {
8504
+ component: () => Promise.resolve().then(function () { return metaDataSelectorEdit_component; }).then((c) => c.AXPMetaDataSelectorWidgetEditComponent),
8505
+ },
8506
+ print: {
8507
+ component: () => Promise.resolve().then(function () { return metaDataSelectorEdit_component; }).then((c) => c.AXPMetaDataSelectorWidgetEditComponent),
8508
+ },
8509
+ },
8510
+ };
8511
+
8512
+ //#region ---- Meta-Data Selector Field Types ----
8513
+ //#endregion
8514
+ //#region ---- Utility Functions ----
8515
+ /**
8516
+ * Convert raw value to designer state
8517
+ */
8518
+ function convertValueToState(value) {
8519
+ // Handle null/undefined
8520
+ if (!value) {
8521
+ return {
8522
+ groups: [createDefaultGroup()],
8523
+ mode: 'designer',
8524
+ };
8525
+ }
8526
+ // Handle old structure (flat array) - no longer supported but graceful fallback
8527
+ if (Array.isArray(value)) {
8528
+ return {
8529
+ groups: [
8530
+ {
8531
+ id: 'group-default',
8532
+ name: 'default',
8533
+ title: 'Default Section',
8534
+ description: undefined,
8535
+ order: 0,
8536
+ fields: value.map((item, index) => ({
8537
+ id: item.id || `field-${index}`,
8538
+ name: item.name,
8539
+ title: item.title,
8540
+ description: item.description,
8541
+ interface: item.interface,
8542
+ configuration: item.configuration,
8543
+ status: item.status || 'active',
8544
+ order: item.order ?? index,
8545
+ isNewlyAdded: item.isNewlyAdded,
8546
+ })),
8547
+ },
8548
+ ],
8549
+ mode: 'designer',
8550
+ };
8551
+ }
8552
+ // Handle new structure (groups)
8553
+ if (value.groups && Array.isArray(value.groups)) {
8554
+ const groups = value.groups.map((group, groupIndex) => ({
8555
+ id: group.id || `group-${group.name}`,
8556
+ name: group.name,
8557
+ title: group.title,
8558
+ description: group.description,
8559
+ order: group.order ?? groupIndex,
8560
+ fields: (group.fields || []).map((field, fieldIndex) => ({
8561
+ id: field.id || `field-${fieldIndex}`,
8562
+ name: field.name,
8563
+ title: field.title,
8564
+ description: field.description,
8565
+ interface: field.interface,
8566
+ configuration: field.configuration,
8567
+ status: field.status || 'active',
8568
+ order: field.order ?? fieldIndex,
8569
+ isNewlyAdded: field.isNewlyAdded,
8570
+ })),
8571
+ isNewlyAdded: group.isNewlyAdded,
8572
+ }));
8573
+ // Ensure at least 1 group exists
8574
+ const finalGroups = groups.length > 0 ? groups : [createDefaultGroup()];
8575
+ return {
8576
+ groups: finalGroups,
8577
+ mode: 'designer',
8578
+ };
8703
8579
  }
8580
+ // Fallback to default
8581
+ return {
8582
+ groups: [createDefaultGroup()],
8583
+ mode: 'designer',
8584
+ };
8704
8585
  }
8705
8586
  /**
8706
- * meta-data-selector plugin
8707
- *
8708
- * Dynamic behavior:
8709
- * - Creates a single property for metadata selector configuration
8710
- * - Dynamically generates entity groups and meta-data-form widgets based on configured groups
8711
- * - Each metadata group becomes a separate entity section with its own meta-data-form widget
8712
- * - Reads group configuration at runtime from the field value
8587
+ * Convert designer state to value for persistence
8713
8588
  */
8714
- const metaDataSelectorPlugin = {
8715
- name: 'meta-data-selector',
8716
- order: 60,
8717
- apply: (ctx, options) => {
8718
- const opts = options ?? {};
8719
- const field = META_DATA_SELECTOR_FIELD;
8720
- // Try to get title from various sources in priority order:
8721
- // 1. Direct options.title
8722
- // 2. meta-data-form plugin configuration (from plugins array - current entity or base entity)
8723
- // 3. meta-data-form extension (if plugin has already run - current entity or base entity)
8724
- // 4. category plugin metaData.title (if enabled via category plugin)
8725
- // 5. Default title
8726
- let metaDataFormTitle;
8727
- let metaDataFormExtTitle;
8728
- let categoryMetaDataTitle;
8729
- // Check current entity's plugins and extensions
8730
- const plugins = ctx.entity.plugins;
8731
- const metaDataFormPlugin = plugins?.find((p) => p.name === 'meta-data-form');
8732
- metaDataFormTitle = metaDataFormPlugin?.options?.title;
8733
- const metaDataFormExt = ctx.entity.extensions?.metaDataForm;
8734
- metaDataFormExtTitle = metaDataFormExt
8735
- ? Object.values(metaDataFormExt).find((ext) => ext?.title)
8736
- : undefined;
8737
- const categoryExt = ctx.entity.extensions?.category;
8738
- categoryMetaDataTitle = categoryExt?.metaData?.title;
8739
- // If running on a category entity (name ends with "Category"), check the base entity
8740
- if (ctx.entity.name.endsWith('Category') && !metaDataFormTitle && !metaDataFormExtTitle) {
8741
- const baseEntityName = ctx.entity.name.replace('Category', '');
8742
- try {
8743
- // Try to access the entity registry to get base entity
8744
- // Note: This requires the registry to be available, which might not always be the case
8745
- // For now, we'll rely on the category extension which should have the title
8746
- // But we can also check if there's a way to access base entity plugins
8747
- }
8748
- catch (error) {
8749
- // Silently fail - we'll use other sources
8750
- }
8751
- }
8752
- // Priority: 1. options.title, 2. meta-data-form plugin title, 3. meta-data-form extension title, 4. category metaData.title, 5. default
8753
- const displayTitle = (opts.title && opts.title.trim().length > 0)
8754
- ? opts.title
8755
- : (metaDataFormTitle && metaDataFormTitle.trim().length > 0)
8756
- ? metaDataFormTitle
8757
- : (metaDataFormExtTitle?.title && metaDataFormExtTitle.title.trim().length > 0)
8758
- ? metaDataFormExtTitle.title
8759
- : (categoryMetaDataTitle && categoryMetaDataTitle.trim().length > 0)
8760
- ? categoryMetaDataTitle
8761
- : '@data-management:metadata-definitions.actions.configure-meta-data.title';
8762
- const displayConfig = normalizeSelectorDisplayConfig(opts.display, displayTitle);
8763
- const sectionConfig = displayConfig.section ?? {};
8764
- const popupConfig = displayConfig.popup ?? {};
8765
- const showSection = sectionConfig.enabled !== false;
8766
- const showPopup = popupConfig.enabled === true;
8767
- const popupTitle = popupConfig.title ?? displayTitle;
8768
- //#region ---- Step 1: Create Meta-Data Selector Property ----
8769
- // Ensure group and section for the selector configuration itself
8770
- const selectorSectionId = `meta-data-config`;
8771
- const selectorGroupId = `meta-data-config`;
8772
- const existingGroups = ctx.groups.list() ?? [];
8773
- if (!existingGroups.some((g) => g.id === selectorGroupId)) {
8774
- ctx.groups.add({ id: selectorGroupId, title: displayTitle });
8775
- }
8776
- // Ensure property exists (using meta-data-selector-editor interface)
8777
- const props = ctx.properties.list();
8778
- if (!props.some((p) => p.name === field)) {
8779
- ctx.properties.add({
8780
- name: field,
8781
- title: displayTitle,
8782
- groupId: selectorGroupId,
8783
- schema: {
8784
- dataType: 'object',
8785
- interface: {
8786
- type: 'meta-data-selector-editor',
8787
- },
8788
- },
8589
+ function convertStateToValue(state) {
8590
+ return {
8591
+ groups: state.groups.map((group) => {
8592
+ // Filter deleted fields only
8593
+ const activeFields = group.fields.filter((field) => field.status !== 'deleted');
8594
+ // Explicitly include only the properties defined in AXMMetaDataSelectorValue
8595
+ // This ensures isNewlyAdded and other internal properties are not included
8596
+ return {
8597
+ name: group.name,
8598
+ title: group.title,
8599
+ description: group.description,
8600
+ order: group.order,
8601
+ fields: activeFields.map((field) => {
8602
+ // Explicitly include only the properties defined in AXMMetaDataSelectorValue
8603
+ // This ensures isNewlyAdded, status, and other internal properties are not included
8604
+ return {
8605
+ id: field.id,
8606
+ name: field.name,
8607
+ title: field.title,
8608
+ description: field.description,
8609
+ interface: field.interface,
8610
+ configuration: field.configuration,
8611
+ order: field.order,
8612
+ };
8613
+ }),
8614
+ };
8615
+ }),
8616
+ };
8617
+ }
8618
+ /**
8619
+ * Create a default group
8620
+ */
8621
+ function createDefaultGroup() {
8622
+ return {
8623
+ id: 'group-default',
8624
+ name: 'default',
8625
+ title: 'Default Section',
8626
+ description: undefined,
8627
+ order: 0,
8628
+ fields: [],
8629
+ isNewlyAdded: true,
8630
+ };
8631
+ }
8632
+ //#endregion
8633
+
8634
+ class AXPMetaDataSelectorWidgetEditComponent extends AXPValueWidgetComponent {
8635
+ constructor() {
8636
+ super(...arguments);
8637
+ //#region ---- Services & Dependencies ----
8638
+ this.dataSelectorService = inject(AXPDataSelectorService);
8639
+ this.metaDataService = inject(AXMMetaDataDefinitionService);
8640
+ this.entityResolver = inject(AXPEntityDefinitionRegistryService);
8641
+ this.dialogService = inject(AXDialogService);
8642
+ this.translationService = inject(AXTranslationService);
8643
+ this.layoutBuilder = inject(AXPLayoutBuilderService);
8644
+ this.widgetPropertyViewerService = inject(AXPWidgetPropertyViewerService);
8645
+ //#endregion
8646
+ //#region ---- Class Properties ----
8647
+ this.DEFAULT_GROUP_NAME = 'default';
8648
+ this.designerState = signal({
8649
+ groups: [createDefaultGroup()],
8650
+ mode: 'designer',
8651
+ }, ...(ngDevMode ? [{ debugName: "designerState" }] : []));
8652
+ //#endregion
8653
+ //#region ---- Computed Properties ----
8654
+ /**
8655
+ * Check if the widget is in readonly mode
8656
+ */
8657
+ this.readonly = computed(() => this.options()['readonly'], ...(ngDevMode ? [{ debugName: "readonly" }] : []));
8658
+ /**
8659
+ * Check if a group is the default group
8660
+ */
8661
+ this.isDefaultGroup = (groupName) => {
8662
+ return groupName === this.DEFAULT_GROUP_NAME;
8663
+ };
8664
+ /**
8665
+ * Check if we can delete a group (more than 1 group exists)
8666
+ */
8667
+ this.canDeleteGroup = computed(() => {
8668
+ return this.designerState().groups.length > 1;
8669
+ }, ...(ngDevMode ? [{ debugName: "canDeleteGroup" }] : []));
8670
+ /**
8671
+ * Disable preview when no groups or all groups are empty
8672
+ */
8673
+ this.isPreviewDisabled = computed(() => {
8674
+ const groups = this.designerState().groups || [];
8675
+ if (groups.length === 0) {
8676
+ return true;
8677
+ }
8678
+ // Check if all groups have no active fields
8679
+ const hasAnyActiveFields = groups.some((group) => group.fields.some((field) => field.status === 'active'));
8680
+ return !hasAnyActiveFields;
8681
+ }, ...(ngDevMode ? [{ debugName: "isPreviewDisabled" }] : []));
8682
+ /**
8683
+ * Get all groups for rendering
8684
+ */
8685
+ this.groups = computed(() => this.designerState().groups, ...(ngDevMode ? [{ debugName: "groups" }] : []));
8686
+ /**
8687
+ * Get groups data formatted for meta-data-form component (only active fields)
8688
+ */
8689
+ this.previewGroups = computed(() => {
8690
+ return this.groups()
8691
+ .map((group) => ({
8692
+ name: group.name,
8693
+ title: group.title,
8694
+ description: group.description,
8695
+ fields: group.fields
8696
+ .filter((field) => field.status === 'active')
8697
+ .sort((a, b) => a.order - b.order)
8698
+ .map((field) => ({
8699
+ name: field.name,
8700
+ title: field.title,
8701
+ description: field.description,
8702
+ interface: field.interface,
8703
+ configuration: field.configuration,
8704
+ defaultValue: field.configuration?.['defaultValue'],
8705
+ })),
8706
+ }))
8707
+ .filter((group) => group.fields.length > 0);
8708
+ }, ...(ngDevMode ? [{ debugName: "previewGroups" }] : []));
8709
+ /**
8710
+ * Convert preview groups to form definition for layout renderer
8711
+ */
8712
+ this.previewFormDefinition = computed(() => {
8713
+ const groups = this.previewGroups();
8714
+ const formGroups = [];
8715
+ groups.forEach((group) => {
8716
+ const fields = group.fields || [];
8717
+ const validFields = fields.filter((field) => field != null);
8718
+ if (validFields.length > 0) {
8719
+ const parameters = validFields.map((field) => this.convertFieldToFormDefinition(field));
8720
+ formGroups.push({
8721
+ name: this.sanitizeGroupName(group.name || 'default'),
8722
+ title: group.title || group.name,
8723
+ description: group.description,
8724
+ look: groups.length > 1 ? 'group' : 'container',
8725
+ parameters,
8726
+ });
8727
+ }
8789
8728
  });
8729
+ return { groups: formGroups };
8730
+ }, ...(ngDevMode ? [{ debugName: "previewFormDefinition" }] : []));
8731
+ //#endregion
8732
+ //#region ---- Lifecycle & Effects ----
8733
+ /**
8734
+ * Sync external value changes to internal state
8735
+ */
8736
+ this.#syncValueToState = effect(() => {
8737
+ const value = this.getValue();
8738
+ const newState = convertValueToState(value);
8739
+ this.designerState.set(newState);
8740
+ }, ...(ngDevMode ? [{ debugName: "#syncValueToState" }] : []));
8741
+ /**
8742
+ * Effect to handle status changes and cleanup before submission
8743
+ */
8744
+ this.#statusChanged = effect(() => {
8745
+ if (this.layoutService.status() === AXPPageStatus.Submitting) {
8746
+ const currentState = this.designerState();
8747
+ const cleanedValue = convertStateToValue(currentState);
8748
+ this.setValue(cleanedValue);
8749
+ }
8750
+ }, ...(ngDevMode ? [{ debugName: "#statusChanged" }] : []));
8751
+ }
8752
+ /**
8753
+ * Convert a field to form field definition
8754
+ */
8755
+ convertFieldToFormDefinition(field) {
8756
+ const interfaceConfig = this.parseInterfaceConfig(field.interface);
8757
+ const defaultValue = field.defaultValue ?? field.configuration?.defaultValue;
8758
+ const description = field.description ?? field.configuration?.description;
8759
+ return {
8760
+ path: field.name || 'unnamed',
8761
+ title: field.title || 'Untitled Field',
8762
+ description: description,
8763
+ widget: {
8764
+ type: interfaceConfig.type || 'text-editor',
8765
+ path: field.name || 'unnamed',
8766
+ options: {
8767
+ ...interfaceConfig.options,
8768
+ defaultValue: defaultValue,
8769
+ readonly: true,
8770
+ validations: this.parseValidations(field.interface),
8771
+ },
8772
+ },
8773
+ };
8774
+ }
8775
+ /**
8776
+ * Parse interface configuration from metadata
8777
+ */
8778
+ parseInterfaceConfig(interfaceValue) {
8779
+ if (typeof interfaceValue === 'string') {
8780
+ try {
8781
+ return JSON.parse(interfaceValue || '{}');
8782
+ }
8783
+ catch (error) {
8784
+ console.warn('Failed to parse interface config:', interfaceValue, error);
8785
+ return {};
8786
+ }
8790
8787
  }
8791
- // Add selector to single/create/modify views only when section display is enabled
8792
- const selectorColSpan = 12;
8793
- if (showSection) {
8794
- ctx.interfaces.master.single.update((single) => {
8795
- const next = single ?? { title: ctx.entity.title, sections: [], properties: [] };
8796
- next.sections = next.sections ?? [];
8797
- if (!next.sections.some((s) => s.id === selectorSectionId)) {
8798
- next.sections.push({
8799
- id: selectorSectionId,
8800
- title: sectionConfig.title ?? displayTitle,
8801
- order: sectionConfig.order ?? 200,
8802
- });
8788
+ return interfaceValue || {};
8789
+ }
8790
+ /**
8791
+ * Parse validations from interface configuration
8792
+ */
8793
+ parseValidations(interfaceValue) {
8794
+ const config = this.parseInterfaceConfig(interfaceValue);
8795
+ return config.options?.validations || [];
8796
+ }
8797
+ /**
8798
+ * Sanitize group name for use as identifier
8799
+ */
8800
+ sanitizeGroupName(name) {
8801
+ return name.toLowerCase().replace(/[^a-z0-9]/g, '-');
8802
+ }
8803
+ //#endregion
8804
+ //#region ---- Lifecycle & Effects ----
8805
+ /**
8806
+ * Sync external value changes to internal state
8807
+ */
8808
+ #syncValueToState;
8809
+ /**
8810
+ * Effect to handle status changes and cleanup before submission
8811
+ */
8812
+ #statusChanged;
8813
+ //#endregion
8814
+ //#region ---- Group Management ----
8815
+ /**
8816
+ * Handle adding a new group
8817
+ */
8818
+ async handleAddGroupClick() {
8819
+ await this.layoutBuilder
8820
+ .create()
8821
+ .dialog((dialog) => {
8822
+ dialog
8823
+ .setTitle('@data-management:metadata-definitions.actions.add-group.title')
8824
+ .setContext({ title: '', description: '' })
8825
+ .content((flex) => {
8826
+ flex
8827
+ .setDirection('column')
8828
+ .formField('@general:terms.common.title', (field) => {
8829
+ field.path('title');
8830
+ field.textBox({ validations: [{ rule: 'required' }] });
8831
+ })
8832
+ .formField('@general:terms.common.description', (field) => {
8833
+ field.path('description');
8834
+ field.largeTextBox({});
8835
+ });
8836
+ })
8837
+ .setActions((actions) => {
8838
+ actions.cancel('@general:actions.cancel.title').submit('@general:actions.save.title');
8839
+ })
8840
+ .onAction(async (dialogRef) => {
8841
+ const context = dialogRef.context();
8842
+ const action = dialogRef.action();
8843
+ if (!context || action === 'cancel') {
8844
+ return;
8803
8845
  }
8804
- next.properties = next.properties ?? [];
8805
- if (!next.properties.some((p) => p.name === field)) {
8806
- next.properties.push({
8807
- name: field,
8808
- layout: {
8809
- label: { visible: false },
8810
- positions: { lg: { colSpan: selectorColSpan, order: 9 } },
8811
- },
8812
- });
8846
+ const form = context;
8847
+ if (form.title?.trim()) {
8848
+ const newGroup = {
8849
+ id: AXPDataGenerator.uuid(),
8850
+ name: generateKebabCase(form.title),
8851
+ title: form.title,
8852
+ description: form.description || undefined,
8853
+ order: this.designerState().groups.length,
8854
+ fields: [],
8855
+ isNewlyAdded: true,
8856
+ };
8857
+ this.designerState.update((state) => ({
8858
+ ...state,
8859
+ groups: [...state.groups, newGroup],
8860
+ }));
8861
+ this.syncStateToValue();
8813
8862
  }
8814
- return next;
8815
8863
  });
8816
- ctx.interfaces.master.create.update((create) => {
8817
- const next = create ?? { sections: [], properties: [] };
8818
- next.sections = next.sections ?? [];
8819
- if (!next.sections.some((s) => s.id === selectorSectionId)) {
8820
- next.sections.push({
8821
- id: selectorSectionId,
8822
- title: sectionConfig.title ?? displayTitle,
8823
- });
8864
+ })
8865
+ .show();
8866
+ }
8867
+ /**
8868
+ * Handle editing a group
8869
+ */
8870
+ async handleGroupEdit(group) {
8871
+ await this.layoutBuilder
8872
+ .create()
8873
+ .dialog((dialog) => {
8874
+ dialog
8875
+ .setTitle('@data-management:metadata-definitions.actions.edit-group.title')
8876
+ .setContext({ title: group.title || group.name, description: group.description || '' })
8877
+ .content((flex) => {
8878
+ flex
8879
+ .setDirection('column')
8880
+ .formField('@general:terms.common.title', (field) => {
8881
+ field.path('title');
8882
+ field.textBox({ validations: [{ rule: 'required' }] });
8883
+ })
8884
+ .formField('@general:terms.common.description', (field) => {
8885
+ field.path('description');
8886
+ field.largeTextBox({});
8887
+ });
8888
+ })
8889
+ .setActions((actions) => {
8890
+ actions.cancel('@general:actions.cancel.title').submit('@general:actions.save.title');
8891
+ })
8892
+ .onAction(async (dialogRef) => {
8893
+ const context = dialogRef.context();
8894
+ const action = dialogRef.action();
8895
+ if (!context || action === 'cancel') {
8896
+ return;
8824
8897
  }
8825
- next.properties = next.properties ?? [];
8826
- if (!next.properties.some((p) => p.name === field)) {
8827
- next.properties.push({
8828
- name: field,
8829
- layout: {
8830
- label: { visible: false },
8831
- positions: { lg: { colSpan: selectorColSpan, order: 7 } },
8832
- },
8833
- });
8898
+ const form = context;
8899
+ if (form.title?.trim()) {
8900
+ this.designerState.update((state) => ({
8901
+ ...state,
8902
+ groups: state.groups.map((g) => g.id === group.id
8903
+ ? {
8904
+ ...g,
8905
+ name: generateKebabCase(form.title),
8906
+ title: form.title,
8907
+ description: form.description || undefined,
8908
+ }
8909
+ : g),
8910
+ }));
8911
+ this.syncStateToValue();
8834
8912
  }
8835
- return next;
8836
8913
  });
8837
- ctx.interfaces.master.modify.update((modify) => {
8838
- const next = modify ?? { sections: [], properties: [] };
8839
- next.sections = next.sections ?? [];
8840
- if (!next.sections.some((s) => s.id === selectorSectionId)) {
8841
- next.sections.push({
8842
- id: selectorSectionId,
8843
- title: sectionConfig.title ?? displayTitle,
8844
- });
8845
- }
8846
- next.properties = next.properties ?? [];
8847
- if (!next.properties.some((p) => p.name === field)) {
8848
- next.properties.push({
8849
- name: field,
8850
- layout: {
8851
- label: { visible: false },
8852
- positions: { lg: { colSpan: selectorColSpan, order: 7 } },
8853
- },
8854
- });
8855
- }
8856
- return next;
8914
+ })
8915
+ .show();
8916
+ }
8917
+ /**
8918
+ * Handle removing a group
8919
+ * Ensures at least 1 group always exists
8920
+ */
8921
+ async handleGroupRemove(group) {
8922
+ if (this.designerState().groups.length <= 1) {
8923
+ return;
8924
+ }
8925
+ const confirmed = await this.dialogService.confirm(await this.translationService.translateAsync('@data-management:metadata-definitions.actions.delete-group.title'), await this.translationService.translateAsync('@data-management:metadata-definitions.components.meta-data-selector.dialogs.delete-group.message'), 'danger', 'horizontal', false);
8926
+ if (confirmed) {
8927
+ this.designerState.update((state) => {
8928
+ const remainingGroups = state.groups.filter((g) => g.id !== group.id);
8929
+ const finalGroups = remainingGroups.length > 0 ? remainingGroups : [createDefaultGroup()];
8930
+ return {
8931
+ ...state,
8932
+ groups: finalGroups,
8933
+ };
8857
8934
  });
8935
+ this.syncStateToValue();
8858
8936
  }
8859
- //#endregion
8860
- //#region ---- Step 2: Dynamic Group Generation Middleware ----
8861
- // Add metadata middleware to dynamically generate groups at runtime
8862
- // This middleware reads the metaDataList field value and creates
8863
- // entity groups + meta-data-form widgets for each configured group
8864
- const metadataMiddleware = {
8865
- name: 'metadata-dynamic-groups',
8866
- order: 100,
8867
- apply: (entityCtx) => {
8868
- // Get the metadata selector value from context
8869
- const metaDataValue = entityCtx.data?.[field];
8870
- if (!metaDataValue?.groups || metaDataValue.groups.length === 0) {
8871
- return; // No groups configured, skip
8872
- }
8873
- // TODO: Implement renderGroupsAsSections option
8874
- // If opts.renderGroupsAsSections === true:
8875
- // - Create separate entity sections for each metadata group
8876
- // - Each section gets its own meta-data-form widget with only that group's fields
8877
- // If opts.renderGroupsAsSections === false (default):
8878
- // - Create single section with all groups (current behavior)
8879
- // - Single meta-data-form widget receives all groups, renders them as cards
8880
- // Current implementation: renderGroupsAsSections = false (default)
8881
- // Create a single section and single meta-data-form widget for all groups
8882
- const sectionId = 'metadata-section';
8883
- const formFieldName = META_DATA_FORM_FIELD;
8884
- const groupId = 'metadata-group';
8885
- // Ensure entity group exists
8886
- if (!entityCtx.groups.list().some((g) => g.id === groupId)) {
8887
- entityCtx.groups.add({
8888
- id: groupId,
8889
- title: displayTitle,
8890
- });
8891
- }
8892
- // Ensure meta-data-form property exists with all groups
8893
- // Always update the property to ensure groups are passed correctly
8894
- const existingProp = entityCtx.properties.list().find((p) => p.name === formFieldName);
8895
- const groupsData = metaDataValue.groups.map((group) => ({
8896
- name: group.name,
8897
- title: group.title,
8898
- description: group.description,
8899
- fields: group.fields,
8900
- }));
8901
- if (!existingProp) {
8902
- entityCtx.properties.add({
8903
- name: formFieldName,
8904
- title: displayTitle,
8905
- groupId: groupId,
8906
- schema: {
8907
- dataType: 'object',
8908
- interface: {
8909
- type: 'meta-data-form-editor',
8910
- options: {
8911
- // Pass all groups so the form can render them as separate groups
8912
- groups: groupsData,
8913
- },
8914
- },
8937
+ }
8938
+ /**
8939
+ * Handle group drag and drop
8940
+ */
8941
+ handleGroupDrop(event) {
8942
+ const groups = [...this.designerState().groups];
8943
+ moveItemInArray$1(groups, event.previousIndex, event.currentIndex);
8944
+ const updatedGroups = groups.map((group, index) => ({
8945
+ ...group,
8946
+ order: index,
8947
+ }));
8948
+ this.designerState.update((state) => ({
8949
+ ...state,
8950
+ groups: updatedGroups,
8951
+ }));
8952
+ this.syncStateToValue();
8953
+ }
8954
+ //#endregion
8955
+ //#region ---- Field Management ----
8956
+ /**
8957
+ * Handle adding fields to a group
8958
+ */
8959
+ async handleAddFieldToGroup(group) {
8960
+ try {
8961
+ const dataSource = new AXDataSource({
8962
+ key: 'id',
8963
+ pageSize: 20,
8964
+ load: async (e) => {
8965
+ const metaDataItems = await this.metaDataService.query(e);
8966
+ return {
8967
+ items: metaDataItems.items,
8968
+ total: metaDataItems.total,
8969
+ };
8970
+ },
8971
+ });
8972
+ const categoryTreeDataSource = {
8973
+ loadRootNodes: async () => {
8974
+ const result = await this.metaDataService.getCategoriesList({
8975
+ skip: 0,
8976
+ take: 1000,
8977
+ filter: {
8978
+ field: 'parentId',
8979
+ operator: { type: 'isEmpty' },
8980
+ value: true,
8915
8981
  },
8916
8982
  });
8917
- }
8918
- else {
8919
- // Update existing property to ensure groups are set
8920
- if (existingProp.schema?.interface?.options) {
8921
- existingProp.schema.interface.options.groups = groupsData;
8922
- }
8923
- }
8924
- // Add to single view - single section
8925
- entityCtx.interfaces.master.single.update((single) => {
8926
- const next = single ?? { title: entityCtx.entity.title, sections: [], properties: [] };
8927
- next.sections = next.sections ?? [];
8928
- if (!next.sections.some((s) => s.id === sectionId)) {
8929
- next.sections.push({
8930
- id: sectionId,
8931
- title: displayTitle,
8932
- order: 300,
8933
- });
8934
- }
8935
- next.properties = next.properties ?? [];
8936
- if (!next.properties.some((p) => p.name === formFieldName)) {
8937
- next.properties.push({
8938
- name: formFieldName,
8939
- layout: {
8940
- label: { visible: false },
8941
- positions: { lg: { colSpan: 12, order: 0 } },
8942
- },
8943
- });
8944
- }
8945
- return next;
8946
- });
8947
- // Add to create view - single section
8948
- entityCtx.interfaces.master.create.update((create) => {
8949
- const next = create ?? { sections: [], properties: [] };
8950
- next.sections = next.sections ?? [];
8951
- if (!next.sections.some((s) => s.id === sectionId)) {
8952
- next.sections.push({
8953
- id: sectionId,
8954
- title: displayTitle,
8955
- });
8956
- }
8957
- next.properties = next.properties ?? [];
8958
- if (!next.properties.some((p) => p.name === formFieldName)) {
8959
- next.properties.push({
8960
- name: formFieldName,
8961
- layout: {
8962
- label: { visible: false },
8963
- positions: { lg: { colSpan: 12, order: 10 } },
8964
- },
8965
- });
8966
- }
8967
- return next;
8968
- });
8969
- // Add to modify view - single section
8970
- entityCtx.interfaces.master.modify.update((modify) => {
8971
- const next = modify ?? { sections: [], properties: [] };
8972
- next.sections = next.sections ?? [];
8973
- if (!next.sections.some((s) => s.id === sectionId)) {
8974
- next.sections.push({
8975
- id: sectionId,
8976
- title: displayTitle,
8977
- });
8978
- }
8979
- next.properties = next.properties ?? [];
8980
- if (!next.properties.some((p) => p.name === formFieldName)) {
8981
- next.properties.push({
8982
- name: formFieldName,
8983
- layout: {
8984
- label: { visible: false },
8985
- positions: { lg: { colSpan: 12, order: 10 } },
8986
- },
8987
- });
8988
- }
8989
- return next;
8990
- });
8991
- },
8992
- };
8993
- // Register the middleware (if middleware system exists)
8994
- // Note: This is conceptual - actual implementation depends on platform capabilities
8995
- // (ctx as any).middleware?.add?.(metadataMiddleware);
8996
- //#endregion
8997
- //#region ---- Step 3: Popup actions (when display is popup or both) ----
8998
- if (showPopup) {
8999
- const actionName = `show-meta-data-selector-popup-${field}`;
9000
- const commandName = 'show-meta-data-selector-popup';
9001
- ctx.interfaces.master.single.update((single) => {
9002
- const next = single ?? { title: ctx.entity.title, sections: [], properties: [], actions: [] };
9003
- next.actions = next.actions ?? [];
9004
- if (!actionExists(next.actions, commandName, actionName)) {
9005
- next.actions.push({
9006
- name: actionName,
9007
- title: popupTitle,
9008
- command: {
9009
- name: commandName,
9010
- options: {
9011
- entity: `${ctx.entity.module}.${ctx.entity.name}`,
9012
- id: '{{ context.eval("id") }}',
9013
- field,
9014
- title: popupTitle,
9015
- },
8983
+ return result.items.map((item) => ({
8984
+ id: item.id,
8985
+ title: item.title || item.name,
8986
+ description: item.description || '',
8987
+ parentId: item.parentId,
8988
+ childrenCount: item.childrenCount || 0,
8989
+ }));
8990
+ },
8991
+ loadChildNodes: async (parentId) => {
8992
+ const result = await this.metaDataService.getCategoriesList({
8993
+ skip: 0,
8994
+ take: 1000,
8995
+ filter: {
8996
+ field: 'parentId',
8997
+ operator: { type: 'equal' },
8998
+ value: parentId,
9016
8999
  },
9017
- priority: 'secondary',
9018
- type: 'configure',
9019
- icon: 'fa-light fa-list-check',
9020
- scope: AXPEntityCommandScope.Individual,
9021
9000
  });
9022
- }
9023
- return next;
9024
- });
9025
- ctx.interfaces.master.list.update((list) => {
9026
- const next = list ?? { actions: [], views: [] };
9027
- next.actions = next.actions ?? [];
9028
- if (!actionExists(next.actions, commandName, actionName)) {
9029
- next.actions.push({
9030
- name: actionName,
9031
- title: popupTitle,
9032
- command: {
9033
- name: commandName,
9034
- options: {
9035
- entity: `${ctx.entity.module}.${ctx.entity.name}`,
9036
- id: '{{ context.eval("id") }}',
9037
- field,
9038
- title: popupTitle,
9039
- },
9001
+ return result.items.map((item) => ({
9002
+ id: item.id,
9003
+ title: item.title || item.name,
9004
+ description: item.description || '',
9005
+ parentId: item.parentId,
9006
+ childrenCount: item.childrenCount || 0,
9007
+ }));
9008
+ },
9009
+ searchNodes: async (searchValue) => {
9010
+ const result = await this.metaDataService.getCategoriesList({
9011
+ skip: 0,
9012
+ take: 1000,
9013
+ filter: {
9014
+ filters: [
9015
+ {
9016
+ field: 'title',
9017
+ operator: { type: 'contains' },
9018
+ value: searchValue,
9019
+ },
9020
+ {
9021
+ field: 'name',
9022
+ operator: { type: 'contains' },
9023
+ value: searchValue,
9024
+ },
9025
+ ],
9026
+ logic: 'or',
9040
9027
  },
9041
- priority: 'secondary',
9042
- type: 'configure',
9043
- icon: 'fa-light fa-list-check',
9044
- scope: AXPEntityCommandScope.Individual,
9045
9028
  });
9046
- }
9047
- return next;
9029
+ return result.items.map((item) => ({
9030
+ id: item.id,
9031
+ title: item.title || item.name,
9032
+ description: item.description || '',
9033
+ parentId: item.parentId,
9034
+ childrenCount: item.childrenCount || 0,
9035
+ }));
9036
+ },
9037
+ };
9038
+ const entity = await this.entityResolver.resolve(RootConfig.module.name, RootConfig.entities.metaDataDefinition.name);
9039
+ if (!entity) {
9040
+ throw new Error('Entity not found with name: ' + RootConfig.entities.metaDataDefinition.name);
9041
+ }
9042
+ const columns = entity.columns
9043
+ ?.filter((column) => entity.properties.some((property) => property.name === column.name))
9044
+ .map((column) => {
9045
+ const property = entity.properties.find((prop) => prop.name === column.name);
9046
+ return {
9047
+ name: column.name,
9048
+ title: property?.title ?? '',
9049
+ visible: column.options?.visible !== false,
9050
+ widget: {
9051
+ type: column.showAs?.type ?? property?.schema?.interface?.type ?? 'text-editor',
9052
+ options: column.showAs?.options ?? property?.schema?.interface?.options ?? {},
9053
+ },
9054
+ };
9055
+ }) || [];
9056
+ const result = await this.dataSelectorService.openWithCategoryFilter({
9057
+ title: '@data-management:metadata-definitions.components.meta-data-selector.select-items',
9058
+ dataSource: dataSource,
9059
+ columns: columns,
9060
+ selectionMode: 'multiple',
9061
+ searchFields: [
9062
+ { name: 'title', title: '@general:terms.common.title' },
9063
+ { name: 'description', title: '@general:terms.common.description' },
9064
+ ],
9065
+ allowCreate: false,
9066
+ }, {
9067
+ title: '@data-management:metadata-definitions.components.meta-data-selector.categories',
9068
+ dataSource: categoryTreeDataSource,
9069
+ filterField: 'categoryIds',
9070
+ filterOperator: 'contains',
9071
+ width: '350px',
9048
9072
  });
9073
+ if (result?.items && result.items.length > 0) {
9074
+ const newFields = result.items.map((item, index) => ({
9075
+ id: AXPDataGenerator.uuid(),
9076
+ name: item.name,
9077
+ title: item.title,
9078
+ description: item.description || '',
9079
+ interface: typeof item.interface === 'string' ? item.interface : JSON.stringify(item.interface),
9080
+ configuration: {
9081
+ isRequired: false,
9082
+ placeholder: '',
9083
+ },
9084
+ status: 'active',
9085
+ order: group.fields.length + index,
9086
+ isNewlyAdded: true,
9087
+ }));
9088
+ this.designerState.update((state) => ({
9089
+ ...state,
9090
+ groups: state.groups.map((g) => g.id === group.id
9091
+ ? {
9092
+ ...g,
9093
+ fields: [...g.fields, ...newFields],
9094
+ }
9095
+ : g),
9096
+ }));
9097
+ this.syncStateToValue();
9098
+ }
9049
9099
  }
9050
- //#endregion
9051
- //#region ---- Step 4: Extension Metadata ----
9052
- // Stamp normalized config for middleware
9053
- ctx.entity.extensions ??= {};
9054
- ctx.entity.extensions.metaDataSelector ??= {};
9055
- ctx.entity.extensions.metaDataSelector[field] = {
9056
- title: displayTitle,
9057
- display: displayConfig,
9058
- };
9059
- //#endregion
9060
- },
9061
- };
9062
-
9063
- class AXPMetaDataSelectorWidgetViewComponent extends AXPValueWidgetComponent {
9100
+ catch (error) {
9101
+ console.error('Error loading meta-data:', error);
9102
+ }
9103
+ }
9064
9104
  /**
9065
- * Returns a comma-separated list of selected meta titles.
9066
- * Extracting this logic into a getter keeps the template simple and
9067
- * avoids using arrow functions, which are not allowed in Angular
9068
- * interpolation expressions.
9105
+ * Handle field editing - allows overriding the field's interface property
9069
9106
  */
9070
- get display() {
9071
- const val = this.getValue();
9072
- return Array.isArray(val) ? val.map((v) => v.title || v.text).join(', ') : '';
9073
- }
9074
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetViewComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
9075
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.16", type: AXPMetaDataSelectorWidgetViewComponent, isStandalone: true, selector: "axp-meta-data-selector-widget-view", usesInheritance: true, ngImport: i0, template: `<span>{{ display }}</span>`, isInline: true, dependencies: [{ kind: "ngmodule", type: AXDecoratorModule }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9076
- }
9077
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetViewComponent, decorators: [{
9078
- type: Component,
9079
- args: [{
9080
- selector: 'axp-meta-data-selector-widget-view',
9081
- template: `<span>{{ display }}</span>`,
9082
- changeDetection: ChangeDetectionStrategy.OnPush,
9083
- imports: [AXDecoratorModule],
9084
- }]
9085
- }] });
9086
-
9087
- var metaDataSelectorView_component = /*#__PURE__*/Object.freeze({
9088
- __proto__: null,
9089
- AXPMetaDataSelectorWidgetViewComponent: AXPMetaDataSelectorWidgetViewComponent
9090
- });
9091
-
9092
- /**
9093
- * Opens the meta-data-selector (configuration UI for groups/fields) in a popup.
9094
- * Used when meta-data-selector plugin has display: 'popup' or 'both'.
9095
- */
9096
- class ShowMetaDataSelectorPopupCommand {
9097
- constructor() {
9098
- this.layoutBuilder = inject(AXPLayoutBuilderService);
9099
- this.translationService = inject(AXTranslationService);
9100
- this.entityService = inject(AXPEntityService);
9101
- }
9102
- async execute(input) {
9107
+ async handleFieldEdit(field) {
9103
9108
  try {
9104
- const contextOptions = input.__context__?.options;
9105
- const evaluatedInput = {
9106
- ...contextOptions,
9107
- ...input,
9108
- ...(contextOptions ? contextOptions : {}),
9109
- };
9110
- const { entity, id, field = META_DATA_SELECTOR_FIELD, title, } = evaluatedInput;
9111
- if (!entity || !id) {
9112
- return {
9113
- success: false,
9114
- message: {
9115
- text: await this.translationService.translateAsync('@general:messages.entity.invalid-data'),
9116
- },
9117
- };
9109
+ let currentWidget;
9110
+ if (typeof field.interface === 'string') {
9111
+ if (!field.interface || field.interface.trim() === '') {
9112
+ throw new Error('Field interface is empty');
9113
+ }
9114
+ try {
9115
+ const parsed = JSON.parse(field.interface);
9116
+ currentWidget = parsed;
9117
+ }
9118
+ catch (error) {
9119
+ throw new Error(`Failed to parse field interface: ${error}`);
9120
+ }
9118
9121
  }
9119
- const finalId = typeof id === 'string' ? id : String(id);
9120
- if (!finalId) {
9121
- return {
9122
- success: false,
9123
- message: {
9124
- text: await this.translationService.translateAsync('@general:messages.entity.invalid-data'),
9125
- },
9126
- };
9122
+ else {
9123
+ currentWidget = field.interface;
9127
9124
  }
9128
- const currentRecord = await this.findRecord(entity, finalId);
9129
- if (!currentRecord) {
9130
- return {
9131
- success: false,
9132
- message: {
9133
- text: await this.translationService.translateAsync('@general:messages.entity.not-found'),
9125
+ if (!currentWidget || !currentWidget.type) {
9126
+ throw new Error('Invalid widget configuration: missing type');
9127
+ }
9128
+ const fieldName = field.title || field.name || 'Field';
9129
+ const editTitle = await this.translationService.translateAsync('@general:actions.configure.title', {
9130
+ params: { name: fieldName },
9131
+ }) || `Configure ${fieldName}`;
9132
+ const result = await this.widgetPropertyViewerService.open({
9133
+ title: editTitle,
9134
+ widget: cloneDeep(currentWidget),
9135
+ mode: 'simple',
9136
+ });
9137
+ if (result && result.values) {
9138
+ const updatedWidget = {
9139
+ ...currentWidget,
9140
+ ...result.values,
9141
+ options: {
9142
+ ...(currentWidget.options ?? {}),
9143
+ ...(result.values.options ?? {}),
9134
9144
  },
9135
9145
  };
9146
+ const updatedInterface = JSON.stringify(updatedWidget);
9147
+ this.designerState.update((state) => ({
9148
+ ...state,
9149
+ groups: state.groups.map((group) => ({
9150
+ ...group,
9151
+ fields: group.fields.map((f) => f.id === field.id
9152
+ ? {
9153
+ ...f,
9154
+ interface: updatedInterface,
9155
+ }
9156
+ : f),
9157
+ })),
9158
+ }));
9159
+ this.syncStateToValue();
9136
9160
  }
9137
- const currentSelectorValue = currentRecord[field] ?? { groups: [] };
9138
- const dialogTitle = title ??
9139
- (await this.translationService.translateAsync('@data-management:metadata-definitions.actions.configure-meta-data.title'));
9140
- const result = await this.layoutBuilder
9141
- .create()
9142
- .dialog((dialog) => {
9143
- dialog
9144
- .setTitle(dialogTitle)
9145
- .setSize('lg')
9146
- .setCloseButton(true)
9147
- .setContext({
9148
- ...currentRecord,
9149
- [field]: currentSelectorValue,
9150
- })
9151
- .content((layout) => {
9152
- layout.flex((flex) => {
9153
- flex.setDirection('column').setGap('16px');
9154
- flex.formField('', (fieldBuilder) => {
9155
- fieldBuilder
9156
- .path(field)
9157
- .setShowLabel(false)
9158
- .customWidget('meta-data-selector-editor', {});
9159
- });
9160
- });
9161
- })
9162
- .setActions((actions) => {
9163
- actions
9164
- .cancel('@general:actions.cancel.title')
9165
- .submit('@general:actions.save.title');
9166
- })
9167
- .onAction(async (dialogRef) => {
9168
- const context = dialogRef.context();
9169
- const action = dialogRef.action();
9170
- if (!context || action === 'cancel') {
9171
- return { success: false };
9172
- }
9173
- const updateData = { [field]: context[field] };
9174
- const updated = await this.updateRecord(entity, finalId, updateData);
9175
- return {
9176
- success: true,
9177
- data: updated,
9178
- message: {
9179
- text: await this.translationService.translateAsync('@general:messages.entity.updated'),
9180
- },
9181
- };
9182
- });
9183
- })
9184
- .show();
9185
- return result;
9186
9161
  }
9187
9162
  catch (error) {
9188
- return {
9189
- success: false,
9190
- message: {
9191
- text: error instanceof Error
9192
- ? error.message
9193
- : 'Failed to show meta data selector popup',
9194
- },
9195
- };
9163
+ console.error('Error editing field interface:', error);
9164
+ await this.dialogService.alert(await this.translationService.translateAsync('@general:messages.error.title') || 'Error', error instanceof Error ? error.message : 'Failed to edit field interface', 'danger');
9196
9165
  }
9197
9166
  }
9198
- //#region ---- Overridable Methods ----
9199
9167
  /**
9200
- * Loads a record by entity and id. Override to use custom data sources or key handling.
9168
+ * Handle field removal
9201
9169
  */
9202
- findRecord(entity, id) {
9203
- const dataAccessor = this.entityService.withEntity(entity).data();
9204
- return dataAccessor.byKey(id);
9170
+ handleFieldRemove(field, groupId) {
9171
+ this.designerState.update((state) => ({
9172
+ ...state,
9173
+ groups: state.groups.map((group) => {
9174
+ if (group.id !== groupId)
9175
+ return group;
9176
+ if (field.isNewlyAdded) {
9177
+ return {
9178
+ ...group,
9179
+ fields: group.fields.filter((f) => f.id !== field.id),
9180
+ };
9181
+ }
9182
+ if (field.status === 'active') {
9183
+ return {
9184
+ ...group,
9185
+ fields: group.fields.map((f) => (f.id === field.id ? { ...f, status: 'deleted' } : f)),
9186
+ };
9187
+ }
9188
+ return {
9189
+ ...group,
9190
+ fields: group.fields.filter((f) => f.id !== field.id),
9191
+ };
9192
+ }),
9193
+ }));
9194
+ this.syncStateToValue();
9205
9195
  }
9206
9196
  /**
9207
- * Persists meta-data changes. Override to use custom persistence or validation.
9197
+ * Handle field revert (undo deletion)
9208
9198
  */
9209
- updateRecord(entity, id, data) {
9210
- const dataAccessor = this.entityService.withEntity(entity).data();
9211
- return dataAccessor.update(id, data);
9199
+ handleFieldRevert(field, groupId) {
9200
+ this.designerState.update((state) => ({
9201
+ ...state,
9202
+ groups: state.groups.map((group) => group.id === groupId
9203
+ ? {
9204
+ ...group,
9205
+ fields: group.fields.map((f) => (f.id === field.id ? { ...f, status: 'active' } : f)),
9206
+ }
9207
+ : group),
9208
+ }));
9209
+ this.syncStateToValue();
9212
9210
  }
9213
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
9214
- static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, providedIn: 'root' }); }
9215
- }
9216
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, decorators: [{
9217
- type: Injectable,
9218
- args: [{
9219
- providedIn: 'root',
9220
- }]
9221
- }] });
9222
-
9223
- var showMetaDataSelectorPopup_command = /*#__PURE__*/Object.freeze({
9224
- __proto__: null,
9225
- ShowMetaDataSelectorPopupCommand: ShowMetaDataSelectorPopupCommand
9226
- });
9227
-
9228
- const AXPMetaDataFormWidget = {
9229
- name: 'meta-data-form-editor',
9230
- title: '@data-management:metadata-definitions.components.meta-data-form.title',
9231
- categories: AXP_WIDGETS_EDITOR_CATEGORY,
9232
- groups: [AXPWidgetGroupEnum.UtilityWidget],
9233
- description: '@data-management:metadata-definitions.components.meta-data-form.description',
9234
- icon: 'fa-light fa-list-check',
9235
- defaultFilterWidgetName: 'string-filter',
9236
- type: 'editor',
9237
- options: {
9238
- needLabel: false,
9239
- },
9240
- properties: [
9241
- AXP_NAME_PROPERTY,
9242
- AXP_DATA_PATH_PROPERTY,
9243
- AXP_READONLY_PROPERTY,
9244
- AXP_DISABLED_PROPERTY,
9245
- ],
9246
- components: {
9247
- view: {
9248
- component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
9249
- },
9250
- edit: {
9251
- component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
9252
- },
9253
- print: {
9254
- component: () => Promise.resolve().then(function () { return metaDataFormEdit_component; }).then((c) => c.AXPMetaDataFormWidgetEditComponent),
9255
- },
9256
- },
9257
- };
9258
-
9259
- class AXPMetaDataFormWidgetEditComponent extends AXPValueWidgetComponent {
9260
- constructor() {
9261
- super(...arguments);
9262
- //#region ---- Inputs ----
9263
- /**
9264
- * Groups structure from meta-data-selector or evaluated expression
9265
- */
9266
- this.groups = computed(() => {
9267
- const options = this.options();
9268
- const groupsOption = options['groups'];
9269
- // Handle evaluated expression result (array of groups) or direct groups array
9270
- if (Array.isArray(groupsOption) && groupsOption.length > 0) {
9271
- return groupsOption;
9211
+ /**
9212
+ * Handle field drag and drop (within and between groups)
9213
+ */
9214
+ handleFieldDrop(event, targetGroupName) {
9215
+ const sourceGroupName = event.previousContainer.id.replace('group-', '').replace('-fields', '');
9216
+ this.designerState.update((state) => {
9217
+ const groups = [...state.groups];
9218
+ const sourceGroup = groups.find((g) => g.name === sourceGroupName);
9219
+ const targetGroup = groups.find((g) => g.name === targetGroupName);
9220
+ if (!sourceGroup || !targetGroup)
9221
+ return state;
9222
+ if (event.previousContainer === event.container) {
9223
+ const fields = [...sourceGroup.fields];
9224
+ moveItemInArray$1(fields, event.previousIndex, event.currentIndex);
9225
+ const updatedFields = fields.map((field, index) => ({
9226
+ ...field,
9227
+ order: index,
9228
+ }));
9229
+ return {
9230
+ ...state,
9231
+ groups: groups.map((g) => (g.id === sourceGroup.id ? { ...g, fields: updatedFields } : g)),
9232
+ };
9272
9233
  }
9273
- return [];
9274
- }, ...(ngDevMode ? [{ debugName: "groups" }] : []));
9275
- this.#effect = effect(() => {
9276
- this.initializeFormDefinition();
9277
- }, ...(ngDevMode ? [{ debugName: "#effect" }] : []));
9278
- /**
9279
- * Check if there are any valid metadata definitions available
9280
- */
9281
- this.hasDefinitions = computed(() => {
9282
- const groups = this.groups();
9283
- if (groups.length === 0) {
9284
- return false;
9234
+ else {
9235
+ const sourceFields = [...sourceGroup.fields];
9236
+ const targetFields = [...targetGroup.fields];
9237
+ transferArrayItem(sourceFields, targetFields, event.previousIndex, event.currentIndex);
9238
+ const updatedSourceFields = sourceFields.map((field, index) => ({
9239
+ ...field,
9240
+ order: index,
9241
+ }));
9242
+ const updatedTargetFields = targetFields.map((field, index) => ({
9243
+ ...field,
9244
+ order: index,
9245
+ }));
9246
+ return {
9247
+ ...state,
9248
+ groups: groups.map((g) => {
9249
+ if (g.id === sourceGroup.id)
9250
+ return { ...g, fields: updatedSourceFields };
9251
+ if (g.id === targetGroup.id)
9252
+ return { ...g, fields: updatedTargetFields };
9253
+ return g;
9254
+ }),
9255
+ };
9285
9256
  }
9286
- return groups.some((group) => {
9287
- const fields = group.fields || [];
9288
- return fields.length > 0 && fields.some((field) => field != null);
9289
- });
9290
- }, ...(ngDevMode ? [{ debugName: "hasDefinitions" }] : []));
9291
- //#endregion
9292
- //#region ---- Outputs ----
9293
- /**
9294
- * Emitted when form context changes
9295
- */
9296
- this.contextChange = output();
9297
- /**
9298
- * Emitted when form validity changes
9299
- */
9300
- this.validityChange = output();
9301
- //#endregion
9302
- //#region ---- Properties ----
9303
- this.layoutRenderer = viewChild(AXPLayoutRendererComponent, ...(ngDevMode ? [{ debugName: "layoutRenderer" }] : []));
9304
- /**
9305
- * Form definition signal that only updates when structure actually changes
9306
- */
9307
- this.formDefinition = signal({ groups: [] }, ...(ngDevMode ? [{ debugName: "formDefinition" }] : []));
9257
+ });
9258
+ this.syncStateToValue();
9308
9259
  }
9309
- #effect;
9310
- //#endregion
9311
- //#region ---- Event Handlers ----
9312
9260
  /**
9313
- * Handle context change from dynamic form
9261
+ * Get all group drop list IDs for connected drag & drop
9314
9262
  */
9315
- onContextChange(context) {
9316
- this.contextChange.emit(context);
9317
- this.setValue(context);
9263
+ getAllGroupDropLists() {
9264
+ return this.groups().map((group) => `group-${group.name}-fields`);
9318
9265
  }
9266
+ //#endregion
9267
+ //#region ---- Preview Mode ----
9319
9268
  /**
9320
- * Handle validity change from dynamic form
9269
+ * Handle preview button click - opens preview in a dialog using layout builder
9321
9270
  */
9322
- onValidityChange(isValid) {
9323
- this.validityChange.emit(isValid);
9271
+ async handlePreviewClick() {
9272
+ if (this.isPreviewDisabled()) {
9273
+ return;
9274
+ }
9275
+ try {
9276
+ const previewTitle = await this.translationService.translateAsync('@data-management:metadata-definitions.actions.preview.title');
9277
+ const formDef = this.previewFormDefinition();
9278
+ if (!formDef.groups || formDef.groups.length === 0) {
9279
+ const emptyDialogRef = await this.layoutBuilder
9280
+ .create()
9281
+ .dialog((dialog) => {
9282
+ dialog
9283
+ .setTitle(previewTitle)
9284
+ .setSize('md')
9285
+ .setCloseButton(true)
9286
+ .setContext({})
9287
+ .setActions((actions) => actions.cancel('@general:actions.close.title'));
9288
+ })
9289
+ .show();
9290
+ emptyDialogRef.close();
9291
+ return;
9292
+ }
9293
+ const dialogRef = await this.layoutBuilder
9294
+ .create()
9295
+ .dialog((dialog) => {
9296
+ dialog
9297
+ .setTitle(previewTitle)
9298
+ .setSize('lg')
9299
+ .setCloseButton(true)
9300
+ .setContext(this.getValue() || {})
9301
+ .content((layoutBuilder) => {
9302
+ layoutBuilder.dynamicForm(formDef);
9303
+ })
9304
+ .setActions((actions) => actions.cancel('@general:actions.close.title'));
9305
+ })
9306
+ .show();
9307
+ await dialogRef.action();
9308
+ dialogRef.close();
9309
+ }
9310
+ catch (error) {
9311
+ console.error('Error opening preview:', error);
9312
+ await this.dialogService.alert((await this.translationService.translateAsync('@general:messages.error.title')) || 'Error', error instanceof Error ? error.message : 'Failed to open preview', 'danger');
9313
+ }
9324
9314
  }
9325
9315
  //#endregion
9326
- //#region ---- Private Methods ----
9316
+ //#region ---- Utility Methods ----
9327
9317
  /**
9328
- * Initialize form definition based on current inputs
9318
+ * Sync internal state to external value
9319
+ * Ensures at least 1 group always exists
9329
9320
  */
9330
- initializeFormDefinition() {
9331
- const groups = this.groups();
9332
- if (groups.length > 0) {
9333
- const newFormDefinition = this.convertGroupsToFormDefinition(groups);
9334
- this.formDefinition.set(newFormDefinition);
9321
+ syncStateToValue() {
9322
+ const currentState = this.designerState();
9323
+ let groups = currentState.groups;
9324
+ if (groups.length === 0) {
9325
+ groups = [createDefaultGroup()];
9326
+ this.designerState.update((state) => ({
9327
+ ...state,
9328
+ groups,
9329
+ }));
9335
9330
  }
9331
+ const value = convertStateToValue({ ...currentState, groups });
9332
+ this.setValue(value);
9336
9333
  }
9337
9334
  /**
9338
- * Convert groups structure from meta-data-selector to form definition
9339
- * Each metadata group becomes a separate form group with visual separation (card look)
9335
+ * Parse interface field to extract widget type
9340
9336
  */
9341
- convertGroupsToFormDefinition(groups) {
9342
- const formGroups = [];
9343
- groups.forEach((group) => {
9344
- const fields = group.fields || [];
9345
- const validFields = fields.filter((field) => field != null);
9346
- if (validFields.length > 0) {
9347
- const parameters = validFields.map((field) => this.convertMetadataToFieldDefinition(field));
9348
- formGroups.push({
9349
- name: this.sanitizeGroupName(group.name || 'default'),
9350
- title: group.title || group.name,
9351
- description: group.description,
9352
- look: groups.length > 1 ? 'group' : 'container',
9353
- parameters,
9354
- });
9337
+ parseInterfaceType(interfaceValue) {
9338
+ try {
9339
+ if (!interfaceValue)
9340
+ return 'text-editor';
9341
+ // If it's already a string widget type
9342
+ if (!interfaceValue.startsWith('{')) {
9343
+ return interfaceValue;
9355
9344
  }
9356
- });
9357
- return { groups: formGroups };
9345
+ // Try to parse as JSON
9346
+ const parsed = JSON.parse(interfaceValue);
9347
+ return parsed.type || 'text-editor';
9348
+ }
9349
+ catch {
9350
+ return 'text-editor';
9351
+ }
9358
9352
  }
9359
9353
  /**
9360
- * Convert single metadata definition to field definition
9354
+ * Get widget icon for a field
9361
9355
  */
9362
- convertMetadataToFieldDefinition(metadata) {
9363
- // Handle null/undefined metadata
9364
- if (!metadata) {
9365
- console.warn('Undefined metadata definition encountered');
9366
- return {
9367
- path: 'undefined',
9368
- title: 'Undefined Field',
9369
- description: 'This field has undefined metadata',
9370
- widget: {
9371
- type: 'text-editor',
9372
- path: 'undefined',
9373
- options: {
9374
- defaultValue: '',
9375
- validations: [],
9356
+ getWidgetIcon(interfaceValue) {
9357
+ return 'fa-light fa-input-text';
9358
+ }
9359
+ /**
9360
+ * Get widget title for a field
9361
+ */
9362
+ getWidgetTitle(interfaceValue) {
9363
+ const widgetType = this.parseInterfaceType(interfaceValue);
9364
+ return widgetType
9365
+ .replace(/-/g, ' ')
9366
+ .replace(/editor/gi, '')
9367
+ .trim()
9368
+ .split(' ')
9369
+ .map((word) => word.charAt(0).toUpperCase() + word.slice(1))
9370
+ .join(' ') || 'Text';
9371
+ }
9372
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetEditComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
9373
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: AXPMetaDataSelectorWidgetEditComponent, isStandalone: true, selector: "axp-meta-data-selector-widget-edit", usesInheritance: true, ngImport: i0, template: "<div class=\"axp-meta-data-selector-widget-edit\" *translate=\"let t\">\n @if (!readonly()) {\n <div class=\"__header\">\n <div class=\"__header-left\"></div>\n <div class=\"__header-right\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-group.title' | translate | async\" [color]=\"'primary'\"\n (onClick)=\"handleAddGroupClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-layer-group\"></ax-icon>\n </ax-prefix>\n </ax-button>\n\n <ax-button class=\"ax-sm\" [color]=\"'success'\" [disabled]=\"isPreviewDisabled()\"\n [text]=\"'@data-management:metadata-definitions.actions.preview.title' | translate | async\"\n (onClick)=\"handlePreviewClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-eye\"></ax-icon>\n </ax-prefix>\n </ax-button>\n </div>\n </div>\n }\n\n <div class=\"__content\">\n @if (groups().length === 0) {\n <axp-state-message icon=\"fa-light fa-layer-group\"\n [title]=\"'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.title'\"\n [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.description'\n \">\n </axp-state-message>\n } @else {\n <div class=\"__groups-container\" cdkDropList [cdkDropListData]=\"groups()\"\n (cdkDropListDropped)=\"handleGroupDrop($event)\">\n @for (group of groups(); track group.id) {\n <div class=\"__group\" cdkDrag [class.__default-group]=\"isDefaultGroup(group.name)\">\n <div class=\"__group-header\">\n @if (!readonly()) {\n <div class=\"__group-drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n }\n <div class=\"__group-info\">\n <h3 class=\"__group-title\">\n @if (group.title) {\n {{ group.title }}\n <span class=\"__group-name-prefix\">({{ group.name }})</span>\n } @else {\n {{ group.name }}\n }\n @if (isDefaultGroup(group.name) && !group.title) {\n <span class=\"__default-group-badge\">{{\n '@data-management:metadata-definitions.components.meta-data-selector.default-section-badge'\n | translate\n | async\n }}</span>\n }\n </h3>\n @if (group.description) {\n <p class=\"__group-description\">{{ group.description }}</p>\n }\n </div>\n @if (!readonly()) {\n <div class=\"__group-actions\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-field.title' | translate | async\"\n [color]=\"'accent2'\" (onClick)=\"handleAddFieldToGroup(group)\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-plus\"></ax-icon>\n </ax-prefix>\n </ax-button>\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleGroupEdit(group)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n @if (canDeleteGroup()) {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"danger\" (onClick)=\"handleGroupRemove(group)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n\n <div class=\"__fields-container\">\n <div class=\"__items-list\" cdkDropList [id]=\"'group-' + group.name + '-fields'\"\n [cdkDropListData]=\"group.fields\" [cdkDropListConnectedTo]=\"getAllGroupDropLists()\"\n (cdkDropListDropped)=\"handleFieldDrop($event, group.name)\">\n @if (group.fields.length === 0) {\n <axp-state-message icon=\"fa-light fa-inbox\" [title]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.title'\n \" [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.description'\n \">\n </axp-state-message>\n } @else { @for (field of group.fields; track field.id) {\n <div class=\"__field-item\" cdkDrag [class.__deleted]=\"field.status === 'deleted'\">\n <div class=\"__drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n\n <div class=\"__item-content\">\n <div class=\"__item-header\">\n <div class=\"__field-icon\">\n <ax-icon [icon]=\"getWidgetIcon(field.interface)\"></ax-icon>\n </div>\n <div class=\"__field-info\">\n <h4 class=\"__item-title\">{{ field.title }}</h4>\n <span class=\"__widget-type\">{{ getWidgetTitle(field.interface) }}</span>\n @if (field.description) {\n <p class=\"__field-description\">{{ field.description }}</p>\n }\n </div>\n </div>\n </div>\n\n @if (!readonly()) {\n <div class=\"__item-actions\">\n @if (field.status === 'deleted') {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"warning\"\n (onClick)=\"handleFieldRevert(field, group.id)\">\n <ax-icon class=\"fa-light fa-rotate-left\"></ax-icon>\n </ax-button>\n } @else {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleFieldEdit(field)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n\n <ax-button [look]=\"'blank'\" class=\"ax-sm\" color=\"danger\" (onClick)=\"handleFieldRemove(field, group.id)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n } }\n </div>\n </div>\n </div>\n }\n </div>\n }\n </div>\n</div>", styles: [".axp-meta-data-selector-widget-edit{display:flex;height:100%;width:100%;flex-direction:column}.axp-meta-data-selector-widget-edit .__header{display:flex;align-items:center;justify-content:space-between;gap:.75rem;border-bottom-width:1px;padding:.75rem}.axp-meta-data-selector-widget-edit .__header .__header-left,.axp-meta-data-selector-widget-edit .__header .__header-right{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__content{flex:1 1 0%;overflow:auto;padding:.75rem}.axp-meta-data-selector-widget-edit .__groups-container{display:flex;flex-direction:column;gap:1rem}.axp-meta-data-selector-widget-edit .__group{border-radius:.375rem;border-width:1px;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title{margin-bottom:.25rem;display:flex;align-items:center;gap:.5rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__group-name-prefix{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1));font-weight:300}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__default-group-badge{border-radius:.25rem;--tw-bg-opacity: 1;background-color:rgb(245 245 245 / var(--tw-bg-opacity, 1));padding:.25rem .5rem;font-size:.75rem;line-height:1rem;font-weight:400;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-actions{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__group .__fields-container{padding:1rem}.axp-meta-data-selector-widget-edit .__group .__fields-container .__items-list{gap:.75rem;min-height:3rem;display:flex;flex-direction:column}.axp-meta-data-selector-widget-edit .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));cursor:move;-webkit-user-select:none;user-select:none}.axp-meta-data-selector-widget-edit .__field-item:hover{--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__field-item.__deleted{opacity:.6;background-color:rgb(var(--ax-sys-color-danger-lightest-surface));color:rgb(var(--ax-sys-color-on-danger-lightest-surface));border-color:rgb(var(--ax-sys-color-border-danger-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item.__selected{--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab;transition:color .15s ease-in-out}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-actions{display:flex;gap:.5rem}.__group.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 10px 15px -3px rgb(0 0 0 / .1), 0 4px 6px -4px rgb(0 0 0 / .1);--tw-shadow-colored: 0 10px 15px -3px var(--tw-shadow-color), 0 4px 6px -4px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.__group.cdk-drag-preview .__group-info{flex:1 1 0%}.__group.cdk-drag-preview .__group-info .__group-title{margin-bottom:.25rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.__group.cdk-drag-preview .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-preview .__fields-container{padding:.75rem}.__group.cdk-drag-preview .__fields-container .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__field-icon{display:flex;height:2rem;width:2rem;align-items:center;justify-content:center;border-radius:.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content{flex:1 1 0%}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__item-title{margin-bottom:0;font-size:.875rem;line-height:1.25rem;font-weight:500}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__widget-type{font-size:.75rem;line-height:1rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-placeholder{border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));opacity:.5;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));margin-bottom:1rem;min-height:8rem}.__group.cdk-drag-dragging{opacity:.7}.__group:hover:not(.cdk-drag-dragging) .__group-drag-handle{--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 20px 25px -5px rgb(0 0 0 / .1), 0 8px 10px -6px rgb(0 0 0 / .1);--tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));display:flex;align-items:center;gap:.75rem;padding:.75rem;opacity:.9}.__field-item.cdk-drag-preview .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-placeholder{position:relative;border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));border-radius:.375rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));min-height:5rem;margin-bottom:.75rem;opacity:.5}.__field-item.cdk-drag-placeholder>*{opacity:0}.__field-item.cdk-drag-placeholder:before{content:\"\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));pointer-events:none}.__field-item.cdk-drag-animating{transition:transform .25s cubic-bezier(.4,0,.2,1)}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder){margin-bottom:.75rem}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__items-list.cdk-drop-list-dragging{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-dragging axp-state-message{display:none}.__items-list.cdk-drop-list-dragging:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__items-list.cdk-drop-list-receiving{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-receiving axp-state-message{display:none}.__items-list.cdk-drop-list-receiving:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder){margin-bottom:1rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__groups-container.cdk-drop-list-dragging:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__groups-container.cdk-drop-list-receiving:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: AXButtonModule }, { kind: "component", type: i2$1.AXButtonComponent, selector: "ax-button", inputs: ["disabled", "size", "tabIndex", "color", "look", "text", "toggleable", "selected", "iconOnly", "type", "loadingText"], outputs: ["onBlur", "onFocus", "onClick", "selectedChange", "toggleableChange", "lookChange", "colorChange", "disabledChange", "loadingTextChange"] }, { kind: "ngmodule", type: AXDecoratorModule }, { kind: "component", type: i5.AXDecoratorIconComponent, selector: "ax-icon", inputs: ["icon"] }, { kind: "component", type: i5.AXDecoratorGenericComponent, selector: "ax-footer, ax-header, ax-content, ax-divider, ax-form-hint, ax-prefix, ax-suffix, ax-text, ax-title, ax-subtitle, ax-placeholder, ax-overlay" }, { kind: "ngmodule", type: AXFormModule }, { kind: "ngmodule", type: AXTranslationModule }, { kind: "directive", type: i7.AXTranslatorDirective, selector: "[translate]" }, { kind: "component", type: AXPStateMessageComponent, selector: "axp-state-message", inputs: ["mode", "icon", "title", "description", "variant"] }, { kind: "directive", type: CdkDropList, selector: "[cdkDropList], cdk-drop-list", inputs: ["cdkDropListConnectedTo", "cdkDropListData", "cdkDropListOrientation", "id", "cdkDropListLockAxis", "cdkDropListDisabled", "cdkDropListSortingDisabled", "cdkDropListEnterPredicate", "cdkDropListSortPredicate", "cdkDropListAutoScrollDisabled", "cdkDropListAutoScrollStep", "cdkDropListElementContainer", "cdkDropListHasAnchor"], outputs: ["cdkDropListDropped", "cdkDropListEntered", "cdkDropListExited", "cdkDropListSorted"], exportAs: ["cdkDropList"] }, { kind: "directive", type: CdkDrag, selector: "[cdkDrag]", inputs: ["cdkDragData", "cdkDragLockAxis", "cdkDragRootElement", "cdkDragBoundary", "cdkDragStartDelay", "cdkDragFreeDragPosition", "cdkDragDisabled", "cdkDragConstrainPosition", "cdkDragPreviewClass", "cdkDragPreviewContainer", "cdkDragScale"], outputs: ["cdkDragStarted", "cdkDragReleased", "cdkDragEnded", "cdkDragEntered", "cdkDragExited", "cdkDragDropped", "cdkDragMoved"], exportAs: ["cdkDrag"] }, { kind: "directive", type: CdkDragHandle, selector: "[cdkDragHandle]", inputs: ["cdkDragHandleDisabled"] }, { kind: "pipe", type: i6.AsyncPipe, name: "async" }, { kind: "pipe", type: i7.AXTranslatorPipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9374
+ }
9375
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetEditComponent, decorators: [{
9376
+ type: Component,
9377
+ args: [{ selector: 'axp-meta-data-selector-widget-edit', changeDetection: ChangeDetectionStrategy.OnPush, imports: [
9378
+ CommonModule,
9379
+ AXButtonModule,
9380
+ AXDecoratorModule,
9381
+ AXFormModule,
9382
+ AXTranslationModule,
9383
+ AXPStateMessageComponent,
9384
+ CdkDropList,
9385
+ CdkDrag,
9386
+ CdkDragHandle,
9387
+ ], template: "<div class=\"axp-meta-data-selector-widget-edit\" *translate=\"let t\">\n @if (!readonly()) {\n <div class=\"__header\">\n <div class=\"__header-left\"></div>\n <div class=\"__header-right\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-group.title' | translate | async\" [color]=\"'primary'\"\n (onClick)=\"handleAddGroupClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-layer-group\"></ax-icon>\n </ax-prefix>\n </ax-button>\n\n <ax-button class=\"ax-sm\" [color]=\"'success'\" [disabled]=\"isPreviewDisabled()\"\n [text]=\"'@data-management:metadata-definitions.actions.preview.title' | translate | async\"\n (onClick)=\"handlePreviewClick()\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-eye\"></ax-icon>\n </ax-prefix>\n </ax-button>\n </div>\n </div>\n }\n\n <div class=\"__content\">\n @if (groups().length === 0) {\n <axp-state-message icon=\"fa-light fa-layer-group\"\n [title]=\"'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.title'\"\n [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-groups.description'\n \">\n </axp-state-message>\n } @else {\n <div class=\"__groups-container\" cdkDropList [cdkDropListData]=\"groups()\"\n (cdkDropListDropped)=\"handleGroupDrop($event)\">\n @for (group of groups(); track group.id) {\n <div class=\"__group\" cdkDrag [class.__default-group]=\"isDefaultGroup(group.name)\">\n <div class=\"__group-header\">\n @if (!readonly()) {\n <div class=\"__group-drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n }\n <div class=\"__group-info\">\n <h3 class=\"__group-title\">\n @if (group.title) {\n {{ group.title }}\n <span class=\"__group-name-prefix\">({{ group.name }})</span>\n } @else {\n {{ group.name }}\n }\n @if (isDefaultGroup(group.name) && !group.title) {\n <span class=\"__default-group-badge\">{{\n '@data-management:metadata-definitions.components.meta-data-selector.default-section-badge'\n | translate\n | async\n }}</span>\n }\n </h3>\n @if (group.description) {\n <p class=\"__group-description\">{{ group.description }}</p>\n }\n </div>\n @if (!readonly()) {\n <div class=\"__group-actions\">\n <ax-button class=\"ax-sm\"\n [text]=\"'@data-management:metadata-definitions.actions.add-field.title' | translate | async\"\n [color]=\"'accent2'\" (onClick)=\"handleAddFieldToGroup(group)\">\n <ax-prefix>\n <ax-icon icon=\"fa-light fa-plus\"></ax-icon>\n </ax-prefix>\n </ax-button>\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleGroupEdit(group)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n @if (canDeleteGroup()) {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"danger\" (onClick)=\"handleGroupRemove(group)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n\n <div class=\"__fields-container\">\n <div class=\"__items-list\" cdkDropList [id]=\"'group-' + group.name + '-fields'\"\n [cdkDropListData]=\"group.fields\" [cdkDropListConnectedTo]=\"getAllGroupDropLists()\"\n (cdkDropListDropped)=\"handleFieldDrop($event, group.name)\">\n @if (group.fields.length === 0) {\n <axp-state-message icon=\"fa-light fa-inbox\" [title]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.title'\n \" [description]=\"\n '@data-management:metadata-definitions.components.meta-data-selector.empty-states.empty-group.description'\n \">\n </axp-state-message>\n } @else { @for (field of group.fields; track field.id) {\n <div class=\"__field-item\" cdkDrag [class.__deleted]=\"field.status === 'deleted'\">\n <div class=\"__drag-handle\" cdkDragHandle>\n <ax-icon icon=\"fa-light fa-grip-vertical\"></ax-icon>\n </div>\n\n <div class=\"__item-content\">\n <div class=\"__item-header\">\n <div class=\"__field-icon\">\n <ax-icon [icon]=\"getWidgetIcon(field.interface)\"></ax-icon>\n </div>\n <div class=\"__field-info\">\n <h4 class=\"__item-title\">{{ field.title }}</h4>\n <span class=\"__widget-type\">{{ getWidgetTitle(field.interface) }}</span>\n @if (field.description) {\n <p class=\"__field-description\">{{ field.description }}</p>\n }\n </div>\n </div>\n </div>\n\n @if (!readonly()) {\n <div class=\"__item-actions\">\n @if (field.status === 'deleted') {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"warning\"\n (onClick)=\"handleFieldRevert(field, group.id)\">\n <ax-icon class=\"fa-light fa-rotate-left\"></ax-icon>\n </ax-button>\n } @else {\n <ax-button class=\"ax-sm\" [look]=\"'blank'\" color=\"accent3\" (onClick)=\"handleFieldEdit(field)\">\n <ax-icon class=\"fa-light fa-pencil\"></ax-icon>\n </ax-button>\n\n <ax-button [look]=\"'blank'\" class=\"ax-sm\" color=\"danger\" (onClick)=\"handleFieldRemove(field, group.id)\">\n <ax-icon class=\"fa-light fa-trash-can\"></ax-icon>\n </ax-button>\n }\n </div>\n }\n </div>\n } }\n </div>\n </div>\n </div>\n }\n </div>\n }\n </div>\n</div>", styles: [".axp-meta-data-selector-widget-edit{display:flex;height:100%;width:100%;flex-direction:column}.axp-meta-data-selector-widget-edit .__header{display:flex;align-items:center;justify-content:space-between;gap:.75rem;border-bottom-width:1px;padding:.75rem}.axp-meta-data-selector-widget-edit .__header .__header-left,.axp-meta-data-selector-widget-edit .__header .__header-right{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__content{flex:1 1 0%;overflow:auto;padding:.75rem}.axp-meta-data-selector-widget-edit .__groups-container{display:flex;flex-direction:column;gap:1rem}.axp-meta-data-selector-widget-edit .__group{border-radius:.375rem;border-width:1px;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title{margin-bottom:.25rem;display:flex;align-items:center;gap:.5rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__group-name-prefix{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1));font-weight:300}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-title .__default-group-badge{border-radius:.25rem;--tw-bg-opacity: 1;background-color:rgb(245 245 245 / var(--tw-bg-opacity, 1));padding:.25rem .5rem;font-size:.75rem;line-height:1rem;font-weight:400;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__group .__group-header .__group-actions{display:flex;gap:.5rem}.axp-meta-data-selector-widget-edit .__group .__fields-container{padding:1rem}.axp-meta-data-selector-widget-edit .__group .__fields-container .__items-list{gap:.75rem;min-height:3rem;display:flex;flex-direction:column}.axp-meta-data-selector-widget-edit .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));cursor:move;-webkit-user-select:none;user-select:none}.axp-meta-data-selector-widget-edit .__field-item:hover{--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.axp-meta-data-selector-widget-edit .__field-item.__deleted{opacity:.6;background-color:rgb(var(--ax-sys-color-danger-lightest-surface));color:rgb(var(--ax-sys-color-on-danger-lightest-surface));border-color:rgb(var(--ax-sys-color-border-danger-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item.__selected{--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1));cursor:grab;transition:color .15s ease-in-out}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:active{cursor:grabbing}.axp-meta-data-selector-widget-edit .__field-item .__drag-handle:hover{--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info{flex:1 1 0%}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.axp-meta-data-selector-widget-edit .__field-item .__item-actions{display:flex;gap:.5rem}.__group.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 10px 15px -3px rgb(0 0 0 / .1), 0 4px 6px -4px rgb(0 0 0 / .1);--tw-shadow-colored: 0 10px 15px -3px var(--tw-shadow-color), 0 4px 6px -4px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__group-header{display:flex;align-items:center;gap:.75rem;border-bottom-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lighter-surface));color:rgb(var(--ax-sys-color-on-lighter-surface));border-color:rgb(var(--ax-sys-color-border-lighter-surface))}.__group.cdk-drag-preview .__group-info{flex:1 1 0%}.__group.cdk-drag-preview .__group-info .__group-title{margin-bottom:.25rem;font-size:1.125rem;line-height:1.75rem;font-weight:600}.__group.cdk-drag-preview .__group-info .__group-description{font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-preview .__fields-container{padding:.75rem}.__group.cdk-drag-preview .__fields-container .__field-item{display:flex;align-items:center;gap:.75rem;border-radius:.375rem;border-width:1px;padding:.75rem;background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__field-icon{display:flex;height:2rem;width:2rem;align-items:center;justify-content:center;border-radius:.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content{flex:1 1 0%}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__item-title{margin-bottom:0;font-size:.875rem;line-height:1.25rem;font-weight:500}.__group.cdk-drag-preview .__fields-container .__field-item .__item-content .__widget-type{font-size:.75rem;line-height:1rem;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__group.cdk-drag-placeholder{border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));opacity:.5;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));margin-bottom:1rem;min-height:8rem}.__group.cdk-drag-dragging{opacity:.7}.__group:hover:not(.cdk-drag-dragging) .__group-drag-handle{--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview{border-radius:.375rem;border-width:1px;--tw-shadow: 0 20px 25px -5px rgb(0 0 0 / .1), 0 8px 10px -6px rgb(0 0 0 / .1);--tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-lightest-surface));color:rgb(var(--ax-sys-color-on-lightest-surface));border-color:rgb(var(--ax-sys-color-border-lightest-surface));display:flex;align-items:center;gap:.75rem;padding:.75rem;opacity:.9}.__field-item.cdk-drag-preview .__drag-handle{display:flex;height:1.5rem;width:1.5rem;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgb(163 163 163 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header{display:flex;align-items:flex-start;gap:.75rem}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-icon{display:flex;height:2.5rem;width:2.5rem;align-items:center;justify-content:center;border-radius:.375rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));--tw-shadow: 0 1px 2px 0 rgb(0 0 0 / .05);--tw-shadow-colored: 0 1px 2px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow);background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info{flex:1 1 0%}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__item-title{margin-bottom:.25rem;font-size:1rem;line-height:1.5rem;font-weight:600}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__widget-type{font-size:.875rem;line-height:1.25rem;font-weight:500;--tw-text-opacity: 1;color:rgb(82 82 82 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-preview .__item-content .__item-header .__field-info .__field-description{margin-top:.25rem;font-size:.875rem;line-height:1.25rem;line-height:1.625;--tw-text-opacity: 1;color:rgb(115 115 115 / var(--tw-text-opacity, 1))}.__field-item.cdk-drag-placeholder{position:relative;border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1));border-radius:.375rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));min-height:5rem;margin-bottom:.75rem;opacity:.5}.__field-item.cdk-drag-placeholder>*{opacity:0}.__field-item.cdk-drag-placeholder:before{content:\"\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));pointer-events:none}.__field-item.cdk-drag-animating{transition:transform .25s cubic-bezier(.4,0,.2,1)}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder){margin-bottom:.75rem}.__items-list.cdk-drop-list-dragging .__field-item:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__items-list.cdk-drop-list-dragging{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-dragging axp-state-message{display:none}.__items-list.cdk-drop-list-dragging:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__items-list.cdk-drop-list-receiving{position:relative;min-height:4rem;border-radius:.375rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__items-list.cdk-drop-list-receiving axp-state-message{display:none}.__items-list.cdk-drop-list-receiving:has(axp-state-message):after{content:\"Drop fields here\";position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:.875rem;line-height:1.25rem;--tw-text-opacity: 1;color:rgba(var(--ax-sys-color-accent2-500),var(--tw-text-opacity, 1));margin:.5rem;z-index:-1;pointer-events:none;min-height:3rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder){margin-bottom:1rem}.__groups-container.cdk-drop-list-dragging .__group:not(.cdk-drag-placeholder):last-child{margin-bottom:0}.__groups-container.cdk-drop-list-dragging:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}.__groups-container.cdk-drop-list-receiving:has(.__group.cdk-drag-placeholder){border-radius:.5rem;padding:.5rem;background-color:rgb(var(--ax-sys-color-accent2-lightest-surface));color:rgb(var(--ax-sys-color-on-accent2-lightest-surface));border-color:rgb(var(--ax-sys-color-border-accent2-lightest-surface));border-width:2px;border-style:dashed;--tw-border-opacity: 1;border-color:rgba(var(--ax-sys-color-accent2-500),var(--tw-border-opacity, 1))}\n"] }]
9388
+ }] });
9389
+
9390
+ var metaDataSelectorEdit_component = /*#__PURE__*/Object.freeze({
9391
+ __proto__: null,
9392
+ AXPMetaDataSelectorWidgetEditComponent: AXPMetaDataSelectorWidgetEditComponent
9393
+ });
9394
+
9395
+ function normalizeSelectorDisplayConfig(display, defaultTitle) {
9396
+ if (!display)
9397
+ return { section: { enabled: true } };
9398
+ if (typeof display === 'object')
9399
+ return display;
9400
+ switch (display) {
9401
+ case 'section':
9402
+ return { section: { enabled: true, title: defaultTitle }, popup: { enabled: false } };
9403
+ case 'popup':
9404
+ return { section: { enabled: false }, popup: { enabled: true, title: defaultTitle } };
9405
+ case 'both':
9406
+ return { section: { enabled: true, title: defaultTitle }, popup: { enabled: true, title: defaultTitle } };
9407
+ default:
9408
+ return { section: { enabled: true } };
9409
+ }
9410
+ }
9411
+ /**
9412
+ * meta-data-selector plugin
9413
+ *
9414
+ * Dynamic behavior:
9415
+ * - Creates a single property for metadata selector configuration
9416
+ * - Dynamically generates entity groups and meta-data-form widgets based on configured groups
9417
+ * - Each metadata group becomes a separate entity section with its own meta-data-form widget
9418
+ * - Reads group configuration at runtime from the field value
9419
+ */
9420
+ const metaDataSelectorPlugin = {
9421
+ name: 'meta-data-selector',
9422
+ order: 60,
9423
+ apply: (ctx, options) => {
9424
+ const opts = options ?? {};
9425
+ const field = META_DATA_SELECTOR_FIELD;
9426
+ // Try to get title from various sources in priority order:
9427
+ // 1. Direct options.title
9428
+ // 2. meta-data-form plugin configuration (from plugins array - current entity or base entity)
9429
+ // 3. meta-data-form extension (if plugin has already run - current entity or base entity)
9430
+ // 4. category plugin metaData.title (if enabled via category plugin)
9431
+ // 5. Default title
9432
+ let metaDataFormTitle;
9433
+ let metaDataFormExtTitle;
9434
+ let categoryMetaDataTitle;
9435
+ // Check current entity's plugins and extensions
9436
+ const plugins = ctx.entity.plugins;
9437
+ const metaDataFormPlugin = plugins?.find((p) => p.name === 'meta-data-form');
9438
+ metaDataFormTitle = metaDataFormPlugin?.options?.title;
9439
+ const metaDataFormExt = ctx.entity.extensions?.metaDataForm;
9440
+ metaDataFormExtTitle = metaDataFormExt
9441
+ ? Object.values(metaDataFormExt).find((ext) => ext?.title)
9442
+ : undefined;
9443
+ const categoryExt = ctx.entity.extensions?.category;
9444
+ categoryMetaDataTitle = categoryExt?.metaData?.title;
9445
+ // If running on a category entity (name ends with "Category"), check the base entity
9446
+ if (ctx.entity.name.endsWith('Category') && !metaDataFormTitle && !metaDataFormExtTitle) {
9447
+ const baseEntityName = ctx.entity.name.replace('Category', '');
9448
+ try {
9449
+ // Try to access the entity registry to get base entity
9450
+ // Note: This requires the registry to be available, which might not always be the case
9451
+ // For now, we'll rely on the category extension which should have the title
9452
+ // But we can also check if there's a way to access base entity plugins
9453
+ }
9454
+ catch (error) {
9455
+ // Silently fail - we'll use other sources
9456
+ }
9457
+ }
9458
+ // Priority: 1. options.title, 2. meta-data-form plugin title, 3. meta-data-form extension title, 4. category metaData.title, 5. default
9459
+ const displayTitle = (opts.title && opts.title.trim().length > 0)
9460
+ ? opts.title
9461
+ : (metaDataFormTitle && metaDataFormTitle.trim().length > 0)
9462
+ ? metaDataFormTitle
9463
+ : (metaDataFormExtTitle?.title && metaDataFormExtTitle.title.trim().length > 0)
9464
+ ? metaDataFormExtTitle.title
9465
+ : (categoryMetaDataTitle && categoryMetaDataTitle.trim().length > 0)
9466
+ ? categoryMetaDataTitle
9467
+ : '@data-management:metadata-definitions.actions.configure-meta-data.title';
9468
+ const displayConfig = normalizeSelectorDisplayConfig(opts.display, displayTitle);
9469
+ const sectionConfig = displayConfig.section ?? {};
9470
+ const popupConfig = displayConfig.popup ?? {};
9471
+ const showSection = sectionConfig.enabled !== false;
9472
+ const showPopup = popupConfig.enabled === true;
9473
+ const popupTitle = popupConfig.title ?? displayTitle;
9474
+ //#region ---- Step 1: Create Meta-Data Selector Property ----
9475
+ // Ensure group and section for the selector configuration itself
9476
+ const selectorSectionId = `meta-data-config`;
9477
+ const selectorGroupId = `meta-data-config`;
9478
+ const existingGroups = ctx.groups.list() ?? [];
9479
+ if (!existingGroups.some((g) => g.id === selectorGroupId)) {
9480
+ ctx.groups.add({ id: selectorGroupId, title: displayTitle });
9481
+ }
9482
+ // Ensure property exists (using meta-data-selector-editor interface)
9483
+ const props = ctx.properties.list();
9484
+ if (!props.some((p) => p.name === field)) {
9485
+ ctx.properties.add({
9486
+ name: field,
9487
+ title: displayTitle,
9488
+ groupId: selectorGroupId,
9489
+ schema: {
9490
+ dataType: 'object',
9491
+ interface: {
9492
+ type: 'meta-data-selector-editor',
9376
9493
  },
9377
9494
  },
9378
- };
9495
+ });
9379
9496
  }
9380
- const interfaceConfig = this.parseInterfaceConfig(metadata.interface);
9381
- // Handle defaultValue: support both direct property and configuration.defaultValue
9382
- // (meta-data-selector uses configuration.defaultValue, other sources may use defaultValue directly)
9383
- const defaultValue = metadata.defaultValue ?? metadata.configuration?.defaultValue;
9384
- // Handle description: support both direct property and from configuration
9385
- const description = metadata.description ?? metadata.configuration?.description;
9386
- const widget = {
9387
- type: interfaceConfig.type || 'text-editor',
9388
- path: metadata.name || 'unnamed',
9389
- options: {
9390
- ...interfaceConfig.options,
9391
- defaultValue: defaultValue,
9392
- validations: this.parseValidations(metadata.interface),
9497
+ // Add selector to single/create/modify views only when section display is enabled
9498
+ const selectorColSpan = 12;
9499
+ if (showSection) {
9500
+ ctx.interfaces.master.single.update((single) => {
9501
+ const next = single ?? { title: ctx.entity.title, sections: [], properties: [] };
9502
+ next.sections = next.sections ?? [];
9503
+ if (!next.sections.some((s) => s.id === selectorSectionId)) {
9504
+ next.sections.push({
9505
+ id: selectorSectionId,
9506
+ title: sectionConfig.title ?? displayTitle,
9507
+ order: sectionConfig.order ?? 200,
9508
+ });
9509
+ }
9510
+ next.properties = next.properties ?? [];
9511
+ if (!next.properties.some((p) => p.name === field)) {
9512
+ next.properties.push({
9513
+ name: field,
9514
+ layout: {
9515
+ label: { visible: false },
9516
+ positions: { lg: { colSpan: selectorColSpan, order: 9 } },
9517
+ },
9518
+ });
9519
+ }
9520
+ return next;
9521
+ });
9522
+ ctx.interfaces.master.create.update((create) => {
9523
+ const next = create ?? { sections: [], properties: [] };
9524
+ next.sections = next.sections ?? [];
9525
+ if (!next.sections.some((s) => s.id === selectorSectionId)) {
9526
+ next.sections.push({
9527
+ id: selectorSectionId,
9528
+ title: sectionConfig.title ?? displayTitle,
9529
+ });
9530
+ }
9531
+ next.properties = next.properties ?? [];
9532
+ if (!next.properties.some((p) => p.name === field)) {
9533
+ next.properties.push({
9534
+ name: field,
9535
+ layout: {
9536
+ label: { visible: false },
9537
+ positions: { lg: { colSpan: selectorColSpan, order: 7 } },
9538
+ },
9539
+ });
9540
+ }
9541
+ return next;
9542
+ });
9543
+ ctx.interfaces.master.modify.update((modify) => {
9544
+ const next = modify ?? { sections: [], properties: [] };
9545
+ next.sections = next.sections ?? [];
9546
+ if (!next.sections.some((s) => s.id === selectorSectionId)) {
9547
+ next.sections.push({
9548
+ id: selectorSectionId,
9549
+ title: sectionConfig.title ?? displayTitle,
9550
+ });
9551
+ }
9552
+ next.properties = next.properties ?? [];
9553
+ if (!next.properties.some((p) => p.name === field)) {
9554
+ next.properties.push({
9555
+ name: field,
9556
+ layout: {
9557
+ label: { visible: false },
9558
+ positions: { lg: { colSpan: selectorColSpan, order: 7 } },
9559
+ },
9560
+ });
9561
+ }
9562
+ return next;
9563
+ });
9564
+ }
9565
+ //#endregion
9566
+ //#region ---- Step 2: Dynamic Group Generation Middleware ----
9567
+ // Add metadata middleware to dynamically generate groups at runtime
9568
+ // This middleware reads the metaDataList field value and creates
9569
+ // entity groups + meta-data-form widgets for each configured group
9570
+ const metadataMiddleware = {
9571
+ name: 'metadata-dynamic-groups',
9572
+ order: 100,
9573
+ apply: (entityCtx) => {
9574
+ // Get the metadata selector value from context
9575
+ const metaDataValue = entityCtx.data?.[field];
9576
+ if (!metaDataValue?.groups || metaDataValue.groups.length === 0) {
9577
+ return; // No groups configured, skip
9578
+ }
9579
+ // TODO: Implement renderGroupsAsSections option
9580
+ // If opts.renderGroupsAsSections === true:
9581
+ // - Create separate entity sections for each metadata group
9582
+ // - Each section gets its own meta-data-form widget with only that group's fields
9583
+ // If opts.renderGroupsAsSections === false (default):
9584
+ // - Create single section with all groups (current behavior)
9585
+ // - Single meta-data-form widget receives all groups, renders them as cards
9586
+ // Current implementation: renderGroupsAsSections = false (default)
9587
+ // Create a single section and single meta-data-form widget for all groups
9588
+ const sectionId = 'metadata-section';
9589
+ const formFieldName = META_DATA_FORM_FIELD;
9590
+ const groupId = 'metadata-group';
9591
+ // Ensure entity group exists
9592
+ if (!entityCtx.groups.list().some((g) => g.id === groupId)) {
9593
+ entityCtx.groups.add({
9594
+ id: groupId,
9595
+ title: displayTitle,
9596
+ });
9597
+ }
9598
+ // Ensure meta-data-form property exists with all groups
9599
+ // Always update the property to ensure groups are passed correctly
9600
+ const existingProp = entityCtx.properties.list().find((p) => p.name === formFieldName);
9601
+ const groupsData = metaDataValue.groups.map((group) => ({
9602
+ name: group.name,
9603
+ title: group.title,
9604
+ description: group.description,
9605
+ fields: group.fields,
9606
+ }));
9607
+ if (!existingProp) {
9608
+ entityCtx.properties.add({
9609
+ name: formFieldName,
9610
+ title: displayTitle,
9611
+ groupId: groupId,
9612
+ schema: {
9613
+ dataType: 'object',
9614
+ interface: {
9615
+ type: 'meta-data-form-editor',
9616
+ options: {
9617
+ // Pass all groups so the form can render them as separate groups
9618
+ groups: groupsData,
9619
+ },
9620
+ },
9621
+ },
9622
+ });
9623
+ }
9624
+ else {
9625
+ // Update existing property to ensure groups are set
9626
+ if (existingProp.schema?.interface?.options) {
9627
+ existingProp.schema.interface.options.groups = groupsData;
9628
+ }
9629
+ }
9630
+ // Add to single view - single section
9631
+ entityCtx.interfaces.master.single.update((single) => {
9632
+ const next = single ?? { title: entityCtx.entity.title, sections: [], properties: [] };
9633
+ next.sections = next.sections ?? [];
9634
+ if (!next.sections.some((s) => s.id === sectionId)) {
9635
+ next.sections.push({
9636
+ id: sectionId,
9637
+ title: displayTitle,
9638
+ order: 300,
9639
+ });
9640
+ }
9641
+ next.properties = next.properties ?? [];
9642
+ if (!next.properties.some((p) => p.name === formFieldName)) {
9643
+ next.properties.push({
9644
+ name: formFieldName,
9645
+ layout: {
9646
+ label: { visible: false },
9647
+ positions: { lg: { colSpan: 12, order: 0 } },
9648
+ },
9649
+ });
9650
+ }
9651
+ return next;
9652
+ });
9653
+ // Add to create view - single section
9654
+ entityCtx.interfaces.master.create.update((create) => {
9655
+ const next = create ?? { sections: [], properties: [] };
9656
+ next.sections = next.sections ?? [];
9657
+ if (!next.sections.some((s) => s.id === sectionId)) {
9658
+ next.sections.push({
9659
+ id: sectionId,
9660
+ title: displayTitle,
9661
+ });
9662
+ }
9663
+ next.properties = next.properties ?? [];
9664
+ if (!next.properties.some((p) => p.name === formFieldName)) {
9665
+ next.properties.push({
9666
+ name: formFieldName,
9667
+ layout: {
9668
+ label: { visible: false },
9669
+ positions: { lg: { colSpan: 12, order: 10 } },
9670
+ },
9671
+ });
9672
+ }
9673
+ return next;
9674
+ });
9675
+ // Add to modify view - single section
9676
+ entityCtx.interfaces.master.modify.update((modify) => {
9677
+ const next = modify ?? { sections: [], properties: [] };
9678
+ next.sections = next.sections ?? [];
9679
+ if (!next.sections.some((s) => s.id === sectionId)) {
9680
+ next.sections.push({
9681
+ id: sectionId,
9682
+ title: displayTitle,
9683
+ });
9684
+ }
9685
+ next.properties = next.properties ?? [];
9686
+ if (!next.properties.some((p) => p.name === formFieldName)) {
9687
+ next.properties.push({
9688
+ name: formFieldName,
9689
+ layout: {
9690
+ label: { visible: false },
9691
+ positions: { lg: { colSpan: 12, order: 10 } },
9692
+ },
9693
+ });
9694
+ }
9695
+ return next;
9696
+ });
9393
9697
  },
9394
9698
  };
9395
- if (interfaceConfig.triggers?.length) {
9396
- widget.triggers = interfaceConfig.triggers;
9699
+ // Register the middleware (if middleware system exists)
9700
+ // Note: This is conceptual - actual implementation depends on platform capabilities
9701
+ // (ctx as any).middleware?.add?.(metadataMiddleware);
9702
+ //#endregion
9703
+ //#region ---- Step 3: Popup actions (when display is popup or both) ----
9704
+ if (showPopup) {
9705
+ const actionName = `show-meta-data-selector-popup-${field}`;
9706
+ const commandName = 'show-meta-data-selector-popup';
9707
+ ctx.interfaces.master.single.update((single) => {
9708
+ const next = single ?? { title: ctx.entity.title, sections: [], properties: [], actions: [] };
9709
+ next.actions = next.actions ?? [];
9710
+ if (!actionExists(next.actions, commandName, actionName)) {
9711
+ next.actions.push({
9712
+ name: actionName,
9713
+ title: popupTitle,
9714
+ command: {
9715
+ name: commandName,
9716
+ options: {
9717
+ entity: `${ctx.entity.module}.${ctx.entity.name}`,
9718
+ id: '{{ context.eval("id") }}',
9719
+ field,
9720
+ title: popupTitle,
9721
+ },
9722
+ },
9723
+ priority: 'secondary',
9724
+ type: 'configure',
9725
+ icon: 'fa-light fa-list-check',
9726
+ scope: AXPEntityCommandScope.Individual,
9727
+ });
9728
+ }
9729
+ return next;
9730
+ });
9731
+ ctx.interfaces.master.list.update((list) => {
9732
+ const next = list ?? { actions: [], views: [] };
9733
+ next.actions = next.actions ?? [];
9734
+ if (!actionExists(next.actions, commandName, actionName)) {
9735
+ next.actions.push({
9736
+ name: actionName,
9737
+ title: popupTitle,
9738
+ command: {
9739
+ name: commandName,
9740
+ options: {
9741
+ entity: `${ctx.entity.module}.${ctx.entity.name}`,
9742
+ id: '{{ context.eval("id") }}',
9743
+ field,
9744
+ title: popupTitle,
9745
+ },
9746
+ },
9747
+ priority: 'secondary',
9748
+ type: 'configure',
9749
+ icon: 'fa-light fa-list-check',
9750
+ scope: AXPEntityCommandScope.Individual,
9751
+ });
9752
+ }
9753
+ return next;
9754
+ });
9397
9755
  }
9398
- return {
9399
- path: metadata.name || 'unnamed',
9400
- title: metadata.title || 'Untitled Field',
9401
- description: description,
9402
- widget,
9756
+ //#endregion
9757
+ //#region ---- Step 4: Extension Metadata ----
9758
+ // Stamp normalized config for middleware
9759
+ ctx.entity.extensions ??= {};
9760
+ ctx.entity.extensions.metaDataSelector ??= {};
9761
+ ctx.entity.extensions.metaDataSelector[field] = {
9762
+ title: displayTitle,
9763
+ display: displayConfig,
9403
9764
  };
9404
- }
9405
- /**
9406
- * Parse interface configuration from metadata
9407
- */
9408
- parseInterfaceConfig(interfaceValue) {
9409
- if (typeof interfaceValue === 'string') {
9410
- try {
9411
- return JSON.parse(interfaceValue || '{}');
9412
- }
9413
- catch (error) {
9414
- console.warn('Failed to parse interface config:', interfaceValue, error);
9415
- return {};
9416
- }
9417
- }
9418
- return interfaceValue || {};
9419
- }
9420
- /**
9421
- * Parse validations from interface configuration
9422
- */
9423
- parseValidations(interfaceValue) {
9424
- const config = this.parseInterfaceConfig(interfaceValue);
9425
- return config.options?.validations || [];
9426
- }
9427
- /**
9428
- * Sanitize group name for use as identifier
9429
- */
9430
- sanitizeGroupName(name) {
9431
- return name.toLowerCase().replace(/[^a-z0-9]/g, '-');
9432
- }
9433
- //#endregion
9434
- //#region ---- Public Methods ----
9435
- /**
9436
- * Get the layout renderer component instance
9437
- */
9438
- getLayoutRenderer() {
9439
- return this.layoutRenderer();
9440
- }
9441
- /**
9442
- * Validate the form
9443
- */
9444
- async validate() {
9445
- const renderer = this.layoutRenderer();
9446
- if (renderer) {
9447
- const validation = await renderer.validate();
9448
- return validation.result;
9449
- }
9450
- return false;
9451
- }
9452
- /**
9453
- * Get current form context
9454
- */
9455
- getContext() {
9456
- const renderer = this.layoutRenderer();
9457
- return renderer ? renderer.getContext() : {};
9458
- }
9765
+ //#endregion
9766
+ },
9767
+ };
9768
+
9769
+ class AXPMetaDataSelectorWidgetViewComponent extends AXPValueWidgetComponent {
9459
9770
  /**
9460
- * Update form context programmatically
9771
+ * Returns a comma-separated list of selected meta titles.
9772
+ * Extracting this logic into a getter keeps the template simple and
9773
+ * avoids using arrow functions, which are not allowed in Angular
9774
+ * interpolation expressions.
9461
9775
  */
9462
- updateContext(context) {
9463
- console.log('updateContext', context);
9464
- const renderer = this.layoutRenderer();
9465
- if (renderer) {
9466
- renderer.updateContext(context);
9467
- }
9468
- }
9469
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataFormWidgetEditComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
9470
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: AXPMetaDataFormWidgetEditComponent, isStandalone: true, selector: "axp-meta-data-form-widget-edit", outputs: { contextChange: "contextChange", validityChange: "validityChange" }, viewQueries: [{ propertyName: "layoutRenderer", first: true, predicate: AXPLayoutRendererComponent, descendants: true, isSignal: true }], usesInheritance: true, ngImport: i0, template: `
9471
- @if (hasDefinitions()) {
9472
- <axp-layout-renderer
9473
- [layout]="formDefinition()"
9474
- [context]="getValue()"
9475
- [look]="'container'"
9476
- (contextChange)="onContextChange($event)"
9477
- (validityChange)="onValidityChange($event)"
9478
- >
9479
- </axp-layout-renderer>
9480
- } @else {
9481
- <axp-state-message
9482
- icon="fa-light fa-clipboard-list"
9483
- [title]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.title'"
9484
- [description]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.description'"
9485
- >
9486
- </axp-state-message>
9776
+ get display() {
9777
+ const val = this.getValue();
9778
+ return Array.isArray(val) ? val.map((v) => v.title || v.text).join(', ') : '';
9487
9779
  }
9488
- `, isInline: true, dependencies: [{ kind: "component", type: AXPLayoutRendererComponent, selector: "axp-layout-renderer", inputs: ["layout", "context", "look", "mode"], outputs: ["contextChange", "contextInitiated", "validityChange"] }, { kind: "ngmodule", type: AXFormModule }, { kind: "ngmodule", type: AXLabelModule }, { kind: "ngmodule", type: AXPWidgetCoreModule }, { kind: "component", type: AXPStateMessageComponent, selector: "axp-state-message", inputs: ["mode", "icon", "title", "description", "variant"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9780
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetViewComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
9781
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.16", type: AXPMetaDataSelectorWidgetViewComponent, isStandalone: true, selector: "axp-meta-data-selector-widget-view", usesInheritance: true, ngImport: i0, template: `<span>{{ display }}</span>`, isInline: true, dependencies: [{ kind: "ngmodule", type: AXDecoratorModule }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
9489
9782
  }
9490
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataFormWidgetEditComponent, decorators: [{
9783
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: AXPMetaDataSelectorWidgetViewComponent, decorators: [{
9491
9784
  type: Component,
9492
- args: [{ selector: 'axp-meta-data-form-widget-edit', template: `
9493
- @if (hasDefinitions()) {
9494
- <axp-layout-renderer
9495
- [layout]="formDefinition()"
9496
- [context]="getValue()"
9497
- [look]="'container'"
9498
- (contextChange)="onContextChange($event)"
9499
- (validityChange)="onValidityChange($event)"
9500
- >
9501
- </axp-layout-renderer>
9502
- } @else {
9503
- <axp-state-message
9504
- icon="fa-light fa-clipboard-list"
9505
- [title]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.title'"
9506
- [description]="'@data-management:metadata-definitions.components.meta-data-selector.empty-states.no-metadata-definitions.description'"
9507
- >
9508
- </axp-state-message>
9509
- }
9510
- `, changeDetection: ChangeDetectionStrategy.OnPush, imports: [AXPLayoutRendererComponent, AXFormModule, AXLabelModule, AXPWidgetCoreModule, AXPStateMessageComponent] }]
9511
- }], propDecorators: { contextChange: [{ type: i0.Output, args: ["contextChange"] }], validityChange: [{ type: i0.Output, args: ["validityChange"] }], layoutRenderer: [{ type: i0.ViewChild, args: [i0.forwardRef(() => AXPLayoutRendererComponent), { isSignal: true }] }] } });
9785
+ args: [{
9786
+ selector: 'axp-meta-data-selector-widget-view',
9787
+ template: `<span>{{ display }}</span>`,
9788
+ changeDetection: ChangeDetectionStrategy.OnPush,
9789
+ imports: [AXDecoratorModule],
9790
+ }]
9791
+ }] });
9512
9792
 
9513
- var metaDataFormEdit_component = /*#__PURE__*/Object.freeze({
9793
+ var metaDataSelectorView_component = /*#__PURE__*/Object.freeze({
9514
9794
  __proto__: null,
9515
- AXPMetaDataFormWidgetEditComponent: AXPMetaDataFormWidgetEditComponent
9795
+ AXPMetaDataSelectorWidgetViewComponent: AXPMetaDataSelectorWidgetViewComponent
9516
9796
  });
9517
9797
 
9518
- class ShowMetaDataFormPopupCommand {
9798
+ /**
9799
+ * Opens the meta-data-selector (configuration UI for groups/fields) in a popup.
9800
+ * Used when meta-data-selector plugin has display: 'popup' or 'both'.
9801
+ */
9802
+ class ShowMetaDataSelectorPopupCommand {
9519
9803
  constructor() {
9520
9804
  this.layoutBuilder = inject(AXPLayoutBuilderService);
9521
9805
  this.translationService = inject(AXTranslationService);
9522
9806
  this.entityService = inject(AXPEntityService);
9523
- this.entityRegistry = inject(AXPEntityDefinitionRegistryService);
9524
9807
  }
9525
9808
  async execute(input) {
9526
9809
  try {
9527
- // Extract evaluated options from __context__ (private/controlled data)
9528
- // The __context__.options contains evaluated expressions from entity actions
9529
9810
  const contextOptions = input.__context__?.options;
9530
- // Merge root-level input with evaluated options from __context__
9531
- // Root-level takes precedence if both exist
9532
9811
  const evaluatedInput = {
9533
9812
  ...contextOptions,
9534
9813
  ...input,
9535
- // Ensure we use evaluated options from __context__ if available
9536
9814
  ...(contextOptions ? contextOptions : {}),
9537
9815
  };
9538
- const { entity, id, field = META_DATA_FORM_FIELD, title, path } = evaluatedInput;
9816
+ const { entity, id, field = META_DATA_SELECTOR_FIELD, title, } = evaluatedInput;
9539
9817
  if (!entity || !id) {
9540
9818
  return {
9541
9819
  success: false,
@@ -9544,14 +9822,8 @@ class ShowMetaDataFormPopupCommand {
9544
9822
  },
9545
9823
  };
9546
9824
  }
9547
- // Ensure id is a string
9548
- if (typeof id !== 'string' && id != null) {
9549
- const stringId = String(id);
9550
- if (stringId) {
9551
- evaluatedInput.id = stringId;
9552
- }
9553
- }
9554
- if (!evaluatedInput.id || typeof evaluatedInput.id !== 'string') {
9825
+ const finalId = typeof id === 'string' ? id : String(id);
9826
+ if (!finalId) {
9555
9827
  return {
9556
9828
  success: false,
9557
9829
  message: {
@@ -9559,9 +9831,6 @@ class ShowMetaDataFormPopupCommand {
9559
9831
  },
9560
9832
  };
9561
9833
  }
9562
- const finalId = evaluatedInput.id;
9563
- // Get current entity record to get the metadata expression value
9564
- const [moduleName, entityName] = entity.split('.');
9565
9834
  const currentRecord = await this.findRecord(entity, finalId);
9566
9835
  if (!currentRecord) {
9567
9836
  return {
@@ -9571,46 +9840,9 @@ class ShowMetaDataFormPopupCommand {
9571
9840
  },
9572
9841
  };
9573
9842
  }
9574
- // Note: pathValue might be null/undefined, but the metadata expression evaluator will handle it
9575
- // The expression will return an empty array if pathValue is not available
9576
- // Resolve entity to get metadata expression and determine if it's category or entity lookup
9577
- const entityDef = await this.entityRegistry.resolve(moduleName, entityName);
9578
- const metaDataFormExt = entityDef.extensions?.metaDataForm?.[field];
9579
- if (!metaDataFormExt) {
9580
- return {
9581
- success: false,
9582
- message: {
9583
- text: await this.translationService.translateAsync('@data-management:metadata-definitions.messages.meta-data-form-not-configured'),
9584
- },
9585
- };
9586
- }
9587
- // Get path property to determine metadata source type
9588
- const props = entityDef.properties || [];
9589
- const pathProperty = props.find((p) => p.name === path);
9590
- const targetEntity = pathProperty?.schema?.interface?.options?.['entity'];
9591
- if (!targetEntity) {
9592
- return {
9593
- success: false,
9594
- message: {
9595
- text: await this.translationService.translateAsync('@data-management:metadata-definitions.messages.invalid-path-field'),
9596
- },
9597
- };
9598
- }
9599
- // Build metadata expression based on target entity type
9600
- let metadataExpression;
9601
- if (targetEntity.endsWith('Category')) {
9602
- // Category lookup - use fromCategory
9603
- metadataExpression = `{{ metadata.fromCategory("${entity}", context.eval('${path}')) }}`;
9604
- }
9605
- else {
9606
- // Relationship lookup - use fromEntity
9607
- metadataExpression = `{{ metadata.fromEntity("${targetEntity}", context.eval('${path}')) }}`;
9608
- }
9609
- // Get current meta data form value
9610
- const currentMetaDataValue = currentRecord[field] || {};
9611
- // Build dialog title
9612
- const dialogTitle = title || metaDataFormExt.title || await this.translationService.translateAsync('@data-management:metadata-definitions.components.meta-data-form.title');
9613
- // Open dialog with meta-data-form-editor widget
9843
+ const currentSelectorValue = currentRecord[field] ?? { groups: [] };
9844
+ const dialogTitle = title ??
9845
+ (await this.translationService.translateAsync('@data-management:metadata-definitions.actions.configure-meta-data.title'));
9614
9846
  const result = await this.layoutBuilder
9615
9847
  .create()
9616
9848
  .dialog((dialog) => {
@@ -9620,19 +9852,16 @@ class ShowMetaDataFormPopupCommand {
9620
9852
  .setCloseButton(true)
9621
9853
  .setContext({
9622
9854
  ...currentRecord,
9623
- [field]: currentMetaDataValue,
9855
+ [field]: currentSelectorValue,
9624
9856
  })
9625
9857
  .content((layout) => {
9626
9858
  layout.flex((flex) => {
9627
9859
  flex.setDirection('column').setGap('16px');
9628
- // Add meta-data-form-editor widget with metadata expression
9629
9860
  flex.formField('', (fieldBuilder) => {
9630
9861
  fieldBuilder
9631
9862
  .path(field)
9632
9863
  .setShowLabel(false)
9633
- .customWidget('meta-data-form-editor', {
9634
- groups: metadataExpression,
9635
- });
9864
+ .customWidget('meta-data-selector-editor', {});
9636
9865
  });
9637
9866
  });
9638
9867
  })
@@ -9647,9 +9876,7 @@ class ShowMetaDataFormPopupCommand {
9647
9876
  if (!context || action === 'cancel') {
9648
9877
  return { success: false };
9649
9878
  }
9650
- const updateData = {
9651
- [field]: context[field],
9652
- };
9879
+ const updateData = { [field]: context[field] };
9653
9880
  const updated = await this.updateRecord(entity, finalId, updateData);
9654
9881
  return {
9655
9882
  success: true,
@@ -9667,7 +9894,9 @@ class ShowMetaDataFormPopupCommand {
9667
9894
  return {
9668
9895
  success: false,
9669
9896
  message: {
9670
- text: error instanceof Error ? error.message : 'Failed to show meta data form popup',
9897
+ text: error instanceof Error
9898
+ ? error.message
9899
+ : 'Failed to show meta data selector popup',
9671
9900
  },
9672
9901
  };
9673
9902
  }
@@ -9681,25 +9910,25 @@ class ShowMetaDataFormPopupCommand {
9681
9910
  return dataAccessor.byKey(id);
9682
9911
  }
9683
9912
  /**
9684
- * Persists meta-data form changes. Override to use custom persistence or validation.
9913
+ * Persists meta-data changes. Override to use custom persistence or validation.
9685
9914
  */
9686
9915
  updateRecord(entity, id, data) {
9687
9916
  const dataAccessor = this.entityService.withEntity(entity).data();
9688
9917
  return dataAccessor.update(id, data);
9689
9918
  }
9690
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
9691
- static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, providedIn: 'root' }); }
9919
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
9920
+ static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, providedIn: 'root' }); }
9692
9921
  }
9693
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataFormPopupCommand, decorators: [{
9922
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: ShowMetaDataSelectorPopupCommand, decorators: [{
9694
9923
  type: Injectable,
9695
9924
  args: [{
9696
9925
  providedIn: 'root',
9697
9926
  }]
9698
9927
  }] });
9699
9928
 
9700
- var showMetaDataFormPopup_command = /*#__PURE__*/Object.freeze({
9929
+ var showMetaDataSelectorPopup_command = /*#__PURE__*/Object.freeze({
9701
9930
  __proto__: null,
9702
- ShowMetaDataFormPopupCommand: ShowMetaDataFormPopupCommand
9931
+ ShowMetaDataSelectorPopupCommand: ShowMetaDataSelectorPopupCommand
9703
9932
  });
9704
9933
 
9705
9934
  /**
@@ -10411,5 +10640,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
10411
10640
  * Generated bundle index. Do not edit.
10412
10641
  */
10413
10642
 
10414
- export { AXMColumnFilterSelectorWidget, AXMColumnFilterSelectorWidgetColumnComponent, AXMColumnFilterSelectorWidgetEditComponent, AXMColumnFilterSelectorWidgetFilterComponent, AXMColumnFilterSelectorWidgetPrintComponent, AXMColumnFilterSelectorWidgetViewComponent, AXMDataManagementFeatureKeys, AXMDataManagementModule, AXMDataSourceEntityModule, AXMDataSourceOutputType, AXMDataSourceService, AXMDataSourceServiceImpl, AXMDataSourceType, AXMDefaultAggregateFunctionProvider, AXMDefaultDatabaseTypeProvider, AXMEntityProvider, AXMMenuProvider, AXMMetaDataDefinitionEntityModule, AXMMetaDataDefinitionService, AXMMetaDataFeatureModule, AXMMetadataEvaluatorScopeProvider, AXMPMetaDataDefinitionServiceImpl, AXMPermissionsKeys, AXMQueryEntityModule, AXMQueryService, AXMQueryServiceImpl, AXMTagEntityModule, AXMTagEntityService, AXMTagsFeatureModule, AXM_COLUMN_DEF_WIDGET, AXM_FILTER_DEF_WIDGET, AXPAggregateBuilderComponent, AXPAggregateFunctionService, AXPAggregateFunctionsRegistry, AXPColumnsBuilderComponent, AXPDataManagementMenuKeys, AXPDatabaseTypeService, AXPGroupByBuilderComponent, AXPMetaDataSelectorWidget, AXPMetaDataSelectorWidgetEditComponent, AXPMetaDataSelectorWidgetViewComponent, AXPQueryBuilderComponent, AXPQueryBuilderWidget, AXPQueryBuilderWidgetColumnComponent, AXPQueryBuilderWidgetDesignerComponent, AXPQueryBuilderWidgetEditComponent, AXPQueryBuilderWidgetViewComponent, AXPRawQueryBuilderComponent, AXPSortBuilderComponent, AXPSystemTagProvider, AXPWhereBuilderComponent, AXP_AGGREGATE_FUNCTION_PROVIDER, AXP_DATABASE_TYPE_PROVIDER, AXP_DEFAULT_AGGREGATE_FUNCTION_PROVIDER, AXP_DEFAULT_DATABASE_TYPE_PROVIDER, META_DATA_FORM_FIELD, META_DATA_SELECTOR_FIELD, RootConfig, ShowMetaDataSelectorPopupCommand, convertStateToValue, convertValueToState, createDefaultGroup, dataSourceEntityFactory, factory, metaDataDefinitionFactory, metaDataSelectorPlugin, queryFactory, tagsPlugin };
10643
+ export { AXMColumnFilterSelectorWidget, AXMColumnFilterSelectorWidgetColumnComponent, AXMColumnFilterSelectorWidgetEditComponent, AXMColumnFilterSelectorWidgetFilterComponent, AXMColumnFilterSelectorWidgetPrintComponent, AXMColumnFilterSelectorWidgetViewComponent, AXMDataManagementFeatureKeys, AXMDataManagementModule, AXMDataSourceEntityModule, AXMDataSourceOutputType, AXMDataSourceService, AXMDataSourceServiceImpl, AXMDataSourceType, AXMDefaultAggregateFunctionProvider, AXMDefaultDatabaseTypeProvider, AXMEntityProvider, AXMMenuProvider, AXMMetaDataDefinitionEntityModule, AXMMetaDataDefinitionService, AXMMetaDataFeatureModule, AXMMetadataEvaluatorScopeProvider, AXMPMetaDataDefinitionServiceImpl, AXMPermissionsKeys, AXMQueryEntityModule, AXMQueryService, AXMQueryServiceImpl, AXMTagEntityModule, AXMTagEntityService, AXMTagsFeatureModule, AXM_COLUMN_DEF_WIDGET, AXM_FILTER_DEF_WIDGET, AXPAggregateBuilderComponent, AXPAggregateFunctionService, AXPAggregateFunctionsRegistry, AXPColumnsBuilderComponent, AXPDataManagementMenuKeys, AXPDatabaseTypeService, AXPGroupByBuilderComponent, AXPMetaDataFormWidget, AXPMetaDataFormWidgetEditComponent, AXPMetaDataSelectorWidget, AXPMetaDataSelectorWidgetEditComponent, AXPMetaDataSelectorWidgetViewComponent, AXPQueryBuilderComponent, AXPQueryBuilderWidget, AXPQueryBuilderWidgetColumnComponent, AXPQueryBuilderWidgetDesignerComponent, AXPQueryBuilderWidgetEditComponent, AXPQueryBuilderWidgetViewComponent, AXPRawQueryBuilderComponent, AXPSortBuilderComponent, AXPSystemTagProvider, AXPWhereBuilderComponent, AXP_AGGREGATE_FUNCTION_PROVIDER, AXP_DATABASE_TYPE_PROVIDER, AXP_DEFAULT_AGGREGATE_FUNCTION_PROVIDER, AXP_DEFAULT_DATABASE_TYPE_PROVIDER, META_DATA_FORM_FIELD, META_DATA_SELECTOR_FIELD, RootConfig, ShowMetaDataFormPopupCommand, ShowMetaDataSelectorPopupCommand, convertStateToValue, convertValueToState, createDefaultGroup, dataSourceEntityFactory, equipmentFactory, factory, metaDataDefinitionFactory, metaDataSelectorPlugin, queryFactory, tagsPlugin };
10415
10644
  //# sourceMappingURL=acorex-modules-data-management.mjs.map