@siliconst/metaui 1.4.8 → 1.4.10

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 (70) hide show
  1. package/package.json +1 -1
  2. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost-dbg.js +13 -0
  3. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost-dbg.js.map +1 -1
  4. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost.d.ts.map +1 -1
  5. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost.js +1 -1
  6. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost.js.map +1 -1
  7. package/src/nz/co/siliconst/ui5/metaui/controls/DynamicHost.ts +14 -0
  8. package/src/nz/co/siliconst/ui5/metaui/controls/host/delegates/ODataDelegate-dbg.js.map +1 -1
  9. package/src/nz/co/siliconst/ui5/metaui/controls/host/delegates/ODataDelegate.js.map +1 -1
  10. package/src/nz/co/siliconst/ui5/metaui/controls/host/delegates/ODataDelegate.ts +1 -1
  11. package/src/nz/co/siliconst/ui5/metaui/core/Engine-dbg.js +2 -0
  12. package/src/nz/co/siliconst/ui5/metaui/core/Engine-dbg.js.map +1 -1
  13. package/src/nz/co/siliconst/ui5/metaui/core/Engine.d.ts +2 -0
  14. package/src/nz/co/siliconst/ui5/metaui/core/Engine.d.ts.map +1 -1
  15. package/src/nz/co/siliconst/ui5/metaui/core/Engine.js.map +1 -1
  16. package/src/nz/co/siliconst/ui5/metaui/core/Engine.ts +3 -0
  17. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout-dbg.js +10 -0
  18. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout-dbg.js.map +1 -1
  19. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout.d.ts.map +1 -1
  20. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout.js +1 -1
  21. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout.js.map +1 -1
  22. package/src/nz/co/siliconst/ui5/metaui/layouts/TableLayout.ts +10 -0
  23. package/src/nz/co/siliconst/ui5/metaui/library-dbg.js +2 -2
  24. package/src/nz/co/siliconst/ui5/metaui/library-dbg.js.map +1 -1
  25. package/src/nz/co/siliconst/ui5/metaui/library-preload.js +10 -9
  26. package/src/nz/co/siliconst/ui5/metaui/library-preload.js.map +1 -1
  27. package/src/nz/co/siliconst/ui5/metaui/library.d.ts +13 -0
  28. package/src/nz/co/siliconst/ui5/metaui/library.d.ts.map +1 -1
  29. package/src/nz/co/siliconst/ui5/metaui/library.js +1 -1
  30. package/src/nz/co/siliconst/ui5/metaui/library.js.map +1 -1
  31. package/src/nz/co/siliconst/ui5/metaui/library.ts +19 -1
  32. package/src/nz/co/siliconst/ui5/metaui/manifest.json +2 -1
  33. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin-dbg.js +11 -3
  34. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin-dbg.js.map +1 -1
  35. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.d.ts.map +1 -1
  36. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.js +1 -1
  37. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.js.map +1 -1
  38. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.ts +10 -3
  39. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin-dbg.js +14 -3
  40. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin-dbg.js.map +1 -1
  41. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.d.ts.map +1 -1
  42. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.js +1 -1
  43. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.js.map +1 -1
  44. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.ts +14 -3
  45. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin-dbg.js +5 -2
  46. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin-dbg.js.map +1 -1
  47. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.d.ts.map +1 -1
  48. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.js +1 -1
  49. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.js.map +1 -1
  50. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.ts +5 -2
  51. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin-dbg.js +11 -3
  52. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin-dbg.js.map +1 -1
  53. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin.d.ts.map +1 -1
  54. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin.js +1 -1
  55. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin.js.map +1 -1
  56. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin.ts +10 -3
  57. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin-dbg.js +39 -3
  58. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin-dbg.js.map +1 -1
  59. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin.d.ts +4 -0
  60. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin.d.ts.map +1 -1
  61. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin.js +1 -1
  62. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin.js.map +1 -1
  63. package/src/nz/co/siliconst/ui5/metaui/plugins/controls/TextAreaPlugin.ts +40 -2
  64. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder-dbg.js +50 -0
  65. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder-dbg.js.map +1 -0
  66. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder.d.ts +19 -0
  67. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder.d.ts.map +1 -0
  68. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder.js +2 -0
  69. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder.js.map +1 -0
  70. package/src/nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder.ts +43 -0
@@ -1,4 +1,17 @@
1
1
  declare module "nz/co/siliconst/ui5/metaui/library" {
2
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/StringPlugin";
3
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/NumberPlugin";
4
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/BooleanPlugin";
5
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin";
6
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin";
7
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/DropdownPlugin";
8
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/DatePlugin";
9
+ import "nz/co/siliconst/ui5/metaui/core/DefaultLayoutGenerator";
10
+ import "nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder";
11
+ import "nz/co/siliconst/ui5/metaui/layouts/FormLayout";
12
+ import "nz/co/siliconst/ui5/metaui/layouts/TableLayout";
13
+ import "nz/co/siliconst/ui5/metaui/layouts/WizardLayout";
14
+ import "nz/co/siliconst/ui5/metaui/layouts/CompactLayout";
2
15
  global {
3
16
  interface Window {
4
17
  nz: {
@@ -1 +1 @@
1
- {"version":3,"file":"library.d.ts","sourceRoot":"../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/library.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,oCAAoC,CAAC;IAmC5C,MAAM,CAAC;QACX,UAAU,MAAM;YACZ,EAAE,EAAE;gBACA,EAAE,EAAE;oBACA,SAAS,EAAE;wBACP,GAAG,EAAE;4BACD,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;yBACnC,CAAC;qBACL,CAAC;iBACL,CAAC;aACL,CAAC;SACL;KACJ;;IAED,wBAAiD;CAEhD"}
1
+ {"version":3,"file":"library.d.ts","sourceRoot":"../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/library.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,oCAAoC,CAAC;IAUpD,OAAO,0DAA0D,CAAC;IAClE,OAAO,0DAA0D,CAAC;IAClE,OAAO,2DAA2D,CAAC;IACnE,OAAO,0DAA0D,CAAC;IAClE,OAAO,yDAAyD,CAAC;IACjE,OAAO,4DAA4D,CAAC;IACpE,OAAO,wDAAwD,CAAC;IAChE,OAAO,wDAAwD,CAAC;IAChE,OAAO,oDAAoD,CAAC;IAG5D,OAAO,+CAA+C,CAAC;IACvD,OAAO,gDAAgD,CAAC;IACxD,OAAO,iDAAiD,CAAC;IACzD,OAAO,kDAAkD,CAAC;IA6BlD,MAAM,CAAC;QACX,UAAU,MAAM;YACZ,EAAE,EAAE;gBACA,EAAE,EAAE;oBACA,SAAS,EAAE;wBACP,GAAG,EAAE;4BACD,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;yBACnC,CAAC;qBACL,CAAC;iBACL,CAAC;aACL,CAAC;SACL;KACJ;;IAED,wBAAiD;CAEhD"}
@@ -1,2 +1,2 @@
1
- sap.ui.define(["sap/ui/core/Core"],function(o){"use strict";o.initLibrary({name:"nz.co.siliconst.ui5.metaui",version:"1.0.0",dependencies:["sap.ui.core","sap.m","sap.ui.layout","sap.ui.table"],controls:["nz.co.siliconst.ui5.metaui.controls.GeneratorHost","nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl","nz.co.siliconst.ui5.metaui.controls.CameraControl","nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl","nz.co.siliconst.ui5.metaui.controls.SignatureControl","nz.co.siliconst.ui5.metaui.controls.VoiceInputControl","nz.co.siliconst.ui5.metaui.controls.GeolocationControl","nz.co.siliconst.ui5.metaui.controls.RichTextControl"],elements:[],interfaces:[],noLibraryCSS:true});var i=window.nz.co.siliconst.ui5.metaui;return i});
1
+ sap.ui.define(["sap/ui/core/Core","nz/co/siliconst/ui5/metaui/plugins/controls/StringPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/NumberPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/BooleanPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/DropdownPlugin","nz/co/siliconst/ui5/metaui/plugins/controls/DatePlugin","nz/co/siliconst/ui5/metaui/core/DefaultLayoutGenerator","nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder","nz/co/siliconst/ui5/metaui/layouts/FormLayout","nz/co/siliconst/ui5/metaui/layouts/TableLayout","nz/co/siliconst/ui5/metaui/layouts/WizardLayout","nz/co/siliconst/ui5/metaui/layouts/CompactLayout"],function(i,o,n,t,s,u,c,l,e,a,r,m,z,p){"use strict";i.initLibrary({name:"nz.co.siliconst.ui5.metaui",version:"1.0.0",dependencies:["sap.ui.core","sap.m","sap.ui.layout","sap.ui.table"],controls:["nz.co.siliconst.ui5.metaui.controls.DynamicHost","nz.co.siliconst.ui5.metaui.controls.host.GeneratorHost","nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl","nz.co.siliconst.ui5.metaui.controls.CameraControl","nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl","nz.co.siliconst.ui5.metaui.controls.SignatureControl","nz.co.siliconst.ui5.metaui.controls.VoiceInputControl","nz.co.siliconst.ui5.metaui.controls.GeolocationControl","nz.co.siliconst.ui5.metaui.controls.RichTextControl"],elements:[],interfaces:[],noLibraryCSS:true});var g=window.nz.co.siliconst.ui5.metaui;return g});
2
2
  //# sourceMappingURL=library.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"library.js","names":["Core","initLibrary","name","version","dependencies","controls","elements","interfaces","noLibraryCSS","__exports","window","nz","co","siliconst","ui5","metaui"],"sources":["library.ts"],"sourcesContent":["/**\n * @file library.ts\n * @description Standard SAP UI5 library registration file. Exposes the MetaUI namespace \n * and automatically bootstraps the internal PluginRegistry.\n */\n\nimport Core from \"sap/ui/core/Core\";\n\n// Delegate to standard library registration\nCore.initLibrary({\n name: \"nz.co.siliconst.ui5.metaui\",\n version: \"1.0.0\",\n dependencies: [\n \"sap.ui.core\",\n \"sap.m\",\n \"sap.ui.layout\",\n \"sap.ui.table\"\n ],\n controls: [\n \"nz.co.siliconst.ui5.metaui.controls.GeneratorHost\",\n \"nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl\",\n \"nz.co.siliconst.ui5.metaui.controls.CameraControl\",\n \"nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl\",\n \"nz.co.siliconst.ui5.metaui.controls.SignatureControl\",\n \"nz.co.siliconst.ui5.metaui.controls.VoiceInputControl\",\n \"nz.co.siliconst.ui5.metaui.controls.GeolocationControl\",\n \"nz.co.siliconst.ui5.metaui.controls.RichTextControl\"\n ],\n elements: [],\n interfaces: [],\n noLibraryCSS: true\n});\n\n// Exporting window object safely for UI5 compatibility if needed\ndeclare global {\n interface Window {\n nz: {\n co: {\n siliconst: {\n ui5: {\n metaui: Record<string, unknown>;\n };\n };\n };\n };\n }\n}\n\nexport default window.nz.co.siliconst.ui5.metaui;\n"],"mappings":"4DASAA,EAAKC,YAAY,CACbC,KAAM,6BACNC,QAAS,QACTC,aAAc,CACV,cACA,QACA,gBACA,gBAEJC,SAAU,CACN,oDACA,0DACA,oDACA,4DACA,uDACA,wDACA,yDACA,uDAEJC,SAAU,GACVC,WAAY,GACZC,aAAc,OAGlB,IAAAC,EAeeC,OAAOC,GAAGC,GAAGC,UAAUC,IAAIC,OAAM,OAAAN,CAAA","ignoreList":[]}
1
+ {"version":3,"file":"library.js","names":["Core","initLibrary","name","version","dependencies","controls","elements","interfaces","noLibraryCSS","__exports","window","nz","co","siliconst","ui5","metaui"],"sources":["library.ts"],"sourcesContent":["/**\n * @file library.ts\n * @description Standard SAP UI5 library registration file. Exposes the MetaUI namespace \n * and automatically bootstraps the internal PluginRegistry.\n */\n\nimport Core from \"sap/ui/core/Core\";\n\n// Explicitly import core plugins to bundle them into library-preload.js\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/StringPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/NumberPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/BooleanPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/DropdownPlugin\";\nimport \"nz/co/siliconst/ui5/metaui/plugins/controls/DatePlugin\";\nimport \"nz/co/siliconst/ui5/metaui/core/DefaultLayoutGenerator\";\nimport \"nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder\";\n\n// Explicitly import core Layouts\nimport \"nz/co/siliconst/ui5/metaui/layouts/FormLayout\";\nimport \"nz/co/siliconst/ui5/metaui/layouts/TableLayout\";\nimport \"nz/co/siliconst/ui5/metaui/layouts/WizardLayout\";\nimport \"nz/co/siliconst/ui5/metaui/layouts/CompactLayout\";\n\n// Delegate to standard library registration\nCore.initLibrary({\n name: \"nz.co.siliconst.ui5.metaui\",\n version: \"1.0.0\",\n dependencies: [\n \"sap.ui.core\",\n \"sap.m\",\n \"sap.ui.layout\",\n \"sap.ui.table\"\n ],\n controls: [\n \"nz.co.siliconst.ui5.metaui.controls.DynamicHost\",\n \"nz.co.siliconst.ui5.metaui.controls.host.GeneratorHost\",\n \"nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl\",\n \"nz.co.siliconst.ui5.metaui.controls.CameraControl\",\n \"nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl\",\n \"nz.co.siliconst.ui5.metaui.controls.SignatureControl\",\n \"nz.co.siliconst.ui5.metaui.controls.VoiceInputControl\",\n \"nz.co.siliconst.ui5.metaui.controls.GeolocationControl\",\n \"nz.co.siliconst.ui5.metaui.controls.RichTextControl\"\n ],\n elements: [],\n interfaces: [],\n noLibraryCSS: true\n});\n\n// Exporting window object safely for UI5 compatibility if needed\ndeclare global {\n interface Window {\n nz: {\n co: {\n siliconst: {\n ui5: {\n metaui: Record<string, unknown>;\n };\n };\n };\n };\n }\n}\n\nexport default window.nz.co.siliconst.ui5.metaui;\n"],"mappings":"uyBA0BAA,EAAKC,YAAY,CACbC,KAAM,6BACNC,QAAS,QACTC,aAAc,CACV,cACA,QACA,gBACA,gBAEJC,SAAU,CACN,kDACA,yDACA,0DACA,oDACA,4DACA,uDACA,wDACA,yDACA,uDAEJC,SAAU,GACVC,WAAY,GACZC,aAAc,OAGlB,IAAAC,EAeeC,OAAOC,GAAGC,GAAGC,UAAUC,IAAIC,OAAM,OAAAN,CAAA","ignoreList":[]}
@@ -6,6 +6,23 @@
6
6
 
7
7
  import Core from "sap/ui/core/Core";
8
8
 
9
+ // Explicitly import core plugins to bundle them into library-preload.js
10
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/StringPlugin";
11
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/NumberPlugin";
12
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/BooleanPlugin";
13
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/ObjectPlugin";
14
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin";
15
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/DropdownPlugin";
16
+ import "nz/co/siliconst/ui5/metaui/plugins/controls/DatePlugin";
17
+ import "nz/co/siliconst/ui5/metaui/core/DefaultLayoutGenerator";
18
+ import "nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder";
19
+
20
+ // Explicitly import core Layouts
21
+ import "nz/co/siliconst/ui5/metaui/layouts/FormLayout";
22
+ import "nz/co/siliconst/ui5/metaui/layouts/TableLayout";
23
+ import "nz/co/siliconst/ui5/metaui/layouts/WizardLayout";
24
+ import "nz/co/siliconst/ui5/metaui/layouts/CompactLayout";
25
+
9
26
  // Delegate to standard library registration
10
27
  Core.initLibrary({
11
28
  name: "nz.co.siliconst.ui5.metaui",
@@ -17,7 +34,8 @@ Core.initLibrary({
17
34
  "sap.ui.table"
18
35
  ],
19
36
  controls: [
20
- "nz.co.siliconst.ui5.metaui.controls.GeneratorHost",
37
+ "nz.co.siliconst.ui5.metaui.controls.DynamicHost",
38
+ "nz.co.siliconst.ui5.metaui.controls.host.GeneratorHost",
21
39
  "nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl",
22
40
  "nz.co.siliconst.ui5.metaui.controls.CameraControl",
23
41
  "nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl",
@@ -24,7 +24,8 @@
24
24
  "css": false,
25
25
  "content": {
26
26
  "controls": [
27
- "nz.co.siliconst.ui5.metaui.controls.GeneratorHost",
27
+ "nz.co.siliconst.ui5.metaui.controls.DynamicHost",
28
+ "nz.co.siliconst.ui5.metaui.controls.host.GeneratorHost",
28
29
  "nz.co.siliconst.ui5.metaui.controls.BaseHardwareControl",
29
30
  "nz.co.siliconst.ui5.metaui.controls.CameraControl",
30
31
  "nz.co.siliconst.ui5.metaui.controls.BarcodeScannerControl",
@@ -46,9 +46,11 @@ sap.ui.define(["./BasePlugin", "sap/m/Button"], function (___BasePlugin, Button)
46
46
  const ctxPath = bindingContext.getPath();
47
47
  updatePath = ctxPath.endsWith("/") ? ctxPath + bindingPath : ctxPath === "/" ? "/" + bindingPath : ctxPath + "/" + bindingPath;
48
48
  }
49
- const nestedData = parentModel.getProperty(updatePath) || [];
50
- sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/host/GeneratorHost"], GeneratorHost => {
51
- const host = new GeneratorHost({
49
+
50
+ // Deep clone to prevent live-mutations on the parent model before 'Submit' is clicked
51
+ const nestedData = JSON.parse(JSON.stringify(parentModel.getProperty(updatePath) || []));
52
+ sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/DynamicHost"], DynamicHost => {
53
+ const host = new DynamicHost({
52
54
  schemaDefinition: subSchema,
53
55
  data: nestedData,
54
56
  editable: this.isEditable // Pass the display mode down to the child Engine!
@@ -59,6 +61,12 @@ sap.ui.define(["./BasePlugin", "sap/m/Button"], function (___BasePlugin, Button)
59
61
  host.attachSubmit(e => {
60
62
  const payload = e.getParameter("payload");
61
63
  parentModel.setProperty(updatePath, payload);
64
+
65
+ // CRITICAL: Notify the parent Engine that this field mutated
66
+ // so it can trigger LiveUpdate syncs and validate!
67
+ if (this.onChange) {
68
+ this.onChange(true, propKey);
69
+ }
62
70
  });
63
71
  }
64
72
  const buttonText = field.ui?.dialogButtonText || (!this.isEditable ? "Close" : "OK");
@@ -1 +1 @@
1
- {"version":3,"file":"ArrayPlugin-dbg.js","names":["BasePlugin","___BasePlugin","ArrayPlugin","render","field","bindingPath","modelName","engineScopeId","onChange","metadata","propKey","startsWith","substring","subSchema","type","title","ui","label","items","properties","uiLayout","control","Button","id","generateStableId","text","isEditable","icon","press","oEvent","btn","getSource","parentModel","getModel","bindingContext","getBindingContext","updatePath","ctxPath","getPath","endsWith","nestedData","getProperty","sap","require","GeneratorHost","host","schemaDefinition","data","editable","attachSubmit","e","payload","getParameter","setProperty","buttonText","dialogButtonText","openInDialog","getValue","applyState","__exports","__esModule"],"sources":["ArrayPlugin.ts"],"sourcesContent":["/**\n * @file ArrayPlugin.ts\n * @description Renders a button that drills down into a nested table (array) via a recursive Dialog using v2 schema.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport Button from \"sap/m/Button\";\nimport JSONModel from \"sap/ui/model/json/JSONModel\";\n\nexport class ArrayPlugin extends BasePlugin {\n /**\n * Renders a `sap.m.Button` to open a nested array form dialog.\n * \n * @param field The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured Button control.\n */\n public render(field: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = field;\n const propKey = bindingPath.startsWith(\"/\") ? bindingPath.substring(1) : bindingPath;\n \n const subSchema: ISchema = {\n type: \"array\",\n title: field.ui?.label || propKey,\n items: field.items || {\n type: \"object\",\n properties: {} // inference will handle it if empty\n }\n };\n\n if (field.uiLayout) {\n subSchema.uiLayout = field.uiLayout;\n }\n\n this.control = new Button({\n id: this.generateStableId(engineScopeId, bindingPath),\n text: !this.isEditable ? \"View Records\" : \"Edit Records\",\n icon: !this.isEditable ? \"sap-icon://display\" : \"sap-icon://list\",\n press: (oEvent: sap.ui.base.Event) => {\n const btn = oEvent.getSource() as Button;\n const parentModel = btn.getModel(modelName) as JSONModel;\n if (!parentModel) return;\n \n const bindingContext = btn.getBindingContext(modelName);\n let updatePath = bindingPath;\n if (bindingContext && !bindingPath.startsWith(\"/\")) {\n const ctxPath = bindingContext.getPath();\n updatePath = ctxPath.endsWith(\"/\") ? ctxPath + bindingPath : (ctxPath === \"/\" ? \"/\" + bindingPath : ctxPath + \"/\" + bindingPath);\n }\n \n const nestedData = parentModel.getProperty(updatePath) || [];\n\n sap.ui.require([\"nz/co/siliconst/ui5/metaui/controls/host/GeneratorHost\"], (GeneratorHost: typeof import(\"../../controls/host/GeneratorHost\").default) => {\n const host = new GeneratorHost({\n schemaDefinition: subSchema,\n data: nestedData,\n editable: this.isEditable // Pass the display mode down to the child Engine!\n });\n\n // Only attach submit event if we are not in display mode\n if (!!this.isEditable) {\n host.attachSubmit((e: sap.ui.base.Event) => {\n const payload = e.getParameter(\"payload\");\n parentModel.setProperty(updatePath, payload);\n });\n }\n\n const buttonText = field.ui?.dialogButtonText || (!this.isEditable ? \"Close\" : \"OK\");\n host.openInDialog(`Nested Records: ${field.ui?.label || propKey}`, buttonText);\n });\n }\n });\n \n return this.control as Control;\n }\n\n /**\n * Read-only component for the engine, returns null.\n */\n protected getValue(): unknown {\n return null;\n }\n\n /**\n * Read-only component, no dynamic state handling needed for the button itself.\n */\n protected applyState(): void {\n // dynamic state changes\n }\n}\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"file":"ArrayPlugin-dbg.js","names":["BasePlugin","___BasePlugin","ArrayPlugin","render","field","bindingPath","modelName","engineScopeId","onChange","metadata","propKey","startsWith","substring","subSchema","type","title","ui","label","items","properties","uiLayout","control","Button","id","generateStableId","text","isEditable","icon","press","oEvent","btn","getSource","parentModel","getModel","bindingContext","getBindingContext","updatePath","ctxPath","getPath","endsWith","nestedData","JSON","parse","stringify","getProperty","sap","require","DynamicHost","host","schemaDefinition","data","editable","attachSubmit","e","payload","getParameter","setProperty","buttonText","dialogButtonText","openInDialog","getValue","applyState","__exports","__esModule"],"sources":["ArrayPlugin.ts"],"sourcesContent":["/**\n * @file ArrayPlugin.ts\n * @description Renders a button that drills down into a nested table (array) via a recursive Dialog using v2 schema.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport Button from \"sap/m/Button\";\nimport JSONModel from \"sap/ui/model/json/JSONModel\";\n\nexport class ArrayPlugin extends BasePlugin {\n /**\n * Renders a `sap.m.Button` to open a nested array form dialog.\n * \n * @param field The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured Button control.\n */\n public render(field: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = field;\n const propKey = bindingPath.startsWith(\"/\") ? bindingPath.substring(1) : bindingPath;\n \n const subSchema: ISchema = {\n type: \"array\",\n title: field.ui?.label || propKey,\n items: field.items || {\n type: \"object\",\n properties: {} // inference will handle it if empty\n }\n };\n\n if (field.uiLayout) {\n subSchema.uiLayout = field.uiLayout;\n }\n\n this.control = new Button({\n id: this.generateStableId(engineScopeId, bindingPath),\n text: !this.isEditable ? \"View Records\" : \"Edit Records\",\n icon: !this.isEditable ? \"sap-icon://display\" : \"sap-icon://list\",\n press: (oEvent: sap.ui.base.Event) => {\n const btn = oEvent.getSource() as Button;\n const parentModel = btn.getModel(modelName) as JSONModel;\n if (!parentModel) return;\n \n const bindingContext = btn.getBindingContext(modelName);\n let updatePath = bindingPath;\n if (bindingContext && !bindingPath.startsWith(\"/\")) {\n const ctxPath = bindingContext.getPath();\n updatePath = ctxPath.endsWith(\"/\") ? ctxPath + bindingPath : (ctxPath === \"/\" ? \"/\" + bindingPath : ctxPath + \"/\" + bindingPath);\n }\n \n // Deep clone to prevent live-mutations on the parent model before 'Submit' is clicked\n const nestedData = JSON.parse(JSON.stringify(parentModel.getProperty(updatePath) || []));\n\n sap.ui.require([\"nz/co/siliconst/ui5/metaui/controls/DynamicHost\"], (DynamicHost: typeof import(\"../../controls/DynamicHost\").default) => {\n const host = new DynamicHost({\n schemaDefinition: subSchema,\n data: nestedData,\n editable: this.isEditable // Pass the display mode down to the child Engine!\n });\n\n // Only attach submit event if we are not in display mode\n if (!!this.isEditable) {\n host.attachSubmit((e: sap.ui.base.Event) => {\n const payload = e.getParameter(\"payload\");\n parentModel.setProperty(updatePath, payload);\n\n // CRITICAL: Notify the parent Engine that this field mutated\n // so it can trigger LiveUpdate syncs and validate!\n if (this.onChange) {\n this.onChange(true, propKey);\n }\n });\n }\n\n const buttonText = field.ui?.dialogButtonText || (!this.isEditable ? \"Close\" : \"OK\");\n host.openInDialog(`Nested Records: ${field.ui?.label || propKey}`, buttonText);\n });\n }\n });\n \n return this.control as Control;\n }\n\n /**\n * Read-only component for the engine, returns null.\n */\n protected getValue(): unknown {\n return null;\n }\n\n /**\n * Read-only component, no dynamic state handling needed for the button itself.\n */\n protected applyState(): void {\n // dynamic state changes\n }\n}\n"],"mappings":"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","ignoreList":[]}
@@ -1 +1 @@
1
- {"version":3,"file":"ArrayPlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,yDAAyD,CAAC;IACzE;;;OAGG;IAEH,OAAO,EAAE,UAAU,EAAE,MAAM,wDAAwD,CAAC;IACpF,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAI1C,MAAa,WAAY,SAAQ,UAAU;QACvC;;;;;;;;;WASG;QACI,MAAM,CAAC,KAAK,EAAE,iBAAiB,EAAG,WAAW,EAAE,MAAM,EAAG,SAAS,GAAE,MAAe,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QA4DrL;;WAEG;QACH,SAAS,CAAC,QAAQ,IAAI,OAAO;QAI7B;;WAEG;QACH,SAAS,CAAC,UAAU,IAAI,IAAI;KAG/B;CAEA"}
1
+ {"version":3,"file":"ArrayPlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/ArrayPlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,yDAAyD,CAAC;IACzE;;;OAGG;IAEH,OAAO,EAAE,UAAU,EAAE,MAAM,wDAAwD,CAAC;IACpF,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAI1C,MAAa,WAAY,SAAQ,UAAU;QACvC;;;;;;;;;WASG;QACI,MAAM,CAAC,KAAK,EAAE,iBAAiB,EAAG,WAAW,EAAE,MAAM,EAAG,SAAS,GAAE,MAAe,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QAmErL;;WAEG;QACH,SAAS,CAAC,QAAQ,IAAI,OAAO;QAI7B;;WAEG;QACH,SAAS,CAAC,UAAU,IAAI,IAAI;KAG/B;CAEA"}
@@ -1,2 +1,2 @@
1
- sap.ui.define(["./BasePlugin","sap/m/Button"],function(t,e){"use strict";const i=t["BasePlugin"];class s extends i{render(t,i,s="meta",a,n){this.onChange=n;this.metadata=t;const o=i.startsWith("/")?i.substring(1):i;const r={type:"array",title:t.ui?.label||o,items:t.items||{type:"object",properties:{}}};if(t.uiLayout){r.uiLayout=t.uiLayout}this.control=new e({id:this.generateStableId(a,i),text:!this.isEditable?"View Records":"Edit Records",icon:!this.isEditable?"sap-icon://display":"sap-icon://list",press:e=>{const a=e.getSource();const n=a.getModel(s);if(!n)return;const l=a.getBindingContext(s);let u=i;if(l&&!i.startsWith("/")){const t=l.getPath();u=t.endsWith("/")?t+i:t==="/"?"/"+i:t+"/"+i}const c=n.getProperty(u)||[];sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/host/GeneratorHost"],e=>{const i=new e({schemaDefinition:r,data:c,editable:this.isEditable});if(!!this.isEditable){i.attachSubmit(t=>{const e=t.getParameter("payload");n.setProperty(u,e)})}const s=t.ui?.dialogButtonText||(!this.isEditable?"Close":"OK");i.openInDialog(`Nested Records: ${t.ui?.label||o}`,s)})}});return this.control}getValue(){return null}applyState(){}}var a={__esModule:true};a.ArrayPlugin=s;return a});
1
+ sap.ui.define(["./BasePlugin","sap/m/Button"],function(t,e){"use strict";const i=t["BasePlugin"];class s extends i{render(t,i,s="meta",n,a){this.onChange=a;this.metadata=t;const o=i.startsWith("/")?i.substring(1):i;const r={type:"array",title:t.ui?.label||o,items:t.items||{type:"object",properties:{}}};if(t.uiLayout){r.uiLayout=t.uiLayout}this.control=new e({id:this.generateStableId(n,i),text:!this.isEditable?"View Records":"Edit Records",icon:!this.isEditable?"sap-icon://display":"sap-icon://list",press:e=>{const n=e.getSource();const a=n.getModel(s);if(!a)return;const l=n.getBindingContext(s);let u=i;if(l&&!i.startsWith("/")){const t=l.getPath();u=t.endsWith("/")?t+i:t==="/"?"/"+i:t+"/"+i}const c=JSON.parse(JSON.stringify(a.getProperty(u)||[]));sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/DynamicHost"],e=>{const i=new e({schemaDefinition:r,data:c,editable:this.isEditable});if(!!this.isEditable){i.attachSubmit(t=>{const e=t.getParameter("payload");a.setProperty(u,e);if(this.onChange){this.onChange(true,o)}})}const s=t.ui?.dialogButtonText||(!this.isEditable?"Close":"OK");i.openInDialog(`Nested Records: ${t.ui?.label||o}`,s)})}});return this.control}getValue(){return null}applyState(){}}var n={__esModule:true};n.ArrayPlugin=s;return n});
2
2
  //# sourceMappingURL=ArrayPlugin.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ArrayPlugin.js","names":["BasePlugin","___BasePlugin","ArrayPlugin","render","field","bindingPath","modelName","engineScopeId","onChange","this","metadata","propKey","startsWith","substring","subSchema","type","title","ui","label","items","properties","uiLayout","control","Button","id","generateStableId","text","isEditable","icon","press","oEvent","btn","getSource","parentModel","getModel","bindingContext","getBindingContext","updatePath","ctxPath","getPath","endsWith","nestedData","getProperty","sap","require","GeneratorHost","host","schemaDefinition","data","editable","attachSubmit","e","payload","getParameter","setProperty","buttonText","dialogButtonText","openInDialog","getValue","applyState","__exports","__esModule"],"sources":["ArrayPlugin.ts"],"sourcesContent":["/**\n * @file ArrayPlugin.ts\n * @description Renders a button that drills down into a nested table (array) via a recursive Dialog using v2 schema.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport Button from \"sap/m/Button\";\nimport JSONModel from \"sap/ui/model/json/JSONModel\";\n\nexport class ArrayPlugin extends BasePlugin {\n /**\n * Renders a `sap.m.Button` to open a nested array form dialog.\n * \n * @param field The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured Button control.\n */\n public render(field: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = field;\n const propKey = bindingPath.startsWith(\"/\") ? bindingPath.substring(1) : bindingPath;\n \n const subSchema: ISchema = {\n type: \"array\",\n title: field.ui?.label || propKey,\n items: field.items || {\n type: \"object\",\n properties: {} // inference will handle it if empty\n }\n };\n\n if (field.uiLayout) {\n subSchema.uiLayout = field.uiLayout;\n }\n\n this.control = new Button({\n id: this.generateStableId(engineScopeId, bindingPath),\n text: !this.isEditable ? \"View Records\" : \"Edit Records\",\n icon: !this.isEditable ? \"sap-icon://display\" : \"sap-icon://list\",\n press: (oEvent: sap.ui.base.Event) => {\n const btn = oEvent.getSource() as Button;\n const parentModel = btn.getModel(modelName) as JSONModel;\n if (!parentModel) return;\n \n const bindingContext = btn.getBindingContext(modelName);\n let updatePath = bindingPath;\n if (bindingContext && !bindingPath.startsWith(\"/\")) {\n const ctxPath = bindingContext.getPath();\n updatePath = ctxPath.endsWith(\"/\") ? ctxPath + bindingPath : (ctxPath === \"/\" ? \"/\" + bindingPath : ctxPath + \"/\" + bindingPath);\n }\n \n const nestedData = parentModel.getProperty(updatePath) || [];\n\n sap.ui.require([\"nz/co/siliconst/ui5/metaui/controls/host/GeneratorHost\"], (GeneratorHost: typeof import(\"../../controls/host/GeneratorHost\").default) => {\n const host = new GeneratorHost({\n schemaDefinition: subSchema,\n data: nestedData,\n editable: this.isEditable // Pass the display mode down to the child Engine!\n });\n\n // Only attach submit event if we are not in display mode\n if (!!this.isEditable) {\n host.attachSubmit((e: sap.ui.base.Event) => {\n const payload = e.getParameter(\"payload\");\n parentModel.setProperty(updatePath, payload);\n });\n }\n\n const buttonText = field.ui?.dialogButtonText || (!this.isEditable ? \"Close\" : \"OK\");\n host.openInDialog(`Nested Records: ${field.ui?.label || propKey}`, buttonText);\n });\n }\n });\n \n return this.control as Control;\n }\n\n /**\n * Read-only component for the engine, returns null.\n */\n protected getValue(): unknown {\n return null;\n }\n\n /**\n * Read-only component, no dynamic state handling needed for the button itself.\n */\n protected applyState(): void {\n // dynamic state changes\n }\n}\n"],"mappings":"yEAAA,MAKSA,EAAUC,EAAA,cAMZ,MAAMC,UAAoBF,EAWtBG,OAAOC,EAA2BC,EAAsBC,EAAoB,OAAQC,EAAwBC,GAC/GC,KAAKD,SAAWA,EAChBC,KAAKC,SAAWN,EAChB,MAAMO,EAAUN,EAAYO,WAAW,KAAOP,EAAYQ,UAAU,GAAKR,EAEzE,MAAMS,EAAqB,CACvBC,KAAM,QACNC,MAAOZ,EAAMa,IAAIC,OAASP,EAC1BQ,MAAOf,EAAMe,OAAS,CAClBJ,KAAM,SACNK,WAAY,CAAC,IAIrB,GAAIhB,EAAMiB,SAAU,CAChBP,EAAUO,SAAWjB,EAAMiB,QAC/B,CAEAZ,KAAKa,QAAU,IAAIC,EAAO,CACtBC,GAAIf,KAAKgB,iBAAiBlB,EAAeF,GACzCqB,MAAOjB,KAAKkB,WAAa,eAAiB,eAC1CC,MAAOnB,KAAKkB,WAAa,qBAAuB,kBAChDE,MAAQC,IACJ,MAAMC,EAAMD,EAAOE,YACnB,MAAMC,EAAcF,EAAIG,SAAS5B,GACjC,IAAK2B,EAAa,OAElB,MAAME,EAAiBJ,EAAIK,kBAAkB9B,GAC7C,IAAI+B,EAAahC,EACjB,GAAI8B,IAAmB9B,EAAYO,WAAW,KAAM,CAChD,MAAM0B,EAAUH,EAAeI,UAC/BF,EAAaC,EAAQE,SAAS,KAAOF,EAAUjC,EAAeiC,IAAY,IAAM,IAAMjC,EAAciC,EAAU,IAAMjC,CACxH,CAEA,MAAMoC,EAAaR,EAAYS,YAAYL,IAAe,GAE1DM,IAAI1B,GAAG2B,QAAQ,CAAC,0DAA4DC,IACxE,MAAMC,EAAO,IAAID,EAAc,CAC3BE,iBAAkBjC,EAClBkC,KAAMP,EACNQ,SAAUxC,KAAKkB,aAInB,KAAMlB,KAAKkB,WAAY,CACnBmB,EAAKI,aAAcC,IACf,MAAMC,EAAUD,EAAEE,aAAa,WAC/BpB,EAAYqB,YAAYjB,EAAYe,IAE5C,CAEA,MAAMG,EAAanD,EAAMa,IAAIuC,oBAAsB/C,KAAKkB,WAAa,QAAU,MAC/EmB,EAAKW,aAAa,mBAAmBrD,EAAMa,IAAIC,OAASP,IAAW4C,QAK/E,OAAO9C,KAAKa,OAChB,CAKUoC,WACN,OAAO,IACX,CAKUC,aACN,EAEP,IAAAC,EAAA,CAAAC,WAAA,MAAAD,EAAA1D,cAAA,OAAA0D,CAAA","ignoreList":[]}
1
+ {"version":3,"file":"ArrayPlugin.js","names":["BasePlugin","___BasePlugin","ArrayPlugin","render","field","bindingPath","modelName","engineScopeId","onChange","this","metadata","propKey","startsWith","substring","subSchema","type","title","ui","label","items","properties","uiLayout","control","Button","id","generateStableId","text","isEditable","icon","press","oEvent","btn","getSource","parentModel","getModel","bindingContext","getBindingContext","updatePath","ctxPath","getPath","endsWith","nestedData","JSON","parse","stringify","getProperty","sap","require","DynamicHost","host","schemaDefinition","data","editable","attachSubmit","e","payload","getParameter","setProperty","buttonText","dialogButtonText","openInDialog","getValue","applyState","__exports","__esModule"],"sources":["ArrayPlugin.ts"],"sourcesContent":["/**\n * @file ArrayPlugin.ts\n * @description Renders a button that drills down into a nested table (array) via a recursive Dialog using v2 schema.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport Button from \"sap/m/Button\";\nimport JSONModel from \"sap/ui/model/json/JSONModel\";\n\nexport class ArrayPlugin extends BasePlugin {\n /**\n * Renders a `sap.m.Button` to open a nested array form dialog.\n * \n * @param field The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured Button control.\n */\n public render(field: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = field;\n const propKey = bindingPath.startsWith(\"/\") ? bindingPath.substring(1) : bindingPath;\n \n const subSchema: ISchema = {\n type: \"array\",\n title: field.ui?.label || propKey,\n items: field.items || {\n type: \"object\",\n properties: {} // inference will handle it if empty\n }\n };\n\n if (field.uiLayout) {\n subSchema.uiLayout = field.uiLayout;\n }\n\n this.control = new Button({\n id: this.generateStableId(engineScopeId, bindingPath),\n text: !this.isEditable ? \"View Records\" : \"Edit Records\",\n icon: !this.isEditable ? \"sap-icon://display\" : \"sap-icon://list\",\n press: (oEvent: sap.ui.base.Event) => {\n const btn = oEvent.getSource() as Button;\n const parentModel = btn.getModel(modelName) as JSONModel;\n if (!parentModel) return;\n \n const bindingContext = btn.getBindingContext(modelName);\n let updatePath = bindingPath;\n if (bindingContext && !bindingPath.startsWith(\"/\")) {\n const ctxPath = bindingContext.getPath();\n updatePath = ctxPath.endsWith(\"/\") ? ctxPath + bindingPath : (ctxPath === \"/\" ? \"/\" + bindingPath : ctxPath + \"/\" + bindingPath);\n }\n \n // Deep clone to prevent live-mutations on the parent model before 'Submit' is clicked\n const nestedData = JSON.parse(JSON.stringify(parentModel.getProperty(updatePath) || []));\n\n sap.ui.require([\"nz/co/siliconst/ui5/metaui/controls/DynamicHost\"], (DynamicHost: typeof import(\"../../controls/DynamicHost\").default) => {\n const host = new DynamicHost({\n schemaDefinition: subSchema,\n data: nestedData,\n editable: this.isEditable // Pass the display mode down to the child Engine!\n });\n\n // Only attach submit event if we are not in display mode\n if (!!this.isEditable) {\n host.attachSubmit((e: sap.ui.base.Event) => {\n const payload = e.getParameter(\"payload\");\n parentModel.setProperty(updatePath, payload);\n\n // CRITICAL: Notify the parent Engine that this field mutated\n // so it can trigger LiveUpdate syncs and validate!\n if (this.onChange) {\n this.onChange(true, propKey);\n }\n });\n }\n\n const buttonText = field.ui?.dialogButtonText || (!this.isEditable ? \"Close\" : \"OK\");\n host.openInDialog(`Nested Records: ${field.ui?.label || propKey}`, buttonText);\n });\n }\n });\n \n return this.control as Control;\n }\n\n /**\n * Read-only component for the engine, returns null.\n */\n protected getValue(): unknown {\n return null;\n }\n\n /**\n * Read-only component, no dynamic state handling needed for the button itself.\n */\n protected applyState(): void {\n // dynamic state changes\n }\n}\n"],"mappings":"yEAAA,MAKSA,EAAUC,EAAA,cAMZ,MAAMC,UAAoBF,EAWtBG,OAAOC,EAA2BC,EAAsBC,EAAoB,OAAQC,EAAwBC,GAC/GC,KAAKD,SAAWA,EAChBC,KAAKC,SAAWN,EAChB,MAAMO,EAAUN,EAAYO,WAAW,KAAOP,EAAYQ,UAAU,GAAKR,EAEzE,MAAMS,EAAqB,CACvBC,KAAM,QACNC,MAAOZ,EAAMa,IAAIC,OAASP,EAC1BQ,MAAOf,EAAMe,OAAS,CAClBJ,KAAM,SACNK,WAAY,CAAC,IAIrB,GAAIhB,EAAMiB,SAAU,CAChBP,EAAUO,SAAWjB,EAAMiB,QAC/B,CAEAZ,KAAKa,QAAU,IAAIC,EAAO,CACtBC,GAAIf,KAAKgB,iBAAiBlB,EAAeF,GACzCqB,MAAOjB,KAAKkB,WAAa,eAAiB,eAC1CC,MAAOnB,KAAKkB,WAAa,qBAAuB,kBAChDE,MAAQC,IACJ,MAAMC,EAAMD,EAAOE,YACnB,MAAMC,EAAcF,EAAIG,SAAS5B,GACjC,IAAK2B,EAAa,OAElB,MAAME,EAAiBJ,EAAIK,kBAAkB9B,GAC7C,IAAI+B,EAAahC,EACjB,GAAI8B,IAAmB9B,EAAYO,WAAW,KAAM,CAChD,MAAM0B,EAAUH,EAAeI,UAC/BF,EAAaC,EAAQE,SAAS,KAAOF,EAAUjC,EAAeiC,IAAY,IAAM,IAAMjC,EAAciC,EAAU,IAAMjC,CACxH,CAGA,MAAMoC,EAAaC,KAAKC,MAAMD,KAAKE,UAAUX,EAAYY,YAAYR,IAAe,KAEpFS,IAAI7B,GAAG8B,QAAQ,CAAC,mDAAqDC,IACjE,MAAMC,EAAO,IAAID,EAAY,CACzBE,iBAAkBpC,EAClBqC,KAAMV,EACNW,SAAU3C,KAAKkB,aAInB,KAAMlB,KAAKkB,WAAY,CACnBsB,EAAKI,aAAcC,IACf,MAAMC,EAAUD,EAAEE,aAAa,WAC/BvB,EAAYwB,YAAYpB,EAAYkB,GAIpC,GAAI9C,KAAKD,SAAU,CACfC,KAAKD,SAAS,KAAMG,EACxB,GAER,CAEA,MAAM+C,EAAatD,EAAMa,IAAI0C,oBAAsBlD,KAAKkB,WAAa,QAAU,MAC/EsB,EAAKW,aAAa,mBAAmBxD,EAAMa,IAAIC,OAASP,IAAW+C,QAK/E,OAAOjD,KAAKa,OAChB,CAKUuC,WACN,OAAO,IACX,CAKUC,aACN,EAEP,IAAAC,EAAA,CAAAC,WAAA,MAAAD,EAAA7D,cAAA,OAAA6D,CAAA","ignoreList":[]}
@@ -54,10 +54,11 @@ export class ArrayPlugin extends BasePlugin {
54
54
  updatePath = ctxPath.endsWith("/") ? ctxPath + bindingPath : (ctxPath === "/" ? "/" + bindingPath : ctxPath + "/" + bindingPath);
55
55
  }
56
56
 
57
- const nestedData = parentModel.getProperty(updatePath) || [];
57
+ // Deep clone to prevent live-mutations on the parent model before 'Submit' is clicked
58
+ const nestedData = JSON.parse(JSON.stringify(parentModel.getProperty(updatePath) || []));
58
59
 
59
- sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/host/GeneratorHost"], (GeneratorHost: typeof import("../../controls/host/GeneratorHost").default) => {
60
- const host = new GeneratorHost({
60
+ sap.ui.require(["nz/co/siliconst/ui5/metaui/controls/DynamicHost"], (DynamicHost: typeof import("../../controls/DynamicHost").default) => {
61
+ const host = new DynamicHost({
61
62
  schemaDefinition: subSchema,
62
63
  data: nestedData,
63
64
  editable: this.isEditable // Pass the display mode down to the child Engine!
@@ -68,6 +69,12 @@ export class ArrayPlugin extends BasePlugin {
68
69
  host.attachSubmit((e: sap.ui.base.Event) => {
69
70
  const payload = e.getParameter("payload");
70
71
  parentModel.setProperty(updatePath, payload);
72
+
73
+ // CRITICAL: Notify the parent Engine that this field mutated
74
+ // so it can trigger LiveUpdate syncs and validate!
75
+ if (this.onChange) {
76
+ this.onChange(true, propKey);
77
+ }
71
78
  });
72
79
  }
73
80
 
@@ -138,18 +138,29 @@ sap.ui.define(["../../core/PipelineManager"], function (____core_PipelineManager
138
138
  control.setEditable(!metadata.ui.readOnly);
139
139
  }
140
140
  if (metadata.ui?.visibleOn) {
141
- const expr = `{= ${metadata.ui.visibleOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
141
+ const ExpressionBuilder = sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;
142
+ let expr = "";
143
+ if (ExpressionBuilder) {
144
+ expr = ExpressionBuilder.build(metadata.ui.visibleOn, this.fieldKey, modelName);
145
+ } else {
146
+ expr = `{= ${metadata.ui.visibleOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
147
+ }
142
148
  control.bindProperty("visible", {
143
149
  parts: [{
144
150
  path: "meta>/"
145
151
  }],
146
152
  formatter: () => false
147
153
  });
148
- // The ConditionEngine handles actual binding injection, but here we can set a fallback or natively bind if we bypass ConditionEngine.
149
154
  control.bindProperty("visible", expr);
150
155
  }
151
156
  if (metadata.ui?.enabledOn && typeof control.setEnabled === "function") {
152
- const expr = `{= ${metadata.ui.enabledOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
157
+ const ExpressionBuilder = sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;
158
+ let expr = "";
159
+ if (ExpressionBuilder) {
160
+ expr = ExpressionBuilder.build(metadata.ui.enabledOn, this.fieldKey, modelName);
161
+ } else {
162
+ expr = `{= ${metadata.ui.enabledOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
163
+ }
153
164
  control.bindProperty("enabled", expr);
154
165
  }
155
166
  }
@@ -1 +1 @@
1
- {"version":3,"file":"BasePlugin-dbg.js","names":["GlobalPipeline","____core_PipelineManager","BasePlugin","control","metadata","fieldKey","modelName","isEditable","setEditable","editable","generateStableId","engineScopeId","bindingPath","undefined","safePath","replace","validate","isValid","getVisible","validatorsToRun","argsMap","maxLength","required","push","ui","validators","v","name","args","length","errorMessage","val","getValue","result","executeValidation","onStateChange","newMetadata","applyState","applyCommonDirectives","readOnly","visibleOn","expr","bindProperty","parts","path","formatter","enabledOn","setEnabled","destroy","__exports","__esModule"],"sources":["BasePlugin.ts"],"sourcesContent":["/**\n * @file BasePlugin.ts\n * @description Abstract foundation for all MetaUI plugins, enforcing lifecycle hooks for v2 Schema.\n */\n\nimport { IPlugin } from \"../../interfaces/IPlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport { GlobalPipeline } from \"../../core/PipelineManager\";\n\n/**\n * Abstract class representing a standard MetaUI Plugin.\n * Enforces the required rendering, state extraction, and validation contracts.\n * \n * @abstract\n * @public\n */\nexport abstract class BasePlugin implements IPlugin {\n /** The instantiated UI5 control for this plugin. */\n protected control: Control | null = null;\n \n /** The metadata schema defining the field rules. */\n protected metadata: IPropertyMetadata | null = null;\n \n /** The internal JSON path of the field relative to its parent payload. */\n protected fieldKey: string = \"\";\n \n /** The UI5 JSONModel name used for absolute binding paths. */\n protected modelName: string = \"meta\";\n\n /** Indicates if the engine is enforcing an editable mode. */\n protected isEditable: boolean = true;\n \n /** Internal callback provided by GeneratorHost to signal validation/data changes upwards */\n protected onChange?: (isValid: boolean, fieldKey?: string, errorMessage?: string, controlId?: string) => void;\n\n /**\n * Injects the global editable mode context into the plugin before rendering.\n * @param editable True if the plugin should render in editable mode.\n */\n public setEditable(editable: boolean): void {\n this.isEditable = editable;\n }\n\n /**\n * Instantiates the raw UI5 control and binds it to the model.\n * \n * @param fieldMetadata The JSON Schema for the field.\n * @param bindingPath The JSON path to bind to.\n * @param modelName The UI5 model name.\n * @param engineScopeId The deterministic scope ID provided by the Engine to prevent cloning collisions.\n * @param onChange The callback fired natively when a field value blur/change occurs.\n * @returns {Control} The generated UI5 control.\n */\n public abstract render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName?: string, engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control;\n\n /**\n * Generates a deterministic, globally unique ID for this control.\n * Prefixes the sanitized binding path with the Engine's scoped ID.\n */\n protected generateStableId(engineScopeId: string | undefined, bindingPath: string): string | undefined {\n if (!engineScopeId) return undefined;\n // Strip leading slash and replace internal slashes with hyphens\n const safePath = bindingPath.replace(/^\\//, '').replace(/\\//g, '-');\n return `${engineScopeId}--${safePath}`;\n }\n\n /**\n * Extracts the current raw value from the underlying UI5 control.\n */\n protected abstract getValue(): unknown;\n\n /**\n * Universal pipeline validation.\n */\n public validate(): import(\"../../interfaces/IPlugin\").IPluginValidationResult {\n if (!this.control || !this.metadata) return { isValid: true };\n \n // Skip validation for hidden fields (e.g. hidden by ConditionEngine visibleOn)\n if (typeof (this.control as Control).getVisible === \"function\") {\n if (!(this.control as Control).getVisible()) {\n return { isValid: true };\n }\n }\n \n const validatorsToRun: string[] = [];\n const argsMap: Record<string, unknown> = {\n \"maxLength\": this.metadata.maxLength\n };\n\n if (this.metadata.required) {\n validatorsToRun.push(\"required\");\n }\n if (this.metadata.maxLength) validatorsToRun.push(\"maxLength\");\n \n if (this.metadata.ui?.validators) {\n for (const v of this.metadata.ui.validators) {\n if (typeof v === \"string\") {\n validatorsToRun.push(v);\n } else if (v && v.name) {\n validatorsToRun.push(v.name);\n if (v.args !== undefined) {\n argsMap[v.name] = v.args;\n }\n }\n }\n }\n\n if (validatorsToRun.length === 0) {\n return { isValid: true, errorMessage: undefined, fieldKey: this.fieldKey };\n }\n\n const val = this.getValue();\n const result = GlobalPipeline.executeValidation(val, validatorsToRun, argsMap);\n return { isValid: result.isValid, errorMessage: result.errorMessage, fieldKey: this.fieldKey };\n }\n\n /**\n * Executes when the condition engine pushes new schema metadata to this field (e.g. readOnly changing).\n * @param newMetadata The mutated schema metadata.\n */\n public onStateChange(newMetadata: IPropertyMetadata): void {\n this.metadata = newMetadata;\n this.applyState();\n }\n\n /**\n * Abstract hook for the plugin to apply state changes to its specific UI5 control (e.g. placeholders, labels).\n */\n protected abstract applyState(): void;\n\n /**\n * Helper to apply common UI directives (like readOnly, visibleOn) directly to any control.\n */\n protected applyCommonDirectives(control: Control, metadata: IPropertyMetadata, modelName: string = \"meta\"): void {\n if (metadata.ui?.readOnly !== undefined && typeof control.setEditable === \"function\") {\n control.setEditable(!metadata.ui.readOnly);\n }\n\n if (metadata.ui?.visibleOn) {\n const expr = `{= ${metadata.ui.visibleOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n control.bindProperty(\"visible\", { parts: [{ path: \"meta>/\" }], formatter: () => false });\n // The ConditionEngine handles actual binding injection, but here we can set a fallback or natively bind if we bypass ConditionEngine.\n control.bindProperty(\"visible\", expr);\n }\n \n if (metadata.ui?.enabledOn && typeof control.setEnabled === \"function\") {\n const expr = `{= ${metadata.ui.enabledOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n control.bindProperty(\"enabled\", expr);\n }\n }\n\n\n\n /**\n * Natively destroys the instantiated UI5 control to prevent memory leaks.\n * Can be overridden by subclasses if they manage secondary controls or custom models.\n */\n public destroy(): void {\n if (this.control && typeof this.control.destroy === \"function\") {\n this.control.destroy();\n this.control = null;\n }\n }\n}\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"file":"BasePlugin-dbg.js","names":["GlobalPipeline","____core_PipelineManager","BasePlugin","control","metadata","fieldKey","modelName","isEditable","setEditable","editable","generateStableId","engineScopeId","bindingPath","undefined","safePath","replace","validate","isValid","getVisible","validatorsToRun","argsMap","maxLength","required","push","ui","validators","v","name","args","length","errorMessage","val","getValue","result","executeValidation","onStateChange","newMetadata","applyState","applyCommonDirectives","readOnly","visibleOn","ExpressionBuilder","sap","require","expr","build","bindProperty","parts","path","formatter","enabledOn","setEnabled","destroy","__exports","__esModule"],"sources":["BasePlugin.ts"],"sourcesContent":["/**\n * @file BasePlugin.ts\n * @description Abstract foundation for all MetaUI plugins, enforcing lifecycle hooks for v2 Schema.\n */\n\nimport { IPlugin } from \"../../interfaces/IPlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport { GlobalPipeline } from \"../../core/PipelineManager\";\n\n/**\n * Abstract class representing a standard MetaUI Plugin.\n * Enforces the required rendering, state extraction, and validation contracts.\n * \n * @abstract\n * @public\n */\nexport abstract class BasePlugin implements IPlugin {\n /** The instantiated UI5 control for this plugin. */\n protected control: Control | null = null;\n \n /** The metadata schema defining the field rules. */\n protected metadata: IPropertyMetadata | null = null;\n \n /** The internal JSON path of the field relative to its parent payload. */\n protected fieldKey: string = \"\";\n \n /** The UI5 JSONModel name used for absolute binding paths. */\n protected modelName: string = \"meta\";\n\n /** Indicates if the engine is enforcing an editable mode. */\n protected isEditable: boolean = true;\n \n /** Internal callback provided by GeneratorHost to signal validation/data changes upwards */\n protected onChange?: (isValid: boolean, fieldKey?: string, errorMessage?: string, controlId?: string) => void;\n\n /**\n * Injects the global editable mode context into the plugin before rendering.\n * @param editable True if the plugin should render in editable mode.\n */\n public setEditable(editable: boolean): void {\n this.isEditable = editable;\n }\n\n /**\n * Instantiates the raw UI5 control and binds it to the model.\n * \n * @param fieldMetadata The JSON Schema for the field.\n * @param bindingPath The JSON path to bind to.\n * @param modelName The UI5 model name.\n * @param engineScopeId The deterministic scope ID provided by the Engine to prevent cloning collisions.\n * @param onChange The callback fired natively when a field value blur/change occurs.\n * @returns {Control} The generated UI5 control.\n */\n public abstract render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName?: string, engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control;\n\n /**\n * Generates a deterministic, globally unique ID for this control.\n * Prefixes the sanitized binding path with the Engine's scoped ID.\n */\n protected generateStableId(engineScopeId: string | undefined, bindingPath: string): string | undefined {\n if (!engineScopeId) return undefined;\n // Strip leading slash and replace internal slashes with hyphens\n const safePath = bindingPath.replace(/^\\//, '').replace(/\\//g, '-');\n return `${engineScopeId}--${safePath}`;\n }\n\n /**\n * Extracts the current raw value from the underlying UI5 control.\n */\n protected abstract getValue(): unknown;\n\n /**\n * Universal pipeline validation.\n */\n public validate(): import(\"../../interfaces/IPlugin\").IPluginValidationResult {\n if (!this.control || !this.metadata) return { isValid: true };\n \n // Skip validation for hidden fields (e.g. hidden by ConditionEngine visibleOn)\n if (typeof (this.control as Control).getVisible === \"function\") {\n if (!(this.control as Control).getVisible()) {\n return { isValid: true };\n }\n }\n \n const validatorsToRun: string[] = [];\n const argsMap: Record<string, unknown> = {\n \"maxLength\": this.metadata.maxLength\n };\n\n if (this.metadata.required) {\n validatorsToRun.push(\"required\");\n }\n if (this.metadata.maxLength) validatorsToRun.push(\"maxLength\");\n \n if (this.metadata.ui?.validators) {\n for (const v of this.metadata.ui.validators) {\n if (typeof v === \"string\") {\n validatorsToRun.push(v);\n } else if (v && v.name) {\n validatorsToRun.push(v.name);\n if (v.args !== undefined) {\n argsMap[v.name] = v.args;\n }\n }\n }\n }\n\n if (validatorsToRun.length === 0) {\n return { isValid: true, errorMessage: undefined, fieldKey: this.fieldKey };\n }\n\n const val = this.getValue();\n const result = GlobalPipeline.executeValidation(val, validatorsToRun, argsMap);\n return { isValid: result.isValid, errorMessage: result.errorMessage, fieldKey: this.fieldKey };\n }\n\n /**\n * Executes when the condition engine pushes new schema metadata to this field (e.g. readOnly changing).\n * @param newMetadata The mutated schema metadata.\n */\n public onStateChange(newMetadata: IPropertyMetadata): void {\n this.metadata = newMetadata;\n this.applyState();\n }\n\n /**\n * Abstract hook for the plugin to apply state changes to its specific UI5 control (e.g. placeholders, labels).\n */\n protected abstract applyState(): void;\n\n /**\n * Helper to apply common UI directives (like readOnly, visibleOn) directly to any control.\n */\n protected applyCommonDirectives(control: Control, metadata: IPropertyMetadata, modelName: string = \"meta\"): void {\n if (metadata.ui?.readOnly !== undefined && typeof control.setEditable === \"function\") {\n control.setEditable(!metadata.ui.readOnly);\n }\n\n if (metadata.ui?.visibleOn) {\n const ExpressionBuilder = sap.ui.require(\"nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder\")?.ExpressionBuilder;\n let expr = \"\";\n if (ExpressionBuilder) {\n expr = ExpressionBuilder.build(metadata.ui.visibleOn, this.fieldKey, modelName);\n } else {\n expr = `{= ${metadata.ui.visibleOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n }\n control.bindProperty(\"visible\", { parts: [{ path: \"meta>/\" }], formatter: () => false });\n control.bindProperty(\"visible\", expr);\n }\n \n if (metadata.ui?.enabledOn && typeof control.setEnabled === \"function\") {\n const ExpressionBuilder = sap.ui.require(\"nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder\")?.ExpressionBuilder;\n let expr = \"\";\n if (ExpressionBuilder) {\n expr = ExpressionBuilder.build(metadata.ui.enabledOn, this.fieldKey, modelName);\n } else {\n expr = `{= ${metadata.ui.enabledOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n }\n control.bindProperty(\"enabled\", expr);\n }\n }\n\n\n\n /**\n * Natively destroys the instantiated UI5 control to prevent memory leaks.\n * Can be overridden by subclasses if they manage secondary controls or custom models.\n */\n public destroy(): void {\n if (this.control && typeof this.control.destroy === \"function\") {\n this.control.destroy();\n this.control = null;\n }\n }\n}\n"],"mappings":";;;EAAA;AACA;AACA;AACA;EAHA,MAQSA,cAAc,GAAAC,wBAAA;EAEvB;AACA;AACA;AACA;AACA;AACA;AACA;EACO,MAAeC,UAAU,CAAoB;IAChD;IACUC,OAAO,GAAmB,IAAI;;IAExC;IACUC,QAAQ,GAA6B,IAAI;;IAEnD;IACUC,QAAQ,GAAW,EAAE;;IAE/B;IACUC,SAAS,GAAW,MAAM;;IAEpC;IACUC,UAAU,GAAY,IAAI;;IAEpC;;IAGA;AACJ;AACA;AACA;IACWC,WAAWA,CAACC,QAAiB,EAAQ;MACxC,IAAI,CAACF,UAAU,GAAGE,QAAQ;IAC9B;;IAEA;AACJ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;IAGI;AACJ;AACA;AACA;IACcC,gBAAgBA,CAACC,aAAiC,EAAEC,WAAmB,EAAsB;MACnG,IAAI,CAACD,aAAa,EAAE,OAAOE,SAAS;MACpC;MACA,MAAMC,QAAQ,GAAGF,WAAW,CAACG,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAACA,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC;MACnE,OAAO,GAAGJ,aAAa,KAAKG,QAAQ,EAAE;IAC1C;;IAEA;AACJ;AACA;;IAGI;AACJ;AACA;IACWE,QAAQA,CAAA,EAA+D;MAC1E,IAAI,CAAC,IAAI,CAACb,OAAO,IAAI,CAAC,IAAI,CAACC,QAAQ,EAAE,OAAO;QAAEa,OAAO,EAAE;MAAK,CAAC;;MAE7D;MACA,IAAI,OAAQ,IAAI,CAACd,OAAO,CAAae,UAAU,KAAK,UAAU,EAAE;QAC5D,IAAI,CAAE,IAAI,CAACf,OAAO,CAAae,UAAU,CAAC,CAAC,EAAE;UACzC,OAAO;YAAED,OAAO,EAAE;UAAK,CAAC;QAC5B;MACJ;MAEA,MAAME,eAAyB,GAAG,EAAE;MACpC,MAAMC,OAAgC,GAAG;QACrC,WAAW,EAAE,IAAI,CAAChB,QAAQ,CAACiB;MAC/B,CAAC;MAED,IAAI,IAAI,CAACjB,QAAQ,CAACkB,QAAQ,EAAE;QACxBH,eAAe,CAACI,IAAI,CAAC,UAAU,CAAC;MACpC;MACA,IAAI,IAAI,CAACnB,QAAQ,CAACiB,SAAS,EAAEF,eAAe,CAACI,IAAI,CAAC,WAAW,CAAC;MAE9D,IAAI,IAAI,CAACnB,QAAQ,CAACoB,EAAE,EAAEC,UAAU,EAAE;QAC9B,KAAK,MAAMC,CAAC,IAAI,IAAI,CAACtB,QAAQ,CAACoB,EAAE,CAACC,UAAU,EAAE;UACzC,IAAI,OAAOC,CAAC,KAAK,QAAQ,EAAE;YACvBP,eAAe,CAACI,IAAI,CAACG,CAAC,CAAC;UAC3B,CAAC,MAAM,IAAIA,CAAC,IAAIA,CAAC,CAACC,IAAI,EAAE;YACpBR,eAAe,CAACI,IAAI,CAACG,CAAC,CAACC,IAAI,CAAC;YAC5B,IAAID,CAAC,CAACE,IAAI,KAAKf,SAAS,EAAE;cACtBO,OAAO,CAACM,CAAC,CAACC,IAAI,CAAC,GAAGD,CAAC,CAACE,IAAI;YAC5B;UACJ;QACJ;MACJ;MAEA,IAAIT,eAAe,CAACU,MAAM,KAAK,CAAC,EAAE;QAC9B,OAAO;UAAEZ,OAAO,EAAE,IAAI;UAAEa,YAAY,EAAEjB,SAAS;UAAER,QAAQ,EAAE,IAAI,CAACA;QAAS,CAAC;MAC9E;MAEA,MAAM0B,GAAG,GAAG,IAAI,CAACC,QAAQ,CAAC,CAAC;MAC3B,MAAMC,MAAM,GAAGjC,cAAc,CAACkC,iBAAiB,CAACH,GAAG,EAAEZ,eAAe,EAAEC,OAAO,CAAC;MAC9E,OAAO;QAAEH,OAAO,EAAEgB,MAAM,CAAChB,OAAO;QAAEa,YAAY,EAAEG,MAAM,CAACH,YAAY;QAAEzB,QAAQ,EAAE,IAAI,CAACA;MAAS,CAAC;IAClG;;IAEA;AACJ;AACA;AACA;IACW8B,aAAaA,CAACC,WAA8B,EAAQ;MACvD,IAAI,CAAChC,QAAQ,GAAGgC,WAAW;MAC3B,IAAI,CAACC,UAAU,CAAC,CAAC;IACrB;;IAEA;AACJ;AACA;;IAGI;AACJ;AACA;IACcC,qBAAqBA,CAACnC,OAAgB,EAAEC,QAA2B,EAAEE,SAAiB,GAAG,MAAM,EAAQ;MAC7G,IAAIF,QAAQ,CAACoB,EAAE,EAAEe,QAAQ,KAAK1B,SAAS,IAAI,OAAOV,OAAO,CAACK,WAAW,KAAK,UAAU,EAAE;QAClFL,OAAO,CAACK,WAAW,CAAC,CAACJ,QAAQ,CAACoB,EAAE,CAACe,QAAQ,CAAC;MAC9C;MAEA,IAAInC,QAAQ,CAACoB,EAAE,EAAEgB,SAAS,EAAE;QACxB,MAAMC,iBAAiB,GAAGC,GAAG,CAAClB,EAAE,CAACmB,OAAO,CAAC,oDAAoD,CAAC,EAAEF,iBAAiB;QACjH,IAAIG,IAAI,GAAG,EAAE;QACb,IAAIH,iBAAiB,EAAE;UACnBG,IAAI,GAAGH,iBAAiB,CAACI,KAAK,CAACzC,QAAQ,CAACoB,EAAE,CAACgB,SAAS,EAAE,IAAI,CAACnC,QAAQ,EAAEC,SAAS,CAAC;QACnF,CAAC,MAAM;UACHsC,IAAI,GAAG,MAAMxC,QAAQ,CAACoB,EAAE,CAACgB,SAAS,CAACzB,OAAO,CAAC,WAAW,EAAE,GAAGT,SAAS,IAAI,CAAC,CAACS,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,IAAI;QACrG;QACAZ,OAAO,CAAC2C,YAAY,CAAC,SAAS,EAAE;UAAEC,KAAK,EAAE,CAAC;YAAEC,IAAI,EAAE;UAAS,CAAC,CAAC;UAAEC,SAAS,EAAEA,CAAA,KAAM;QAAM,CAAC,CAAC;QACxF9C,OAAO,CAAC2C,YAAY,CAAC,SAAS,EAAEF,IAAI,CAAC;MACzC;MAEA,IAAIxC,QAAQ,CAACoB,EAAE,EAAE0B,SAAS,IAAI,OAAO/C,OAAO,CAACgD,UAAU,KAAK,UAAU,EAAE;QACpE,MAAMV,iBAAiB,GAAGC,GAAG,CAAClB,EAAE,CAACmB,OAAO,CAAC,oDAAoD,CAAC,EAAEF,iBAAiB;QACjH,IAAIG,IAAI,GAAG,EAAE;QACb,IAAIH,iBAAiB,EAAE;UACnBG,IAAI,GAAGH,iBAAiB,CAACI,KAAK,CAACzC,QAAQ,CAACoB,EAAE,CAAC0B,SAAS,EAAE,IAAI,CAAC7C,QAAQ,EAAEC,SAAS,CAAC;QACnF,CAAC,MAAM;UACHsC,IAAI,GAAG,MAAMxC,QAAQ,CAACoB,EAAE,CAAC0B,SAAS,CAACnC,OAAO,CAAC,WAAW,EAAE,GAAGT,SAAS,IAAI,CAAC,CAACS,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,IAAI;QACrG;QACAZ,OAAO,CAAC2C,YAAY,CAAC,SAAS,EAAEF,IAAI,CAAC;MACzC;IACJ;;IAIA;AACJ;AACA;AACA;IACWQ,OAAOA,CAAA,EAAS;MACnB,IAAI,IAAI,CAACjD,OAAO,IAAI,OAAO,IAAI,CAACA,OAAO,CAACiD,OAAO,KAAK,UAAU,EAAE;QAC5D,IAAI,CAACjD,OAAO,CAACiD,OAAO,CAAC,CAAC;QACtB,IAAI,CAACjD,OAAO,GAAG,IAAI;MACvB;IACJ;EACJ;EAAC,IAAAkD,SAAA;IAAAC,UAAA;EAAA;EAAAD,SAAA,CAAAnD,UAAA,GAAAA,UAAA;EAAA,OAAAmD,SAAA;AAAA","ignoreList":[]}
@@ -1 +1 @@
1
- {"version":3,"file":"BasePlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,wDAAwD,CAAC;IACxE;;;OAGG;IAEH,OAAO,EAAE,OAAO,EAAE,MAAM,+CAA+C,CAAC;IACxE,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAG1C;;;;;;OAMG;IACH,eAAsB,UAAW,YAAW,OAAO;QAC/C,oDAAoD;QACpD,SAAS,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAAQ;QAEzC,oDAAoD;QACpD,SAAS,CAAC,QAAQ,EAAE,iBAAiB,GAAG,IAAI,CAAQ;QAEpD,0EAA0E;QAC1E,SAAS,CAAC,QAAQ,EAAE,MAAM,CAAM;QAEhC,8DAA8D;QAC9D,SAAS,CAAC,SAAS,EAAE,MAAM,CAAU;QAErC,6DAA6D;QAC7D,SAAS,CAAC,UAAU,EAAE,OAAO,CAAQ;QAErC,4FAA4F;QAC5F,SAAS,CAAC,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,EAAE,YAAY,CAAC,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;QAE9G;;;WAGG;QACI,WAAW,CAAC,QAAQ,EAAE,OAAO,GAAG,IAAI;QAI3C;;;;;;;;;WASG;iBACa,MAAM,CAAC,aAAa,EAAE,iBAAiB,EAAE,WAAW,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QAE5L;;;WAGG;QACH,SAAS,CAAC,gBAAgB,CAAC,aAAa,EAAE,MAAM,GAAG,SAAS,EAAE,WAAW,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS;QAOtG;;WAEG;QACH,SAAS,CAAC,QAAQ,CAAC,QAAQ,IAAI,OAAO;QAEtC;;WAEG;QACI,QAAQ,IAAI,OAAO,+CAA+C,EAAE,uBAAuB;QA0ClG;;;WAGG;QACI,aAAa,CAAC,WAAW,EAAE,iBAAiB,GAAG,IAAI;QAK1D;;WAEG;QACH,SAAS,CAAC,QAAQ,CAAC,UAAU,IAAI,IAAI;QAErC;;WAEG;QACH,SAAS,CAAC,qBAAqB,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,iBAAiB,EAAE,SAAS,GAAE,MAAe,GAAG,IAAI;QAoBhH;;;WAGG;QACI,OAAO,IAAI,IAAI;KAMzB;CAEA"}
1
+ {"version":3,"file":"BasePlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/BasePlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,wDAAwD,CAAC;IACxE;;;OAGG;IAEH,OAAO,EAAE,OAAO,EAAE,MAAM,+CAA+C,CAAC;IACxE,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAG1C;;;;;;OAMG;IACH,eAAsB,UAAW,YAAW,OAAO;QAC/C,oDAAoD;QACpD,SAAS,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAAQ;QAEzC,oDAAoD;QACpD,SAAS,CAAC,QAAQ,EAAE,iBAAiB,GAAG,IAAI,CAAQ;QAEpD,0EAA0E;QAC1E,SAAS,CAAC,QAAQ,EAAE,MAAM,CAAM;QAEhC,8DAA8D;QAC9D,SAAS,CAAC,SAAS,EAAE,MAAM,CAAU;QAErC,6DAA6D;QAC7D,SAAS,CAAC,UAAU,EAAE,OAAO,CAAQ;QAErC,4FAA4F;QAC5F,SAAS,CAAC,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,EAAE,YAAY,CAAC,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;QAE9G;;;WAGG;QACI,WAAW,CAAC,QAAQ,EAAE,OAAO,GAAG,IAAI;QAI3C;;;;;;;;;WASG;iBACa,MAAM,CAAC,aAAa,EAAE,iBAAiB,EAAE,WAAW,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,MAAM,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QAE5L;;;WAGG;QACH,SAAS,CAAC,gBAAgB,CAAC,aAAa,EAAE,MAAM,GAAG,SAAS,EAAE,WAAW,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS;QAOtG;;WAEG;QACH,SAAS,CAAC,QAAQ,CAAC,QAAQ,IAAI,OAAO;QAEtC;;WAEG;QACI,QAAQ,IAAI,OAAO,+CAA+C,EAAE,uBAAuB;QA0ClG;;;WAGG;QACI,aAAa,CAAC,WAAW,EAAE,iBAAiB,GAAG,IAAI;QAK1D;;WAEG;QACH,SAAS,CAAC,QAAQ,CAAC,UAAU,IAAI,IAAI;QAErC;;WAEG;QACH,SAAS,CAAC,qBAAqB,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,iBAAiB,EAAE,SAAS,GAAE,MAAe,GAAG,IAAI;QA+BhH;;;WAGG;QACI,OAAO,IAAI,IAAI;KAMzB;CAEA"}
@@ -1,2 +1,2 @@
1
- sap.ui.define(["../../core/PipelineManager"],function(e){"use strict";const t=e["GlobalPipeline"];class i{control=null;metadata=null;fieldKey="";modelName="meta";isEditable=true;setEditable(e){this.isEditable=e}generateStableId(e,t){if(!e)return undefined;const i=t.replace(/^\//,"").replace(/\//g,"-");return`${e}--${i}`}validate(){if(!this.control||!this.metadata)return{isValid:true};if(typeof this.control.getVisible==="function"){if(!this.control.getVisible()){return{isValid:true}}}const e=[];const i={maxLength:this.metadata.maxLength};if(this.metadata.required){e.push("required")}if(this.metadata.maxLength)e.push("maxLength");if(this.metadata.ui?.validators){for(const t of this.metadata.ui.validators){if(typeof t==="string"){e.push(t)}else if(t&&t.name){e.push(t.name);if(t.args!==undefined){i[t.name]=t.args}}}}if(e.length===0){return{isValid:true,errorMessage:undefined,fieldKey:this.fieldKey}}const a=this.getValue();const n=t.executeValidation(a,e,i);return{isValid:n.isValid,errorMessage:n.errorMessage,fieldKey:this.fieldKey}}onStateChange(e){this.metadata=e;this.applyState()}applyCommonDirectives(e,t,i="meta"){if(t.ui?.readOnly!==undefined&&typeof e.setEditable==="function"){e.setEditable(!t.ui.readOnly)}if(t.ui?.visibleOn){const a=`{= ${t.ui.visibleOn.replace(/\$root\./g,`${i}>/`).replace(/\./g,"/")} }`;e.bindProperty("visible",{parts:[{path:"meta>/"}],formatter:()=>false});e.bindProperty("visible",a)}if(t.ui?.enabledOn&&typeof e.setEnabled==="function"){const a=`{= ${t.ui.enabledOn.replace(/\$root\./g,`${i}>/`).replace(/\./g,"/")} }`;e.bindProperty("enabled",a)}}destroy(){if(this.control&&typeof this.control.destroy==="function"){this.control.destroy();this.control=null}}}var a={__esModule:true};a.BasePlugin=i;return a});
1
+ sap.ui.define(["../../core/PipelineManager"],function(e){"use strict";const i=e["GlobalPipeline"];class t{control=null;metadata=null;fieldKey="";modelName="meta";isEditable=true;setEditable(e){this.isEditable=e}generateStableId(e,i){if(!e)return undefined;const t=i.replace(/^\//,"").replace(/\//g,"-");return`${e}--${t}`}validate(){if(!this.control||!this.metadata)return{isValid:true};if(typeof this.control.getVisible==="function"){if(!this.control.getVisible()){return{isValid:true}}}const e=[];const t={maxLength:this.metadata.maxLength};if(this.metadata.required){e.push("required")}if(this.metadata.maxLength)e.push("maxLength");if(this.metadata.ui?.validators){for(const i of this.metadata.ui.validators){if(typeof i==="string"){e.push(i)}else if(i&&i.name){e.push(i.name);if(i.args!==undefined){t[i.name]=i.args}}}}if(e.length===0){return{isValid:true,errorMessage:undefined,fieldKey:this.fieldKey}}const s=this.getValue();const a=i.executeValidation(s,e,t);return{isValid:a.isValid,errorMessage:a.errorMessage,fieldKey:this.fieldKey}}onStateChange(e){this.metadata=e;this.applyState()}applyCommonDirectives(e,i,t="meta"){if(i.ui?.readOnly!==undefined&&typeof e.setEditable==="function"){e.setEditable(!i.ui.readOnly)}if(i.ui?.visibleOn){const s=sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;let a="";if(s){a=s.build(i.ui.visibleOn,this.fieldKey,t)}else{a=`{= ${i.ui.visibleOn.replace(/\$root\./g,`${t}>/`).replace(/\./g,"/")} }`}e.bindProperty("visible",{parts:[{path:"meta>/"}],formatter:()=>false});e.bindProperty("visible",a)}if(i.ui?.enabledOn&&typeof e.setEnabled==="function"){const s=sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;let a="";if(s){a=s.build(i.ui.enabledOn,this.fieldKey,t)}else{a=`{= ${i.ui.enabledOn.replace(/\$root\./g,`${t}>/`).replace(/\./g,"/")} }`}e.bindProperty("enabled",a)}}destroy(){if(this.control&&typeof this.control.destroy==="function"){this.control.destroy();this.control=null}}}var s={__esModule:true};s.BasePlugin=t;return s});
2
2
  //# sourceMappingURL=BasePlugin.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"BasePlugin.js","names":["GlobalPipeline","____core_PipelineManager","BasePlugin","control","metadata","fieldKey","modelName","isEditable","setEditable","editable","this","generateStableId","engineScopeId","bindingPath","undefined","safePath","replace","validate","isValid","getVisible","validatorsToRun","argsMap","maxLength","required","push","ui","validators","v","name","args","length","errorMessage","val","getValue","result","executeValidation","onStateChange","newMetadata","applyState","applyCommonDirectives","readOnly","visibleOn","expr","bindProperty","parts","path","formatter","enabledOn","setEnabled","destroy","__exports","__esModule"],"sources":["BasePlugin.ts"],"sourcesContent":["/**\n * @file BasePlugin.ts\n * @description Abstract foundation for all MetaUI plugins, enforcing lifecycle hooks for v2 Schema.\n */\n\nimport { IPlugin } from \"../../interfaces/IPlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport { GlobalPipeline } from \"../../core/PipelineManager\";\n\n/**\n * Abstract class representing a standard MetaUI Plugin.\n * Enforces the required rendering, state extraction, and validation contracts.\n * \n * @abstract\n * @public\n */\nexport abstract class BasePlugin implements IPlugin {\n /** The instantiated UI5 control for this plugin. */\n protected control: Control | null = null;\n \n /** The metadata schema defining the field rules. */\n protected metadata: IPropertyMetadata | null = null;\n \n /** The internal JSON path of the field relative to its parent payload. */\n protected fieldKey: string = \"\";\n \n /** The UI5 JSONModel name used for absolute binding paths. */\n protected modelName: string = \"meta\";\n\n /** Indicates if the engine is enforcing an editable mode. */\n protected isEditable: boolean = true;\n \n /** Internal callback provided by GeneratorHost to signal validation/data changes upwards */\n protected onChange?: (isValid: boolean, fieldKey?: string, errorMessage?: string, controlId?: string) => void;\n\n /**\n * Injects the global editable mode context into the plugin before rendering.\n * @param editable True if the plugin should render in editable mode.\n */\n public setEditable(editable: boolean): void {\n this.isEditable = editable;\n }\n\n /**\n * Instantiates the raw UI5 control and binds it to the model.\n * \n * @param fieldMetadata The JSON Schema for the field.\n * @param bindingPath The JSON path to bind to.\n * @param modelName The UI5 model name.\n * @param engineScopeId The deterministic scope ID provided by the Engine to prevent cloning collisions.\n * @param onChange The callback fired natively when a field value blur/change occurs.\n * @returns {Control} The generated UI5 control.\n */\n public abstract render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName?: string, engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control;\n\n /**\n * Generates a deterministic, globally unique ID for this control.\n * Prefixes the sanitized binding path with the Engine's scoped ID.\n */\n protected generateStableId(engineScopeId: string | undefined, bindingPath: string): string | undefined {\n if (!engineScopeId) return undefined;\n // Strip leading slash and replace internal slashes with hyphens\n const safePath = bindingPath.replace(/^\\//, '').replace(/\\//g, '-');\n return `${engineScopeId}--${safePath}`;\n }\n\n /**\n * Extracts the current raw value from the underlying UI5 control.\n */\n protected abstract getValue(): unknown;\n\n /**\n * Universal pipeline validation.\n */\n public validate(): import(\"../../interfaces/IPlugin\").IPluginValidationResult {\n if (!this.control || !this.metadata) return { isValid: true };\n \n // Skip validation for hidden fields (e.g. hidden by ConditionEngine visibleOn)\n if (typeof (this.control as Control).getVisible === \"function\") {\n if (!(this.control as Control).getVisible()) {\n return { isValid: true };\n }\n }\n \n const validatorsToRun: string[] = [];\n const argsMap: Record<string, unknown> = {\n \"maxLength\": this.metadata.maxLength\n };\n\n if (this.metadata.required) {\n validatorsToRun.push(\"required\");\n }\n if (this.metadata.maxLength) validatorsToRun.push(\"maxLength\");\n \n if (this.metadata.ui?.validators) {\n for (const v of this.metadata.ui.validators) {\n if (typeof v === \"string\") {\n validatorsToRun.push(v);\n } else if (v && v.name) {\n validatorsToRun.push(v.name);\n if (v.args !== undefined) {\n argsMap[v.name] = v.args;\n }\n }\n }\n }\n\n if (validatorsToRun.length === 0) {\n return { isValid: true, errorMessage: undefined, fieldKey: this.fieldKey };\n }\n\n const val = this.getValue();\n const result = GlobalPipeline.executeValidation(val, validatorsToRun, argsMap);\n return { isValid: result.isValid, errorMessage: result.errorMessage, fieldKey: this.fieldKey };\n }\n\n /**\n * Executes when the condition engine pushes new schema metadata to this field (e.g. readOnly changing).\n * @param newMetadata The mutated schema metadata.\n */\n public onStateChange(newMetadata: IPropertyMetadata): void {\n this.metadata = newMetadata;\n this.applyState();\n }\n\n /**\n * Abstract hook for the plugin to apply state changes to its specific UI5 control (e.g. placeholders, labels).\n */\n protected abstract applyState(): void;\n\n /**\n * Helper to apply common UI directives (like readOnly, visibleOn) directly to any control.\n */\n protected applyCommonDirectives(control: Control, metadata: IPropertyMetadata, modelName: string = \"meta\"): void {\n if (metadata.ui?.readOnly !== undefined && typeof control.setEditable === \"function\") {\n control.setEditable(!metadata.ui.readOnly);\n }\n\n if (metadata.ui?.visibleOn) {\n const expr = `{= ${metadata.ui.visibleOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n control.bindProperty(\"visible\", { parts: [{ path: \"meta>/\" }], formatter: () => false });\n // The ConditionEngine handles actual binding injection, but here we can set a fallback or natively bind if we bypass ConditionEngine.\n control.bindProperty(\"visible\", expr);\n }\n \n if (metadata.ui?.enabledOn && typeof control.setEnabled === \"function\") {\n const expr = `{= ${metadata.ui.enabledOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n control.bindProperty(\"enabled\", expr);\n }\n }\n\n\n\n /**\n * Natively destroys the instantiated UI5 control to prevent memory leaks.\n * Can be overridden by subclasses if they manage secondary controls or custom models.\n */\n public destroy(): void {\n if (this.control && typeof this.control.destroy === \"function\") {\n this.control.destroy();\n this.control = null;\n }\n }\n}\n"],"mappings":"sEAAA,MAQSA,EAAcC,EAAA,kBAShB,MAAeC,EAERC,QAA0B,KAG1BC,SAAqC,KAGrCC,SAAmB,GAGnBC,UAAoB,OAGpBC,WAAsB,KASzBC,YAAYC,GACfC,KAAKH,WAAaE,CACtB,CAkBUE,iBAAiBC,EAAmCC,GAC1D,IAAKD,EAAe,OAAOE,UAE3B,MAAMC,EAAWF,EAAYG,QAAQ,MAAO,IAAIA,QAAQ,MAAO,KAC/D,MAAO,GAAGJ,MAAkBG,GAChC,CAUOE,WACH,IAAKP,KAAKP,UAAYO,KAAKN,SAAU,MAAO,CAAEc,QAAS,MAGvD,UAAYR,KAAKP,QAAoBgB,aAAe,WAAY,CAC5D,IAAMT,KAAKP,QAAoBgB,aAAc,CACzC,MAAO,CAAED,QAAS,KACtB,CACJ,CAEA,MAAME,EAA4B,GAClC,MAAMC,EAAmC,CACrCC,UAAaZ,KAAKN,SAASkB,WAG/B,GAAIZ,KAAKN,SAASmB,SAAU,CACxBH,EAAgBI,KAAK,WACzB,CACA,GAAId,KAAKN,SAASkB,UAAWF,EAAgBI,KAAK,aAElD,GAAId,KAAKN,SAASqB,IAAIC,WAAY,CAC9B,IAAK,MAAMC,KAAKjB,KAAKN,SAASqB,GAAGC,WAAY,CACzC,UAAWC,IAAM,SAAU,CACvBP,EAAgBI,KAAKG,EACzB,MAAO,GAAIA,GAAKA,EAAEC,KAAM,CACpBR,EAAgBI,KAAKG,EAAEC,MACvB,GAAID,EAAEE,OAASf,UAAW,CACtBO,EAAQM,EAAEC,MAAQD,EAAEE,IACxB,CACJ,CACJ,CACJ,CAEA,GAAIT,EAAgBU,SAAW,EAAG,CAC9B,MAAO,CAAEZ,QAAS,KAAMa,aAAcjB,UAAWT,SAAUK,KAAKL,SACpE,CAEA,MAAM2B,EAAMtB,KAAKuB,WACjB,MAAMC,EAASlC,EAAemC,kBAAkBH,EAAKZ,EAAiBC,GACtE,MAAO,CAAEH,QAASgB,EAAOhB,QAASa,aAAcG,EAAOH,aAAc1B,SAAUK,KAAKL,SACxF,CAMO+B,cAAcC,GACjB3B,KAAKN,SAAWiC,EAChB3B,KAAK4B,YACT,CAUUC,sBAAsBpC,EAAkBC,EAA6BE,EAAoB,QAC/F,GAAIF,EAASqB,IAAIe,WAAa1B,kBAAoBX,EAAQK,cAAgB,WAAY,CAClFL,EAAQK,aAAaJ,EAASqB,GAAGe,SACrC,CAEA,GAAIpC,EAASqB,IAAIgB,UAAW,CACxB,MAAMC,EAAO,MAAMtC,EAASqB,GAAGgB,UAAUzB,QAAQ,YAAa,GAAGV,OAAeU,QAAQ,MAAO,SAC/Fb,EAAQwC,aAAa,UAAW,CAAEC,MAAO,CAAC,CAAEC,KAAM,WAAaC,UAAWA,IAAM,QAEhF3C,EAAQwC,aAAa,UAAWD,EACpC,CAEA,GAAItC,EAASqB,IAAIsB,kBAAoB5C,EAAQ6C,aAAe,WAAY,CACpE,MAAMN,EAAO,MAAMtC,EAASqB,GAAGsB,UAAU/B,QAAQ,YAAa,GAAGV,OAAeU,QAAQ,MAAO,SAC/Fb,EAAQwC,aAAa,UAAWD,EACpC,CACJ,CAQOO,UACH,GAAIvC,KAAKP,gBAAkBO,KAAKP,QAAQ8C,UAAY,WAAY,CAC5DvC,KAAKP,QAAQ8C,UACbvC,KAAKP,QAAU,IACnB,CACJ,EACH,IAAA+C,EAAA,CAAAC,WAAA,MAAAD,EAAAhD,aAAA,OAAAgD,CAAA","ignoreList":[]}
1
+ {"version":3,"file":"BasePlugin.js","names":["GlobalPipeline","____core_PipelineManager","BasePlugin","control","metadata","fieldKey","modelName","isEditable","setEditable","editable","this","generateStableId","engineScopeId","bindingPath","undefined","safePath","replace","validate","isValid","getVisible","validatorsToRun","argsMap","maxLength","required","push","ui","validators","v","name","args","length","errorMessage","val","getValue","result","executeValidation","onStateChange","newMetadata","applyState","applyCommonDirectives","readOnly","visibleOn","ExpressionBuilder","sap","require","expr","build","bindProperty","parts","path","formatter","enabledOn","setEnabled","destroy","__exports","__esModule"],"sources":["BasePlugin.ts"],"sourcesContent":["/**\n * @file BasePlugin.ts\n * @description Abstract foundation for all MetaUI plugins, enforcing lifecycle hooks for v2 Schema.\n */\n\nimport { IPlugin } from \"../../interfaces/IPlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport { GlobalPipeline } from \"../../core/PipelineManager\";\n\n/**\n * Abstract class representing a standard MetaUI Plugin.\n * Enforces the required rendering, state extraction, and validation contracts.\n * \n * @abstract\n * @public\n */\nexport abstract class BasePlugin implements IPlugin {\n /** The instantiated UI5 control for this plugin. */\n protected control: Control | null = null;\n \n /** The metadata schema defining the field rules. */\n protected metadata: IPropertyMetadata | null = null;\n \n /** The internal JSON path of the field relative to its parent payload. */\n protected fieldKey: string = \"\";\n \n /** The UI5 JSONModel name used for absolute binding paths. */\n protected modelName: string = \"meta\";\n\n /** Indicates if the engine is enforcing an editable mode. */\n protected isEditable: boolean = true;\n \n /** Internal callback provided by GeneratorHost to signal validation/data changes upwards */\n protected onChange?: (isValid: boolean, fieldKey?: string, errorMessage?: string, controlId?: string) => void;\n\n /**\n * Injects the global editable mode context into the plugin before rendering.\n * @param editable True if the plugin should render in editable mode.\n */\n public setEditable(editable: boolean): void {\n this.isEditable = editable;\n }\n\n /**\n * Instantiates the raw UI5 control and binds it to the model.\n * \n * @param fieldMetadata The JSON Schema for the field.\n * @param bindingPath The JSON path to bind to.\n * @param modelName The UI5 model name.\n * @param engineScopeId The deterministic scope ID provided by the Engine to prevent cloning collisions.\n * @param onChange The callback fired natively when a field value blur/change occurs.\n * @returns {Control} The generated UI5 control.\n */\n public abstract render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName?: string, engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control;\n\n /**\n * Generates a deterministic, globally unique ID for this control.\n * Prefixes the sanitized binding path with the Engine's scoped ID.\n */\n protected generateStableId(engineScopeId: string | undefined, bindingPath: string): string | undefined {\n if (!engineScopeId) return undefined;\n // Strip leading slash and replace internal slashes with hyphens\n const safePath = bindingPath.replace(/^\\//, '').replace(/\\//g, '-');\n return `${engineScopeId}--${safePath}`;\n }\n\n /**\n * Extracts the current raw value from the underlying UI5 control.\n */\n protected abstract getValue(): unknown;\n\n /**\n * Universal pipeline validation.\n */\n public validate(): import(\"../../interfaces/IPlugin\").IPluginValidationResult {\n if (!this.control || !this.metadata) return { isValid: true };\n \n // Skip validation for hidden fields (e.g. hidden by ConditionEngine visibleOn)\n if (typeof (this.control as Control).getVisible === \"function\") {\n if (!(this.control as Control).getVisible()) {\n return { isValid: true };\n }\n }\n \n const validatorsToRun: string[] = [];\n const argsMap: Record<string, unknown> = {\n \"maxLength\": this.metadata.maxLength\n };\n\n if (this.metadata.required) {\n validatorsToRun.push(\"required\");\n }\n if (this.metadata.maxLength) validatorsToRun.push(\"maxLength\");\n \n if (this.metadata.ui?.validators) {\n for (const v of this.metadata.ui.validators) {\n if (typeof v === \"string\") {\n validatorsToRun.push(v);\n } else if (v && v.name) {\n validatorsToRun.push(v.name);\n if (v.args !== undefined) {\n argsMap[v.name] = v.args;\n }\n }\n }\n }\n\n if (validatorsToRun.length === 0) {\n return { isValid: true, errorMessage: undefined, fieldKey: this.fieldKey };\n }\n\n const val = this.getValue();\n const result = GlobalPipeline.executeValidation(val, validatorsToRun, argsMap);\n return { isValid: result.isValid, errorMessage: result.errorMessage, fieldKey: this.fieldKey };\n }\n\n /**\n * Executes when the condition engine pushes new schema metadata to this field (e.g. readOnly changing).\n * @param newMetadata The mutated schema metadata.\n */\n public onStateChange(newMetadata: IPropertyMetadata): void {\n this.metadata = newMetadata;\n this.applyState();\n }\n\n /**\n * Abstract hook for the plugin to apply state changes to its specific UI5 control (e.g. placeholders, labels).\n */\n protected abstract applyState(): void;\n\n /**\n * Helper to apply common UI directives (like readOnly, visibleOn) directly to any control.\n */\n protected applyCommonDirectives(control: Control, metadata: IPropertyMetadata, modelName: string = \"meta\"): void {\n if (metadata.ui?.readOnly !== undefined && typeof control.setEditable === \"function\") {\n control.setEditable(!metadata.ui.readOnly);\n }\n\n if (metadata.ui?.visibleOn) {\n const ExpressionBuilder = sap.ui.require(\"nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder\")?.ExpressionBuilder;\n let expr = \"\";\n if (ExpressionBuilder) {\n expr = ExpressionBuilder.build(metadata.ui.visibleOn, this.fieldKey, modelName);\n } else {\n expr = `{= ${metadata.ui.visibleOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n }\n control.bindProperty(\"visible\", { parts: [{ path: \"meta>/\" }], formatter: () => false });\n control.bindProperty(\"visible\", expr);\n }\n \n if (metadata.ui?.enabledOn && typeof control.setEnabled === \"function\") {\n const ExpressionBuilder = sap.ui.require(\"nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder\")?.ExpressionBuilder;\n let expr = \"\";\n if (ExpressionBuilder) {\n expr = ExpressionBuilder.build(metadata.ui.enabledOn, this.fieldKey, modelName);\n } else {\n expr = `{= ${metadata.ui.enabledOn.replace(/\\$root\\./g, `${modelName}>/`).replace(/\\./g, '/')} }`;\n }\n control.bindProperty(\"enabled\", expr);\n }\n }\n\n\n\n /**\n * Natively destroys the instantiated UI5 control to prevent memory leaks.\n * Can be overridden by subclasses if they manage secondary controls or custom models.\n */\n public destroy(): void {\n if (this.control && typeof this.control.destroy === \"function\") {\n this.control.destroy();\n this.control = null;\n }\n }\n}\n"],"mappings":"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","ignoreList":[]}
@@ -138,14 +138,25 @@ export abstract class BasePlugin implements IPlugin {
138
138
  }
139
139
 
140
140
  if (metadata.ui?.visibleOn) {
141
- const expr = `{= ${metadata.ui.visibleOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
141
+ const ExpressionBuilder = sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;
142
+ let expr = "";
143
+ if (ExpressionBuilder) {
144
+ expr = ExpressionBuilder.build(metadata.ui.visibleOn, this.fieldKey, modelName);
145
+ } else {
146
+ expr = `{= ${metadata.ui.visibleOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
147
+ }
142
148
  control.bindProperty("visible", { parts: [{ path: "meta>/" }], formatter: () => false });
143
- // The ConditionEngine handles actual binding injection, but here we can set a fallback or natively bind if we bypass ConditionEngine.
144
149
  control.bindProperty("visible", expr);
145
150
  }
146
151
 
147
152
  if (metadata.ui?.enabledOn && typeof control.setEnabled === "function") {
148
- const expr = `{= ${metadata.ui.enabledOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
153
+ const ExpressionBuilder = sap.ui.require("nz/co/siliconst/ui5/metaui/utils/ExpressionBuilder")?.ExpressionBuilder;
154
+ let expr = "";
155
+ if (ExpressionBuilder) {
156
+ expr = ExpressionBuilder.build(metadata.ui.enabledOn, this.fieldKey, modelName);
157
+ } else {
158
+ expr = `{= ${metadata.ui.enabledOn.replace(/\$root\./g, `${modelName}>/`).replace(/\./g, '/')} }`;
159
+ }
149
160
  control.bindProperty("enabled", expr);
150
161
  }
151
162
  }
@@ -135,8 +135,11 @@ sap.ui.define(["./BasePlugin", "sap/ui/codeeditor/CodeEditor"], function (___Bas
135
135
  */
136
136
  applyState() {
137
137
  if (this.control && this.metadata) {
138
- if (!this.isEditable) return;
139
- this.control.setEditable(!this.metadata.ui?.readOnly);
138
+ if (!this.isEditable) {
139
+ this.control.setEditable(false);
140
+ } else {
141
+ this.control.setEditable(!this.metadata.ui?.readOnly);
142
+ }
140
143
  }
141
144
  }
142
145
  }
@@ -1 +1 @@
1
- {"version":3,"file":"CodeEditorPlugin-dbg.js","names":["BasePlugin","___BasePlugin","CodeEditorPlugin","detectLanguage","value","trimmed","trim","startsWith","JSON","parse","e","test","adjustHeight","control","val","getValue","lines","split","length","newHeight","Math","max","setHeight","render","fieldMetadata","bindingPath","modelName","engineScopeId","onChange","metadata","fieldKey","replace","CodeEditor","id","generateStableId","type","ui","args","editable","isEditable","readOnly","height","width","change","result","validate","isValid","currentVal","detectedType","getType","setType","attachEventOnce","oBinding","getBinding","initLogic","attachChange","applyCommonDirectives","applyState","setEditable","__exports","__esModule"],"sources":["CodeEditorPlugin.ts"],"sourcesContent":["/**\n * @file CodeEditorPlugin.ts\n * @description Renders a sap.ui.codeeditor.CodeEditor for editing source code/JSON.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport CodeEditor from \"sap/ui/codeeditor/CodeEditor\";\n\n/**\n * Handles rendering logic for code editing.\n * Requires the `sap.ui.codeeditor` library to be loaded.\n * \n * @namespace nz.co.siliconst.ui5.metaui.plugins.controls\n * @public\n */\nexport class CodeEditorPlugin extends BasePlugin {\n /**\n * Infers the language type from the content.\n * @param value The raw string.\n * @returns The language string.\n */\n private detectLanguage(value: string): string {\n if (!value || typeof value !== \"string\") return \"javascript\";\n \n const trimmed = value.trim();\n if (trimmed === \"\") return \"javascript\";\n\n // 1. JSON\n if (trimmed.startsWith(\"{\") || trimmed.startsWith(\"[\")) {\n try {\n JSON.parse(trimmed);\n return \"json\";\n } catch (e) {\n // Not valid JSON, continue testing\n }\n }\n\n // 2. XML / HTML\n if (/^\\s*<[\\s\\S]*>\\s*$/.test(trimmed)) {\n return \"xml\";\n }\n\n // 3. Fallback to JavaScript\n return \"javascript\";\n }\n\n /**\n * Dynamically adjusts the height of the editor based on content lines.\n */\n private adjustHeight(): void {\n if (!this.control) return;\n const val = (this.control as CodeEditor).getValue() || \"\";\n const lines = val.split(/\\r\\n|\\r|\\n/).length;\n // 18px per line + 20px padding, minimum 100px\n const newHeight = Math.max(100, (lines * 18) + 20);\n (this.control as CodeEditor).setHeight(newHeight + \"px\");\n }\n\n /**\n * Renders a `sap.ui.codeeditor.CodeEditor` component.\n * \n * @param fieldMetadata The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured CodeEditor control.\n */\n public render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = fieldMetadata;\n this.fieldKey = bindingPath.replace(\"/\", \"\"); // For EventBus\n \n \n \n this.control = new CodeEditor({\n id: this.generateStableId(engineScopeId, bindingPath),\n value: `{${modelName}>${bindingPath}}`,\n type: fieldMetadata.ui?.args || \"javascript\", // will be dynamically overridden if args is missing\n editable: !this.isEditable ? false : !fieldMetadata.ui?.readOnly,\n height: \"100px\", // Initial minimum height\n width: \"100%\",\n change: () => {\n const result = this.validate();\n if (this.onChange) {\n this.onChange(result.isValid, this.fieldKey);\n }\n \n // If language isn't explicitly defined, try to guess it dynamically\n if (!fieldMetadata.ui?.args) {\n const currentVal = (this.control as CodeEditor).getValue();\n const detectedType = this.detectLanguage(currentVal);\n if ((this.control as CodeEditor).getType() !== detectedType) {\n (this.control as CodeEditor).setType(detectedType);\n }\n }\n \n this.adjustHeight();\n }\n });\n\n // Clean architecture: Wait for the model context, then attach safely to the binding itself.\n // No timeouts, no DOM hacks, pure UI5 Eventing.\n (this.control as CodeEditor).attachEventOnce(\"modelContextChange\", () => {\n const oBinding = (this.control as CodeEditor).getBinding(\"value\");\n \n const initLogic = () => {\n if (this.control) {\n const currentVal = (this.control as CodeEditor).getValue();\n if (!fieldMetadata.ui?.args) {\n (this.control as CodeEditor).setType(this.detectLanguage(currentVal));\n }\n this.adjustHeight();\n }\n };\n\n if (oBinding) {\n // Attach for future model changes\n oBinding.attachChange(initLogic);\n }\n \n // Execute immediately in case the model is synchronous (JSONModel)\n initLogic();\n });\n\n this.applyCommonDirectives(this.control, fieldMetadata, modelName);\n\n return this.control as Control;\n }\n\n /**\n * Retrieves the current code string.\n * @returns {unknown} The code value.\n */\n protected getValue(): unknown {\n return this.control ? (this.control as CodeEditor).getValue() : null;\n }\n\n /**\n * Applies dynamic read-only state.\n */\n protected applyState(): void {\n if (this.control && this.metadata) {\n if (!this.isEditable) return;\n (this.control as CodeEditor).setEditable(!this.metadata.ui?.readOnly);\n }\n }\n}\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"file":"CodeEditorPlugin-dbg.js","names":["BasePlugin","___BasePlugin","CodeEditorPlugin","detectLanguage","value","trimmed","trim","startsWith","JSON","parse","e","test","adjustHeight","control","val","getValue","lines","split","length","newHeight","Math","max","setHeight","render","fieldMetadata","bindingPath","modelName","engineScopeId","onChange","metadata","fieldKey","replace","CodeEditor","id","generateStableId","type","ui","args","editable","isEditable","readOnly","height","width","change","result","validate","isValid","currentVal","detectedType","getType","setType","attachEventOnce","oBinding","getBinding","initLogic","attachChange","applyCommonDirectives","applyState","setEditable","__exports","__esModule"],"sources":["CodeEditorPlugin.ts"],"sourcesContent":["/**\n * @file CodeEditorPlugin.ts\n * @description Renders a sap.ui.codeeditor.CodeEditor for editing source code/JSON.\n */\n\nimport { BasePlugin } from \"./BasePlugin\";\nimport { IPropertyMetadata } from \"../../interfaces/ISchema\";\nimport Control from \"sap/ui/core/Control\";\nimport CodeEditor from \"sap/ui/codeeditor/CodeEditor\";\n\n/**\n * Handles rendering logic for code editing.\n * Requires the `sap.ui.codeeditor` library to be loaded.\n * \n * @namespace nz.co.siliconst.ui5.metaui.plugins.controls\n * @public\n */\nexport class CodeEditorPlugin extends BasePlugin {\n /**\n * Infers the language type from the content.\n * @param value The raw string.\n * @returns The language string.\n */\n private detectLanguage(value: string): string {\n if (!value || typeof value !== \"string\") return \"javascript\";\n \n const trimmed = value.trim();\n if (trimmed === \"\") return \"javascript\";\n\n // 1. JSON\n if (trimmed.startsWith(\"{\") || trimmed.startsWith(\"[\")) {\n try {\n JSON.parse(trimmed);\n return \"json\";\n } catch (e) {\n // Not valid JSON, continue testing\n }\n }\n\n // 2. XML / HTML\n if (/^\\s*<[\\s\\S]*>\\s*$/.test(trimmed)) {\n return \"xml\";\n }\n\n // 3. Fallback to JavaScript\n return \"javascript\";\n }\n\n /**\n * Dynamically adjusts the height of the editor based on content lines.\n */\n private adjustHeight(): void {\n if (!this.control) return;\n const val = (this.control as CodeEditor).getValue() || \"\";\n const lines = val.split(/\\r\\n|\\r|\\n/).length;\n // 18px per line + 20px padding, minimum 100px\n const newHeight = Math.max(100, (lines * 18) + 20);\n (this.control as CodeEditor).setHeight(newHeight + \"px\");\n }\n\n /**\n * Renders a `sap.ui.codeeditor.CodeEditor` component.\n * \n * @param fieldMetadata The specific JSON schema properties for this field.\n * @param bindingPath The JSON path bound to this control.\n * @param modelName The UI5 JSONModel name.\n * @param engineScopeId The deterministic scope ID.\n * @param onChange The callback fired on value change.\n * @returns {Control} The configured CodeEditor control.\n */\n public render(fieldMetadata: IPropertyMetadata, bindingPath: string, modelName: string = \"meta\", engineScopeId?: string, onChange?: (isValid: boolean, fieldKey?: string) => void): Control {\n this.onChange = onChange;\n this.metadata = fieldMetadata;\n this.fieldKey = bindingPath.replace(\"/\", \"\"); // For EventBus\n \n \n \n this.control = new CodeEditor({\n id: this.generateStableId(engineScopeId, bindingPath),\n value: `{${modelName}>${bindingPath}}`,\n type: fieldMetadata.ui?.args || \"javascript\", // will be dynamically overridden if args is missing\n editable: !this.isEditable ? false : !fieldMetadata.ui?.readOnly,\n height: \"100px\", // Initial minimum height\n width: \"100%\",\n change: () => {\n const result = this.validate();\n if (this.onChange) {\n this.onChange(result.isValid, this.fieldKey);\n }\n \n // If language isn't explicitly defined, try to guess it dynamically\n if (!fieldMetadata.ui?.args) {\n const currentVal = (this.control as CodeEditor).getValue();\n const detectedType = this.detectLanguage(currentVal);\n if ((this.control as CodeEditor).getType() !== detectedType) {\n (this.control as CodeEditor).setType(detectedType);\n }\n }\n \n this.adjustHeight();\n }\n });\n\n // Clean architecture: Wait for the model context, then attach safely to the binding itself.\n // No timeouts, no DOM hacks, pure UI5 Eventing.\n (this.control as CodeEditor).attachEventOnce(\"modelContextChange\", () => {\n const oBinding = (this.control as CodeEditor).getBinding(\"value\");\n \n const initLogic = () => {\n if (this.control) {\n const currentVal = (this.control as CodeEditor).getValue();\n if (!fieldMetadata.ui?.args) {\n (this.control as CodeEditor).setType(this.detectLanguage(currentVal));\n }\n this.adjustHeight();\n }\n };\n\n if (oBinding) {\n // Attach for future model changes\n oBinding.attachChange(initLogic);\n }\n \n // Execute immediately in case the model is synchronous (JSONModel)\n initLogic();\n });\n\n this.applyCommonDirectives(this.control, fieldMetadata, modelName);\n\n return this.control as Control;\n }\n\n /**\n * Retrieves the current code string.\n * @returns {unknown} The code value.\n */\n protected getValue(): unknown {\n return this.control ? (this.control as CodeEditor).getValue() : null;\n }\n\n /**\n * Applies dynamic read-only state.\n */\n protected applyState(): void {\n if (this.control && this.metadata) {\n if (!this.isEditable) {\n (this.control as CodeEditor).setEditable(false);\n } else {\n (this.control as CodeEditor).setEditable(!this.metadata.ui?.readOnly);\n }\n }\n }\n}\n"],"mappings":"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","ignoreList":[]}
@@ -1 +1 @@
1
- {"version":3,"file":"CodeEditorPlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,8DAA8D,CAAC;IAC9E;;;OAGG;IAEH,OAAO,EAAE,UAAU,EAAE,MAAM,wDAAwD,CAAC;IACpF,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAG1C;;;;;;OAMG;IACH,MAAa,gBAAiB,SAAQ,UAAU;QAC5C;;;;WAIG;QACH,OAAO,CAAC,cAAc;QAyBtB;;WAEG;QACH,OAAO,CAAC,YAAY;QASpB;;;;;;;;;WASG;QACI,MAAM,CAAC,aAAa,EAAE,iBAAiB,EAAE,WAAW,EAAE,MAAM,EAAE,SAAS,GAAE,MAAe,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QA8D3L;;;WAGG;QACH,SAAS,CAAC,QAAQ,IAAI,OAAO;QAI7B;;WAEG;QACH,SAAS,CAAC,UAAU,IAAI,IAAI;KAM/B;CAEA"}
1
+ {"version":3,"file":"CodeEditorPlugin.d.ts","sourceRoot":"../../../../../../../../..","sources":["src/nz/co/siliconst/ui5/metaui/plugins/controls/CodeEditorPlugin.ts"],"names":[],"mappings":"AAAA,OAAO,QAAQ,8DAA8D,CAAC;IAC9E;;;OAGG;IAEH,OAAO,EAAE,UAAU,EAAE,MAAM,wDAAwD,CAAC;IACpF,OAAO,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;IAClF,OAAO,OAAO,MAAM,qBAAqB,CAAC;IAG1C;;;;;;OAMG;IACH,MAAa,gBAAiB,SAAQ,UAAU;QAC5C;;;;WAIG;QACH,OAAO,CAAC,cAAc;QAyBtB;;WAEG;QACH,OAAO,CAAC,YAAY;QASpB;;;;;;;;;WASG;QACI,MAAM,CAAC,aAAa,EAAE,iBAAiB,EAAE,WAAW,EAAE,MAAM,EAAE,SAAS,GAAE,MAAe,EAAE,aAAa,CAAC,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,GAAG,OAAO;QA8D3L;;;WAGG;QACH,SAAS,CAAC,QAAQ,IAAI,OAAO;QAI7B;;WAEG;QACH,SAAS,CAAC,UAAU,IAAI,IAAI;KAS/B;CAEA"}
@@ -1,2 +1,2 @@
1
- sap.ui.define(["./BasePlugin","sap/ui/codeeditor/CodeEditor"],function(t,e){"use strict";const i=t["BasePlugin"];class s extends i{detectLanguage(t){if(!t||typeof t!=="string")return"javascript";const e=t.trim();if(e==="")return"javascript";if(e.startsWith("{")||e.startsWith("[")){try{JSON.parse(e);return"json"}catch(t){}}if(/^\s*<[\s\S]*>\s*$/.test(e)){return"xml"}return"javascript"}adjustHeight(){if(!this.control)return;const t=this.control.getValue()||"";const e=t.split(/\r\n|\r|\n/).length;const i=Math.max(100,e*18+20);this.control.setHeight(i+"px")}render(t,i,s="meta",a,n){this.onChange=n;this.metadata=t;this.fieldKey=i.replace("/","");this.control=new e({id:this.generateStableId(a,i),value:`{${s}>${i}}`,type:t.ui?.args||"javascript",editable:!this.isEditable?false:!t.ui?.readOnly,height:"100px",width:"100%",change:()=>{const e=this.validate();if(this.onChange){this.onChange(e.isValid,this.fieldKey)}if(!t.ui?.args){const t=this.control.getValue();const e=this.detectLanguage(t);if(this.control.getType()!==e){this.control.setType(e)}}this.adjustHeight()}});this.control.attachEventOnce("modelContextChange",()=>{const e=this.control.getBinding("value");const i=()=>{if(this.control){const e=this.control.getValue();if(!t.ui?.args){this.control.setType(this.detectLanguage(e))}this.adjustHeight()}};if(e){e.attachChange(i)}i()});this.applyCommonDirectives(this.control,t,s);return this.control}getValue(){return this.control?this.control.getValue():null}applyState(){if(this.control&&this.metadata){if(!this.isEditable)return;this.control.setEditable(!this.metadata.ui?.readOnly)}}}var a={__esModule:true};a.CodeEditorPlugin=s;return a});
1
+ sap.ui.define(["./BasePlugin","sap/ui/codeeditor/CodeEditor"],function(t,e){"use strict";const i=t["BasePlugin"];class s extends i{detectLanguage(t){if(!t||typeof t!=="string")return"javascript";const e=t.trim();if(e==="")return"javascript";if(e.startsWith("{")||e.startsWith("[")){try{JSON.parse(e);return"json"}catch(t){}}if(/^\s*<[\s\S]*>\s*$/.test(e)){return"xml"}return"javascript"}adjustHeight(){if(!this.control)return;const t=this.control.getValue()||"";const e=t.split(/\r\n|\r|\n/).length;const i=Math.max(100,e*18+20);this.control.setHeight(i+"px")}render(t,i,s="meta",a,n){this.onChange=n;this.metadata=t;this.fieldKey=i.replace("/","");this.control=new e({id:this.generateStableId(a,i),value:`{${s}>${i}}`,type:t.ui?.args||"javascript",editable:!this.isEditable?false:!t.ui?.readOnly,height:"100px",width:"100%",change:()=>{const e=this.validate();if(this.onChange){this.onChange(e.isValid,this.fieldKey)}if(!t.ui?.args){const t=this.control.getValue();const e=this.detectLanguage(t);if(this.control.getType()!==e){this.control.setType(e)}}this.adjustHeight()}});this.control.attachEventOnce("modelContextChange",()=>{const e=this.control.getBinding("value");const i=()=>{if(this.control){const e=this.control.getValue();if(!t.ui?.args){this.control.setType(this.detectLanguage(e))}this.adjustHeight()}};if(e){e.attachChange(i)}i()});this.applyCommonDirectives(this.control,t,s);return this.control}getValue(){return this.control?this.control.getValue():null}applyState(){if(this.control&&this.metadata){if(!this.isEditable){this.control.setEditable(false)}else{this.control.setEditable(!this.metadata.ui?.readOnly)}}}}var a={__esModule:true};a.CodeEditorPlugin=s;return a});
2
2
  //# sourceMappingURL=CodeEditorPlugin.js.map