@elite.framework/ng.ui.core 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (201) hide show
  1. package/README.md +3 -0
  2. package/attachments/README.md +3 -0
  3. package/attachments/index.d.ts +38 -0
  4. package/base-crud/README.md +3 -0
  5. package/base-crud/index.d.ts +68 -0
  6. package/breadcrumb/README.md +3 -0
  7. package/breadcrumb/index.d.ts +17 -0
  8. package/checkbox/README.md +3 -0
  9. package/checkbox/index.d.ts +33 -0
  10. package/color-picker/README.md +3 -0
  11. package/color-picker/index.d.ts +16 -0
  12. package/column-settings-popover/README.md +3 -0
  13. package/column-settings-popover/index.d.ts +46 -0
  14. package/condition-editor/README.md +3 -0
  15. package/condition-editor/index.d.ts +80 -0
  16. package/custom-switch/README.md +3 -0
  17. package/custom-switch/index.d.ts +19 -0
  18. package/datepicker/README.md +3 -0
  19. package/datepicker/index.d.ts +23 -0
  20. package/deactivation-reason/README.md +3 -0
  21. package/deactivation-reason/index.d.ts +31 -0
  22. package/fesm2022/elite.framework-ng.ui.core-attachments.mjs +217 -0
  23. package/fesm2022/elite.framework-ng.ui.core-attachments.mjs.map +1 -0
  24. package/fesm2022/elite.framework-ng.ui.core-base-crud.mjs +312 -0
  25. package/fesm2022/elite.framework-ng.ui.core-base-crud.mjs.map +1 -0
  26. package/fesm2022/elite.framework-ng.ui.core-breadcrumb.mjs +144 -0
  27. package/fesm2022/elite.framework-ng.ui.core-breadcrumb.mjs.map +1 -0
  28. package/fesm2022/elite.framework-ng.ui.core-checkbox.mjs +130 -0
  29. package/fesm2022/elite.framework-ng.ui.core-checkbox.mjs.map +1 -0
  30. package/fesm2022/elite.framework-ng.ui.core-color-picker.mjs +88 -0
  31. package/fesm2022/elite.framework-ng.ui.core-color-picker.mjs.map +1 -0
  32. package/fesm2022/elite.framework-ng.ui.core-column-settings-popover.mjs +184 -0
  33. package/fesm2022/elite.framework-ng.ui.core-column-settings-popover.mjs.map +1 -0
  34. package/fesm2022/elite.framework-ng.ui.core-condition-editor.mjs +782 -0
  35. package/fesm2022/elite.framework-ng.ui.core-condition-editor.mjs.map +1 -0
  36. package/fesm2022/elite.framework-ng.ui.core-custom-switch.mjs +122 -0
  37. package/fesm2022/elite.framework-ng.ui.core-custom-switch.mjs.map +1 -0
  38. package/fesm2022/elite.framework-ng.ui.core-datepicker.mjs +206 -0
  39. package/fesm2022/elite.framework-ng.ui.core-datepicker.mjs.map +1 -0
  40. package/fesm2022/elite.framework-ng.ui.core-deactivation-reason.mjs +142 -0
  41. package/fesm2022/elite.framework-ng.ui.core-deactivation-reason.mjs.map +1 -0
  42. package/fesm2022/elite.framework-ng.ui.core-form-button.mjs +62 -0
  43. package/fesm2022/elite.framework-ng.ui.core-form-button.mjs.map +1 -0
  44. package/fesm2022/elite.framework-ng.ui.core-form-field.mjs +155 -0
  45. package/fesm2022/elite.framework-ng.ui.core-form-field.mjs.map +1 -0
  46. package/fesm2022/elite.framework-ng.ui.core-form-template.mjs +37 -0
  47. package/fesm2022/elite.framework-ng.ui.core-form-template.mjs.map +1 -0
  48. package/fesm2022/elite.framework-ng.ui.core-formly-avatar-image.mjs +112 -0
  49. package/fesm2022/elite.framework-ng.ui.core-formly-avatar-image.mjs.map +1 -0
  50. package/fesm2022/elite.framework-ng.ui.core-formly-avatar-label.mjs +90 -0
  51. package/fesm2022/elite.framework-ng.ui.core-formly-avatar-label.mjs.map +1 -0
  52. package/fesm2022/elite.framework-ng.ui.core-formly-button-selector.mjs +179 -0
  53. package/fesm2022/elite.framework-ng.ui.core-formly-button-selector.mjs.map +1 -0
  54. package/fesm2022/elite.framework-ng.ui.core-formly-button.mjs +74 -0
  55. package/fesm2022/elite.framework-ng.ui.core-formly-button.mjs.map +1 -0
  56. package/fesm2022/elite.framework-ng.ui.core-formly-presets.mjs +201 -0
  57. package/fesm2022/elite.framework-ng.ui.core-formly-presets.mjs.map +1 -0
  58. package/fesm2022/elite.framework-ng.ui.core-formly-split-button.mjs +62 -0
  59. package/fesm2022/elite.framework-ng.ui.core-formly-split-button.mjs.map +1 -0
  60. package/fesm2022/elite.framework-ng.ui.core-formly-ui.mjs +416 -0
  61. package/fesm2022/elite.framework-ng.ui.core-formly-ui.mjs.map +1 -0
  62. package/fesm2022/elite.framework-ng.ui.core-formly-username-with-domain.mjs +88 -0
  63. package/fesm2022/elite.framework-ng.ui.core-formly-username-with-domain.mjs.map +1 -0
  64. package/fesm2022/elite.framework-ng.ui.core-generic-autocomplete.mjs +175 -0
  65. package/fesm2022/elite.framework-ng.ui.core-generic-autocomplete.mjs.map +1 -0
  66. package/fesm2022/elite.framework-ng.ui.core-generic-button.mjs +145 -0
  67. package/fesm2022/elite.framework-ng.ui.core-generic-button.mjs.map +1 -0
  68. package/fesm2022/elite.framework-ng.ui.core-generic-card.mjs +219 -0
  69. package/fesm2022/elite.framework-ng.ui.core-generic-card.mjs.map +1 -0
  70. package/fesm2022/elite.framework-ng.ui.core-generic-crud-table.mjs +398 -0
  71. package/fesm2022/elite.framework-ng.ui.core-generic-crud-table.mjs.map +1 -0
  72. package/fesm2022/elite.framework-ng.ui.core-generic-errormessage.mjs +35 -0
  73. package/fesm2022/elite.framework-ng.ui.core-generic-errormessage.mjs.map +1 -0
  74. package/fesm2022/elite.framework-ng.ui.core-generic-formly-fields.mjs +65 -0
  75. package/fesm2022/elite.framework-ng.ui.core-generic-formly-fields.mjs.map +1 -0
  76. package/fesm2022/elite.framework-ng.ui.core-generic-loadingspinner.mjs +35 -0
  77. package/fesm2022/elite.framework-ng.ui.core-generic-loadingspinner.mjs.map +1 -0
  78. package/fesm2022/elite.framework-ng.ui.core-generic-search.mjs +98 -0
  79. package/fesm2022/elite.framework-ng.ui.core-generic-search.mjs.map +1 -0
  80. package/fesm2022/elite.framework-ng.ui.core-generic-selector.mjs +441 -0
  81. package/fesm2022/elite.framework-ng.ui.core-generic-selector.mjs.map +1 -0
  82. package/fesm2022/elite.framework-ng.ui.core-generic-table.mjs +226 -0
  83. package/fesm2022/elite.framework-ng.ui.core-generic-table.mjs.map +1 -0
  84. package/fesm2022/elite.framework-ng.ui.core-header-wrapper.mjs +31 -0
  85. package/fesm2022/elite.framework-ng.ui.core-header-wrapper.mjs.map +1 -0
  86. package/fesm2022/elite.framework-ng.ui.core-icon-picker.mjs +207 -0
  87. package/fesm2022/elite.framework-ng.ui.core-icon-picker.mjs.map +1 -0
  88. package/fesm2022/elite.framework-ng.ui.core-input-switch.mjs +106 -0
  89. package/fesm2022/elite.framework-ng.ui.core-input-switch.mjs.map +1 -0
  90. package/fesm2022/elite.framework-ng.ui.core-input-with-icon.mjs +67 -0
  91. package/fesm2022/elite.framework-ng.ui.core-input-with-icon.mjs.map +1 -0
  92. package/fesm2022/elite.framework-ng.ui.core-input.mjs +201 -0
  93. package/fesm2022/elite.framework-ng.ui.core-input.mjs.map +1 -0
  94. package/fesm2022/elite.framework-ng.ui.core-label-type.mjs +125 -0
  95. package/fesm2022/elite.framework-ng.ui.core-label-type.mjs.map +1 -0
  96. package/fesm2022/elite.framework-ng.ui.core-odata-query-builder.mjs +308 -0
  97. package/fesm2022/elite.framework-ng.ui.core-odata-query-builder.mjs.map +1 -0
  98. package/fesm2022/elite.framework-ng.ui.core-radio.mjs +118 -0
  99. package/fesm2022/elite.framework-ng.ui.core-radio.mjs.map +1 -0
  100. package/fesm2022/elite.framework-ng.ui.core-repeat.mjs +147 -0
  101. package/fesm2022/elite.framework-ng.ui.core-repeat.mjs.map +1 -0
  102. package/fesm2022/elite.framework-ng.ui.core-select.mjs +180 -0
  103. package/fesm2022/elite.framework-ng.ui.core-select.mjs.map +1 -0
  104. package/fesm2022/elite.framework-ng.ui.core-sidebar-cards.mjs +52 -0
  105. package/fesm2022/elite.framework-ng.ui.core-sidebar-cards.mjs.map +1 -0
  106. package/fesm2022/elite.framework-ng.ui.core-sidebar-toggles.mjs +53 -0
  107. package/fesm2022/elite.framework-ng.ui.core-sidebar-toggles.mjs.map +1 -0
  108. package/fesm2022/elite.framework-ng.ui.core-tabs.mjs +57 -0
  109. package/fesm2022/elite.framework-ng.ui.core-tabs.mjs.map +1 -0
  110. package/fesm2022/elite.framework-ng.ui.core-tag-type.mjs +204 -0
  111. package/fesm2022/elite.framework-ng.ui.core-tag-type.mjs.map +1 -0
  112. package/fesm2022/elite.framework-ng.ui.core-text-editor.mjs +56 -0
  113. package/fesm2022/elite.framework-ng.ui.core-text-editor.mjs.map +1 -0
  114. package/fesm2022/elite.framework-ng.ui.core-textarea.mjs +95 -0
  115. package/fesm2022/elite.framework-ng.ui.core-textarea.mjs.map +1 -0
  116. package/fesm2022/elite.framework-ng.ui.core-ui-button.mjs +101 -0
  117. package/fesm2022/elite.framework-ng.ui.core-ui-button.mjs.map +1 -0
  118. package/fesm2022/elite.framework-ng.ui.core-wrappers.mjs +186 -0
  119. package/fesm2022/elite.framework-ng.ui.core-wrappers.mjs.map +1 -0
  120. package/fesm2022/elite.framework-ng.ui.core.mjs +18 -0
  121. package/fesm2022/elite.framework-ng.ui.core.mjs.map +1 -0
  122. package/form-button/README.md +3 -0
  123. package/form-button/index.d.ts +17 -0
  124. package/form-field/README.md +3 -0
  125. package/form-field/index.d.ts +30 -0
  126. package/form-template/README.md +3 -0
  127. package/form-template/index.d.ts +16 -0
  128. package/formly-avatar-image/README.md +3 -0
  129. package/formly-avatar-image/index.d.ts +18 -0
  130. package/formly-avatar-label/README.md +3 -0
  131. package/formly-avatar-label/index.d.ts +36 -0
  132. package/formly-button/README.md +3 -0
  133. package/formly-button/index.d.ts +20 -0
  134. package/formly-button-selector/README.md +3 -0
  135. package/formly-button-selector/index.d.ts +35 -0
  136. package/formly-presets/README.md +3 -0
  137. package/formly-presets/index.d.ts +37 -0
  138. package/formly-split-button/README.md +3 -0
  139. package/formly-split-button/index.d.ts +23 -0
  140. package/formly-ui/README.md +3 -0
  141. package/formly-ui/index.d.ts +42 -0
  142. package/formly-username-with-domain/README.md +3 -0
  143. package/formly-username-with-domain/index.d.ts +19 -0
  144. package/generic-autocomplete/README.md +3 -0
  145. package/generic-autocomplete/index.d.ts +41 -0
  146. package/generic-button/README.md +3 -0
  147. package/generic-button/index.d.ts +42 -0
  148. package/generic-card/README.md +3 -0
  149. package/generic-card/index.d.ts +93 -0
  150. package/generic-crud-table/README.md +3 -0
  151. package/generic-crud-table/index.d.ts +129 -0
  152. package/generic-errormessage/README.md +3 -0
  153. package/generic-errormessage/index.d.ts +17 -0
  154. package/generic-formly-fields/README.md +3 -0
  155. package/generic-formly-fields/index.d.ts +26 -0
  156. package/generic-loadingspinner/README.md +3 -0
  157. package/generic-loadingspinner/index.d.ts +16 -0
  158. package/generic-search/README.md +3 -0
  159. package/generic-search/index.d.ts +36 -0
  160. package/generic-selector/README.md +3 -0
  161. package/generic-selector/index.d.ts +73 -0
  162. package/generic-table/README.md +3 -0
  163. package/generic-table/index.d.ts +66 -0
  164. package/header-wrapper/README.md +3 -0
  165. package/header-wrapper/index.d.ts +15 -0
  166. package/icon-picker/README.md +3 -0
  167. package/icon-picker/index.d.ts +30 -0
  168. package/index.d.ts +8 -0
  169. package/input/README.md +3 -0
  170. package/input/index.d.ts +42 -0
  171. package/input-switch/README.md +3 -0
  172. package/input-switch/index.d.ts +16 -0
  173. package/input-with-icon/README.md +3 -0
  174. package/input-with-icon/index.d.ts +17 -0
  175. package/label-type/README.md +3 -0
  176. package/label-type/index.d.ts +26 -0
  177. package/odata-query-builder/README.md +3 -0
  178. package/odata-query-builder/index.d.ts +87 -0
  179. package/package.json +219 -0
  180. package/radio/README.md +3 -0
  181. package/radio/index.d.ts +38 -0
  182. package/repeat/README.md +3 -0
  183. package/repeat/index.d.ts +24 -0
  184. package/select/README.md +3 -0
  185. package/select/index.d.ts +42 -0
  186. package/sidebar-cards/README.md +3 -0
  187. package/sidebar-cards/index.d.ts +25 -0
  188. package/sidebar-toggles/README.md +3 -0
  189. package/sidebar-toggles/index.d.ts +25 -0
  190. package/tabs/README.md +3 -0
  191. package/tabs/index.d.ts +17 -0
  192. package/tag-type/README.md +3 -0
  193. package/tag-type/index.d.ts +34 -0
  194. package/text-editor/README.md +3 -0
  195. package/text-editor/index.d.ts +16 -0
  196. package/textarea/README.md +3 -0
  197. package/textarea/index.d.ts +36 -0
  198. package/ui-button/README.md +3 -0
  199. package/ui-button/index.d.ts +33 -0
  200. package/wrappers/README.md +3 -0
  201. package/wrappers/index.d.ts +31 -0
@@ -0,0 +1,782 @@
1
+ import * as i0 from '@angular/core';
2
+ import { NgModule, ViewChild, Component } from '@angular/core';
3
+ import * as i2 from '@angular/common';
4
+ import { CommonModule } from '@angular/common';
5
+ import { Chip } from 'primeng/chip';
6
+ import * as i9 from '@ngx-translate/core';
7
+ import { TranslateModule } from '@ngx-translate/core';
8
+ import { FieldType } from '@ngx-formly/core';
9
+ import * as i3 from '@angular/forms';
10
+ import { FormsModule } from '@angular/forms';
11
+ import * as i4 from 'primeng/autocomplete';
12
+ import { AutoCompleteModule } from 'primeng/autocomplete';
13
+ import * as i6 from 'primeng/button';
14
+ import { ButtonModule } from 'primeng/button';
15
+ import * as i7 from 'primeng/inputtext';
16
+ import { InputTextModule } from 'primeng/inputtext';
17
+ import * as i8 from 'primeng/dialog';
18
+ import { DialogModule } from 'primeng/dialog';
19
+ import { PopoverModule } from 'primeng/popover';
20
+ import { firstValueFrom, finalize } from 'rxjs';
21
+ import * as i1 from '@elite.framework/ng.core/services';
22
+ import { BaseService } from '@elite.framework/ng.core/services';
23
+ import * as i5 from 'primeng/api';
24
+
25
+ class ConditionEditorModule {
26
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.8", ngImport: i0, type: ConditionEditorModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
27
+ static ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.1.8", ngImport: i0, type: ConditionEditorModule, imports: [CommonModule] });
28
+ static ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.1.8", ngImport: i0, type: ConditionEditorModule, imports: [CommonModule] });
29
+ }
30
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.8", ngImport: i0, type: ConditionEditorModule, decorators: [{
31
+ type: NgModule,
32
+ args: [{
33
+ imports: [CommonModule],
34
+ }]
35
+ }] });
36
+
37
+ const suggestions = [
38
+ {
39
+ label: "عدد دقائق التأخير",
40
+ value: "AttendanceDelayMinutes",
41
+ kind: "Field",
42
+ detail: "عدد دقائق التأخير",
43
+ documentation: "**AttendanceDelayMinutes**\nعدد الدقائق التي تأخر بها الموظف عن بدء الورديّة."
44
+ },
45
+ {
46
+ label: "دقائق الانصراف المبكر",
47
+ value: "EarlyLeaveMinutes",
48
+ kind: "Field",
49
+ detail: "دقائق الانصراف المبكر",
50
+ documentation: "**EarlyLeaveMinutes**\nعدد الدقائق التي سجل بها الموظف انسحابًا مبكرًا عن الورديّة."
51
+ },
52
+ {
53
+ label: "سعر الساعة",
54
+ value: "HourlyRate",
55
+ kind: "Field",
56
+ detail: "سعر الساعة",
57
+ documentation: "**HourlyRate**\nتكلفة الساعة المستخرجة من الراتب الأساسي وساعات العمل المتوقعة."
58
+ },
59
+ {
60
+ label: "قيمة اليوم المتوقعة",
61
+ value: "ScheduledDayValue",
62
+ kind: "Field",
63
+ detail: "قيمة اليوم المتوقعة",
64
+ documentation: "**ScheduledDayValue**\nقيمة اليوم المحسوبة بناءً على السعر بالساعة وساعات الورديّة المتوقعة."
65
+ },
66
+ {
67
+ label: "قيمة اليوم الفعلية",
68
+ value: "ActualDayValue",
69
+ kind: "Field",
70
+ detail: "قيمة اليوم الفعلية",
71
+ documentation: "**ActualDayValue**\nقيمة اليوم المحسوبة بناءً على السعر بالساعة وساعات العمل الفعليّة."
72
+ },
73
+ {
74
+ label: "عدد أيام العمل",
75
+ value: "WorkingDays",
76
+ kind: "Field",
77
+ detail: "عدد أيام العمل",
78
+ documentation: "**WorkingDays**\nعدد الأيام في دفتر الحضور."
79
+ },
80
+ {
81
+ label: "الراتب الأساسي",
82
+ value: "BasicSalary",
83
+ kind: "Field",
84
+ detail: "بند الراتب الأساسي",
85
+ documentation: "**BasicSalary**\n بند الراتب الأساسي."
86
+ },
87
+ // Employee fields
88
+ {
89
+ label: "رمز الموظف",
90
+ value: "Employee.Code",
91
+ kind: "Field",
92
+ detail: "رمز الموظف",
93
+ documentation: "**Employee.Code**\nالرمز الفريد المعطى للموظف في النظام."
94
+ },
95
+ {
96
+ label: "الاسم الكامل",
97
+ value: "Employee.FullName",
98
+ kind: "Field",
99
+ detail: "الاسم الكامل للموظف",
100
+ documentation: "**Employee.FullName**\nالاسم الأول واسم العائلة للموظف."
101
+ },
102
+ {
103
+ label: "نوع الموظف",
104
+ value: "Employee.Type",
105
+ kind: "Field",
106
+ detail: "نوع الموظف",
107
+ documentation: "**Employee.Type**\nنوع الموظف (دوام كامل، مؤقت، الخ)."
108
+ },
109
+ // Shift fields
110
+ {
111
+ label: "اسم الورديّة",
112
+ value: "Shift.Name",
113
+ kind: "Field",
114
+ detail: "اسم الورديّة",
115
+ documentation: "**Shift.Name**\nالاسم المعطى للورديّة (صباحية، مسائية)."
116
+ },
117
+ {
118
+ label: "بداية الورديّة",
119
+ value: "Shift.StartTime",
120
+ kind: "Field",
121
+ detail: "بداية الورديّة",
122
+ documentation: "**Shift.StartTime**\nوقت بدء الورديّة."
123
+ },
124
+ {
125
+ label: "نهاية الورديّة",
126
+ value: "Shift.EndTime",
127
+ kind: "Field",
128
+ detail: "نهاية الورديّة",
129
+ documentation: "**Shift.EndTime**\nوقت نهاية الورديّة."
130
+ },
131
+ {
132
+ label: "رمز نوع الورديّة",
133
+ value: "Shift.TypeKey",
134
+ kind: "Field",
135
+ detail: "رمز نوع الورديّة",
136
+ documentation: "**Shift.TypeKey**\nالمفتاح البرمجي لنوع الورديّة."
137
+ },
138
+ // AttendanceSheet fields
139
+ {
140
+ label: "من تاريخ",
141
+ value: "Sheet.DateFrom",
142
+ kind: "Field",
143
+ detail: "تاريخ بداية الدفتر",
144
+ documentation: "**Sheet.DateFrom**\nأول يوم في دفتر الحضور (اليوم الأول للشهر)."
145
+ },
146
+ {
147
+ label: "إلى تاريخ",
148
+ value: "Sheet.DateTo",
149
+ kind: "Field",
150
+ detail: "تاريخ نهاية الدفتر",
151
+ documentation: "**Sheet.DateTo**\nآخر يوم في دفتر الحضور (اليوم الأخير للشهر)."
152
+ },
153
+ {
154
+ label: "عدد أيام الحضور",
155
+ value: "Sheet.PresentDays",
156
+ kind: "Field",
157
+ detail: "عدد أيام الحضور",
158
+ documentation: "**Sheet.PresentDays**\nعدد الأيام التي سجل فيها الموظف دخول وخروج."
159
+ },
160
+ // AttendanceDay fields
161
+ {
162
+ label: "تاريخ اليوم",
163
+ value: "Day.Date",
164
+ kind: "Field",
165
+ detail: "تاريخ يوم الحضور",
166
+ documentation: "**Day.Date**\nالتاريخ الفعلي ليوم الحضور."
167
+ },
168
+ {
169
+ label: "تسجيل دخول",
170
+ value: "Day.SignIn",
171
+ kind: "Field",
172
+ detail: "وقت تسجيل دخول الموظف",
173
+ documentation: "**Day.SignIn**\nالطابع الزمني لتسجيل دخول الموظف."
174
+ },
175
+ {
176
+ label: "تسجيل خروج",
177
+ value: "Day.SignOut",
178
+ kind: "Field",
179
+ detail: "وقت تسجيل خروج الموظف",
180
+ documentation: "**Day.SignOut**\nالطابع الزمني لتسجيل خروج الموظف."
181
+ },
182
+ // LeavePolicy fields
183
+ {
184
+ label: "اسم سياسة الإجازة",
185
+ value: "LeavePolicy.Name",
186
+ kind: "Field",
187
+ detail: "اسم سياسة الإجازة",
188
+ documentation: "**LeavePolicy.Name**\nالاسم المعطى لسياسة الإجازة."
189
+ },
190
+ {
191
+ label: "رمز الحالة",
192
+ value: "LeavePolicy.StatusKey",
193
+ kind: "Field",
194
+ detail: "رمز حالة السياسة",
195
+ documentation: "**LeavePolicy.StatusKey**\nالمفتاح البرمجي لحالة سياسة الإجازة."
196
+ },
197
+ {
198
+ label: "حالة السياسة",
199
+ value: "LeavePolicy.Status",
200
+ kind: "Field",
201
+ detail: "حالة السياسة",
202
+ documentation: "**LeavePolicy.Status**\nالوصف الكامل لحالة سياسة الإجازة."
203
+ },
204
+ // Leave fields
205
+ {
206
+ label: "بداية الإجازة",
207
+ value: "Leave.DateStart",
208
+ kind: "Field",
209
+ detail: "بداية الإجازة",
210
+ documentation: "**Leave.DateStart**\nاليوم الأول للإجازة."
211
+ },
212
+ {
213
+ label: "نهاية الإجازة",
214
+ value: "Leave.DateEnd",
215
+ kind: "Field",
216
+ detail: "نهاية الإجازة",
217
+ documentation: "**Leave.DateEnd**\nاليوم الأخير للإجازة."
218
+ },
219
+ // SalaryTemplate fields
220
+ // {
221
+ // label: "بنود الأرباح",
222
+ // value: "template.Earnings",
223
+ // kind: "Field",
224
+ // detail: "قائمة بنود الأرباح",
225
+ // documentation: "**SalaryTemplate.Earnings**\nقائمة العناصر التي تمثل مستحقات (أرباح) القالب."
226
+ // },
227
+ // {
228
+ // label: "بنود الاستقطاعات",
229
+ // value: "template.Deductions",
230
+ // kind: "Field",
231
+ // detail: "قائمة بنود الاستقطاعات",
232
+ // documentation: "**SalaryTemplate.Deductions**\nقائمة العناصر التي تمثل استقطاعات القالب."
233
+ // },
234
+ // // SalaryTemplateItem fields
235
+ // {
236
+ // label: "المبلغ الثابت للبند",
237
+ // value: "item.Amount",
238
+ // kind: "Field",
239
+ // detail: "المبلغ الثابت للبند",
240
+ // documentation: "**SalaryTemplateItem.Amount**\nالقيمة الثابتة المخصصة لهذا البند."
241
+ // },
242
+ // {
243
+ // label: "صيغة البند",
244
+ // value: "item.Formula",
245
+ // kind: "Field",
246
+ // detail: "الصيغة الحسابية للبند",
247
+ // documentation: "**SalaryTemplateItem.Formula**\nالصيغة البرمجية لتعريف قيمة البند عند SalaryValueType = Formula."
248
+ // },
249
+ { label: '(Leave) Total Leaves Taken', value: 'GetLeaveTaken(leaveId)', detail: 'إجمالي الإجازات المأخوذة' },
250
+ { label: '(Leave) Total Leaves Taken Before', value: 'GetLeaveTakenBefore(leaveId)', detail: 'إجمالي الإجازات المأخوذة قبل' },
251
+ { label: '(Leave) Total Leaves After', value: 'GetLeaveTakenAfter(leaveId)', detail: 'إجمالي الإجازات المأخوذة بعد' },
252
+ { label: '(Leave) Leaves Credit Before', value: 'GetLeaveCreditBefore(leaveId)', detail: 'رصيد الإجازات قبل' },
253
+ { label: '(Leave) Leaves Credit After', value: 'GetLeaveCreditAfter(leaveId)', detail: 'رصيد الإجازات بعد' },
254
+ { label: 'عدد مرات تحقق القاعدة', value: 'GetFlagCount(ruleId)', detail: 'عدد مرات تحقق القاعدة خلال الفترة' },
255
+ { label: 'إجمالي قيمة القاعدة', value: 'GetFlagValue(ruleId)', detail: 'القيمة الإجمالية للقاعدة' },
256
+ { label: 'أكبر من', value: '>', detail: 'القيمة الأولى أكبر من الثانية' },
257
+ { label: 'أكبر من أو يساوي', value: '>=', detail: 'القيمة الأولى أكبر من أو تساوي الثانية' },
258
+ { label: 'أصغر من', value: '<', detail: 'القيمة الأولى أصغر من الثانية' },
259
+ { label: 'أصغر من أو يساوي', value: '<=', detail: 'القيمة الأولى أصغر من أو تساوي الثانية' },
260
+ { label: 'يساوي', value: '==', detail: 'القيمتان متساويتان' },
261
+ { label: 'لا يساوي', value: '!=', detail: 'القيمتان غير متساويتان' },
262
+ { label: 'و (AND)', value: '&&', detail: 'تتحقق إذا كان الشرطان صحيحين' },
263
+ { label: 'أو (OR)', value: '||', detail: 'تتحقق إذا كان أحد الشرطين صحيحاً' },
264
+ { label: 'صحيح', value: 'true', detail: 'القيمة صحيحة' },
265
+ { label: 'خطأ', value: 'false', detail: 'القيمة خاطئة' }
266
+ ];
267
+
268
+ class ConditionExpressionBuilderType extends FieldType {
269
+ svc;
270
+ cdr;
271
+ // @ViewChild('paramOverlay') paramOverlay!: OverlayPanel;
272
+ autoComp;
273
+ op;
274
+ tokens = [];
275
+ selectedSuggestion;
276
+ customValue = '';
277
+ filteredSuggestions = [];
278
+ // Dialog state
279
+ displayDialog = false;
280
+ dialogSelectedRule = null;
281
+ pendingSuggestion = null;
282
+ filteredRuleSuggestions = [];
283
+ suggestions = suggestions;
284
+ loading = false;
285
+ api;
286
+ dialogMode = '';
287
+ displayMode = 'full';
288
+ editDialogTitle = 'Edit Expression';
289
+ displayEditDialog = false;
290
+ /**
291
+ *
292
+ */
293
+ valueChangeSubscription;
294
+ constructor(svc, cdr) {
295
+ super();
296
+ this.svc = svc;
297
+ this.cdr = cdr;
298
+ }
299
+ ngOnInit() {
300
+ this.api = this.svc;
301
+ const to = this.props;
302
+ this.api.apiName = to['serviceName'];
303
+ this.displayMode = to['displayMode'] ?? 'full';
304
+ this.initTokens();
305
+ this.valueChangeSubscription = this.formControl.valueChanges
306
+ .subscribe(() => {
307
+ this.initTokens();
308
+ });
309
+ }
310
+ ngOnDestroy() {
311
+ if (this.valueChangeSubscription) {
312
+ this.valueChangeSubscription.unsubscribe();
313
+ }
314
+ }
315
+ initTokens() {
316
+ const existing = this.formControl.value || '';
317
+ if (existing) {
318
+ const tokens = existing.split(' ').filter((x) => x);
319
+ Promise.all(tokens.map(async (v) => ({
320
+ value: v,
321
+ label: await this.getLabelForValue(v)
322
+ }))).then(resolvedTokens => {
323
+ this.tokens = resolvedTokens;
324
+ this.cdr.detectChanges(); // <-- Trigger UI update
325
+ });
326
+ }
327
+ else {
328
+ this.tokens = [];
329
+ }
330
+ }
331
+ openDialogForTableMode() {
332
+ // You can reuse your dialog logic here
333
+ this.displayDialog = true;
334
+ this.dialogMode = 'rule'; // or 'leave', depending on your case
335
+ }
336
+ parseParameterizedToken(value) {
337
+ const match = value.match(/^(\w+)\(([^)]+)\)$/);
338
+ if (match) {
339
+ return { base: match[1], param: match[2] };
340
+ }
341
+ return null;
342
+ }
343
+ async getLabelForValue(value) {
344
+ const paramToken = this.parseParameterizedToken(value);
345
+ if (paramToken) {
346
+ let paramLabel = paramToken.param;
347
+ // Find matching base suggestion early (optional)
348
+ const baseSuggestion = this.suggestions.find(s => s.value === `${paramToken.base}(ruleId)` ||
349
+ s.value === `${paramToken.base}(leaveId)` ||
350
+ s.value === paramToken.base);
351
+ if (value.includes('(ruleId)') || paramToken.base.toLowerCase().includes('flag')) {
352
+ this.api.apiName = this.props['ruleServiceName'];
353
+ try {
354
+ const res = await firstValueFrom(this.api.get(paramToken.param).pipe());
355
+ // Assuming API returns { items: [...] } or array directly
356
+ // const matchedRule = (res.items ?? res ?? []).find((r: any) => r.id == Number(paramToken.param));
357
+ const matchedRule = res;
358
+ if (matchedRule)
359
+ paramLabel = matchedRule.label || matchedRule.name || paramLabel;
360
+ }
361
+ catch {
362
+ // ignore errors, fallback to param value
363
+ }
364
+ }
365
+ if (value.includes('(leaveId)') || paramToken.base.toLowerCase().includes('leave')) {
366
+ this.api.apiName = this.props['leaveServiceName'];
367
+ try {
368
+ const res = await firstValueFrom(this.api.getList(paramToken.param).pipe());
369
+ const matchedLeave = res;
370
+ if (matchedLeave)
371
+ paramLabel = matchedLeave.label || matchedLeave.name || paramLabel;
372
+ }
373
+ catch {
374
+ // ignore errors
375
+ }
376
+ }
377
+ if (baseSuggestion) {
378
+ const baseLabel = baseSuggestion.label
379
+ .replace(/\(ruleId\)/g, '')
380
+ .replace(/\(leaveId\)/g, '')
381
+ .trim();
382
+ return `${baseLabel} (${paramLabel})`;
383
+ }
384
+ }
385
+ // fallback exact match in suggestions
386
+ const exact = this.suggestions.find(s => s.value === value);
387
+ if (exact)
388
+ return exact.label;
389
+ return value;
390
+ }
391
+ filterSuggestions(event) {
392
+ const query = event.query.toLowerCase();
393
+ this.filteredSuggestions = this.suggestions.filter(s => {
394
+ const paramToken = this.parseParameterizedToken(s.value);
395
+ const baseValue = paramToken ? paramToken.base : s.value;
396
+ return (s.label.toLowerCase().includes(query) ||
397
+ baseValue.toLowerCase().includes(query) ||
398
+ s.value.toLowerCase().includes(query));
399
+ });
400
+ }
401
+ search(event) {
402
+ this.api.apiName = this.dialogMode === 'rule'
403
+ ? this.props['ruleServiceName'] // existing rules service
404
+ : this.props['leaveServiceName']; // new leave service
405
+ const q = event.query?.toString().toLowerCase() || '';
406
+ const lf = this.props['labelField'] || 'name';
407
+ const fixedFilters = this.props['fixedFilters'] || {};
408
+ this.loading = true;
409
+ this.filteredRuleSuggestions = [];
410
+ const searchParams = {
411
+ [lf]: q,
412
+ ...fixedFilters,
413
+ };
414
+ this.api.getList(searchParams)
415
+ .pipe(finalize(() => (this.loading = false)))
416
+ .subscribe({
417
+ next: (res) => {
418
+ this.filteredRuleSuggestions = res.items ?? res ?? [];
419
+ setTimeout(() => this.autoComp?.show(), 0);
420
+ },
421
+ error: () => {
422
+ this.filteredRuleSuggestions = [];
423
+ },
424
+ });
425
+ }
426
+ onSuggestionRule(event) {
427
+ const suggestion = event.value;
428
+ if (!suggestion)
429
+ return;
430
+ this.dialogSelectedRule = suggestion;
431
+ }
432
+ async onSuggestionSelected(event) {
433
+ const suggestion = event.value;
434
+ if (!suggestion)
435
+ return;
436
+ if (suggestion.value.includes('(ruleId)') || suggestion.value.includes('(leaveId)')) {
437
+ this.pendingSuggestion = suggestion;
438
+ this.dialogSelectedRule = null;
439
+ this.displayDialog = true;
440
+ // Detect mode: rule or leave
441
+ this.dialogMode = suggestion.value.includes('(ruleId)') ? 'rule' : 'leave';
442
+ }
443
+ else {
444
+ this.tokens.push({
445
+ value: suggestion.value,
446
+ label: await this.getLabelForValue(suggestion.value)
447
+ });
448
+ this.updateExpression();
449
+ }
450
+ this.selectedSuggestion = '';
451
+ }
452
+ async confirmDialog() {
453
+ if (!this.pendingSuggestion || !this.dialogSelectedRule)
454
+ return;
455
+ const paramValue = this.dialogSelectedRule.id
456
+ || this.dialogSelectedRule.value
457
+ || this.dialogSelectedRule.label;
458
+ const placeholder = this.dialogMode === 'rule' ? '(ruleId)' : '(leaveId)';
459
+ const newValue = this.pendingSuggestion.value.replace(placeholder, `(${paramValue})`);
460
+ this.tokens.push({
461
+ value: newValue,
462
+ label: await this.getLabelForValue(newValue)
463
+ });
464
+ this.updateExpression();
465
+ this.closeDialog();
466
+ }
467
+ cancelDialog() {
468
+ this.closeDialog();
469
+ }
470
+ closeDialog() {
471
+ this.displayDialog = false;
472
+ this.dialogSelectedRule = null;
473
+ this.pendingSuggestion = null;
474
+ }
475
+ async addCustomToken() {
476
+ if (!this.customValue.trim())
477
+ return;
478
+ const val = this.customValue.trim();
479
+ this.tokens.push({
480
+ value: val,
481
+ label: await this.getLabelForValue(val)
482
+ });
483
+ this.updateExpression();
484
+ this.customValue = '';
485
+ }
486
+ removeToken(index) {
487
+ this.tokens.splice(index, 1);
488
+ this.updateExpression();
489
+ }
490
+ updateExpression() {
491
+ const expression = this.tokens.map(t => t.value).join(' ');
492
+ this.formControl.setValue(expression);
493
+ if (this.to['expressionChange']) {
494
+ this.to['expressionChange'].emit(expression);
495
+ }
496
+ }
497
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.8", ngImport: i0, type: ConditionExpressionBuilderType, deps: [{ token: i1.BaseService }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component });
498
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.1.8", type: ConditionExpressionBuilderType, isStandalone: true, selector: "condition-expression-builder", providers: [BaseService], viewQueries: [{ propertyName: "autoComp", first: true, predicate: ["autoComp"], descendants: true }, { propertyName: "op", first: true, predicate: ["op"], descendants: true }], usesInheritance: true, ngImport: i0, template: `
499
+ <div class="flex flex-col gap-3">
500
+
501
+ <!-- TABLE MODE -->
502
+ @if (displayMode === 'table') {
503
+ <div class="flex gap-2">
504
+ <div class="flex flex-wrap flex-1 gap-1">
505
+ <div class="border rounded-md p-2 bg-gray-50 flex flex-wrap gap-2 min-h-[40px] items-center">
506
+
507
+
508
+ @for (token of tokens; track $index) {
509
+ <span class="px-2 py-1 rounded bg-blue-100 text-blue-800 flex items-center gap-1">
510
+ {{ token.label | translate }}
511
+ </span>
512
+ }
513
+ </div>
514
+ </div>
515
+ <button type="button" pButton icon="pi pi-pencil" label=""
516
+ class="p-button-sm"
517
+ (click)="displayEditDialog = true"></button>
518
+ </div>
519
+
520
+ <!-- Dialog with full editor inside -->
521
+ <p-dialog [(visible)]="displayEditDialog" [modal]="false" [style]="{width: '700px'}">
522
+
523
+ <ng-template pTemplate="header">
524
+ {{ editDialogTitle | translate }}
525
+ </ng-template>
526
+
527
+ <div class="p-4 space-y-4">
528
+ <ng-container *ngTemplateOutlet="fullEditorTpl"></ng-container>
529
+ </div>
530
+
531
+ </p-dialog>
532
+ }
533
+ @else{
534
+ <ng-container *ngTemplateOutlet="fullEditorTpl"></ng-container>
535
+ }
536
+
537
+
538
+ <!-- FULL MODE -->
539
+ <ng-template #fullEditorTpl>
540
+ <!-- Your existing full UI layout here -->
541
+ <div class="flex flex-col gap-3">
542
+
543
+ <!-- Expression preview -->
544
+ <div class="border rounded-md p-2 bg-gray-50 flex flex-wrap gap-2 min-h-[40px] items-center">
545
+ @for (token of tokens; track $index) {
546
+ <span class="px-2 py-1 rounded bg-blue-100 text-blue-800 flex items-center gap-1">
547
+ {{ token.label | translate }}
548
+ <button type="button" pButton icon="pi pi-times"
549
+ class="p-button-rounded p-button-text p-button-sm"
550
+ (click)="removeToken($index)">
551
+ </button>
552
+ </span>
553
+ }
554
+ </div>
555
+
556
+ <!-- Autocomplete for suggestions -->
557
+ <p-autoComplete
558
+ [(ngModel)]="selectedSuggestion"
559
+ field="label"
560
+ [suggestions]="filteredSuggestions"
561
+ (completeMethod)="filterSuggestions($event)"
562
+ (onSelect)="onSuggestionSelected($event)"
563
+ placeholder="اكتب للبحث عن الحقول أو العمليات أو الدوال..."
564
+ [forceSelection]="false"
565
+ [dropdown]="true"
566
+ dropdownMode="current"
567
+ appendTo="body"
568
+ class="w-full"
569
+ >
570
+ <ng-template let-suggestion pTemplate="item">
571
+ <div>
572
+ <strong>{{ suggestion.label | translate}}</strong>
573
+ <small class="block text-gray-500">{{ suggestion.detail| translate }}</small>
574
+ </div>
575
+ </ng-template>
576
+ </p-autoComplete>
577
+
578
+ <!-- Add custom value -->
579
+ <div class="flex gap-2">
580
+ <input pInputText type="text" [(ngModel)]="customValue" placeholder="أدخل قيمة ثابتة..." class="flex-1">
581
+ <button pButton label="إضافة" icon="pi pi-plus" (click)="addCustomToken()" class="p-button-sm" type="button"></button>
582
+ </div>
583
+
584
+ <!-- Parameter input dialog -->
585
+ <p-dialog [(visible)]="displayDialog" [modal]="false" [closable]="false" [style]="{width: '400px'}">
586
+ <ng-template pTemplate="header">
587
+ {{ (dialogMode === 'rule' ? 'اختر القاعدة' : 'اختر الإجازة') | translate }}
588
+ </ng-template>
589
+
590
+ <div class="p-4 space-y-4">
591
+ <p-autoComplete
592
+ #autoComp
593
+ [(ngModel)]="dialogSelectedRule"
594
+ field="name"
595
+ optionLabel="name"
596
+ [suggestions]="filteredRuleSuggestions"
597
+ (completeMethod)="search($event)"
598
+ (onSelect)="onSuggestionRule($event)"
599
+ placeholder="{{ dialogMode === 'rule' ? 'ابحث عن قاعدة' : 'ابحث عن إجازة' }}"
600
+ [forceSelection]="true"
601
+ [dropdown]="true"
602
+ dropdownMode="current"
603
+ appendTo="body"
604
+ class="w-full rounded-none"
605
+ >
606
+ <ng-template let-suggestion pTemplate="item">
607
+ <div>
608
+ <strong>{{ suggestion.name | translate}}</strong>
609
+ <small class="block text-gray-500">{{ suggestion.description | translate}}</small>
610
+ </div>
611
+ </ng-template>
612
+ </p-autoComplete>
613
+ </div>
614
+
615
+ <p-footer class="flex justify-end gap-2">
616
+ <button type="button" pButton label="إلغاء" icon="pi pi-times" class="p-button-text" severity="danger" (click)="cancelDialog()"></button>
617
+ <button type="button" pButton label="موافق" icon="pi pi-check" (click)="confirmDialog()" [disabled]="!dialogSelectedRule"></button>
618
+ </p-footer>
619
+ </p-dialog>
620
+ </div>
621
+ </ng-template>
622
+ </div>
623
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i2.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i3.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "ngmodule", type: AutoCompleteModule }, { kind: "component", type: i4.AutoComplete, selector: "p-autoComplete, p-autocomplete, p-auto-complete", inputs: ["minLength", "minQueryLength", "delay", "panelStyle", "styleClass", "panelStyleClass", "inputStyle", "inputId", "inputStyleClass", "placeholder", "readonly", "scrollHeight", "lazy", "virtualScroll", "virtualScrollItemSize", "virtualScrollOptions", "autoHighlight", "forceSelection", "type", "autoZIndex", "baseZIndex", "ariaLabel", "dropdownAriaLabel", "ariaLabelledBy", "dropdownIcon", "unique", "group", "completeOnFocus", "showClear", "dropdown", "showEmptyMessage", "dropdownMode", "multiple", "tabindex", "dataKey", "emptyMessage", "showTransitionOptions", "hideTransitionOptions", "autofocus", "autocomplete", "optionGroupChildren", "optionGroupLabel", "overlayOptions", "suggestions", "optionLabel", "optionValue", "id", "searchMessage", "emptySelectionMessage", "selectionMessage", "autoOptionFocus", "selectOnFocus", "searchLocale", "optionDisabled", "focusOnHover", "typeahead", "appendTo"], outputs: ["completeMethod", "onSelect", "onUnselect", "onFocus", "onBlur", "onDropdownClick", "onClear", "onKeyUp", "onShow", "onHide", "onLazyLoad"] }, { kind: "component", type: i5.Footer, selector: "p-footer" }, { kind: "directive", type: i5.PrimeTemplate, selector: "[pTemplate]", inputs: ["type", "pTemplate"] }, { kind: "ngmodule", type: ButtonModule }, { kind: "directive", type: i6.ButtonDirective, selector: "[pButton]", inputs: ["iconPos", "loadingIcon", "loading", "severity", "raised", "rounded", "text", "outlined", "size", "plain", "fluid", "label", "icon", "buttonProps"] }, { kind: "ngmodule", type: InputTextModule }, { kind: "directive", type: i7.InputText, selector: "[pInputText]", inputs: ["pSize", "variant", "fluid", "invalid"] }, { kind: "ngmodule", type: DialogModule }, { kind: "component", type: i8.Dialog, selector: "p-dialog", inputs: ["header", "draggable", "resizable", "contentStyle", "contentStyleClass", "modal", "closeOnEscape", "dismissableMask", "rtl", "closable", "breakpoints", "styleClass", "maskStyleClass", "maskStyle", "showHeader", "blockScroll", "autoZIndex", "baseZIndex", "minX", "minY", "focusOnShow", "maximizable", "keepInViewport", "focusTrap", "transitionOptions", "closeIcon", "closeAriaLabel", "closeTabindex", "minimizeIcon", "maximizeIcon", "closeButtonProps", "maximizeButtonProps", "visible", "style", "position", "role", "appendTo", "content", "contentTemplate", "footerTemplate", "closeIconTemplate", "maximizeIconTemplate", "minimizeIconTemplate", "headlessTemplate"], outputs: ["onShow", "onHide", "visibleChange", "onResizeInit", "onResizeEnd", "onDragEnd", "onMaximize"] }, { kind: "ngmodule", type: PopoverModule }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i9.TranslatePipe, name: "translate" }] });
624
+ }
625
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.8", ngImport: i0, type: ConditionExpressionBuilderType, decorators: [{
626
+ type: Component,
627
+ args: [{
628
+ selector: 'condition-expression-builder',
629
+ standalone: true,
630
+ imports: [
631
+ CommonModule,
632
+ FormsModule,
633
+ AutoCompleteModule,
634
+ Chip,
635
+ ButtonModule,
636
+ InputTextModule,
637
+ DialogModule,
638
+ PopoverModule,
639
+ TranslateModule
640
+ ],
641
+ providers: [BaseService],
642
+ template: `
643
+ <div class="flex flex-col gap-3">
644
+
645
+ <!-- TABLE MODE -->
646
+ @if (displayMode === 'table') {
647
+ <div class="flex gap-2">
648
+ <div class="flex flex-wrap flex-1 gap-1">
649
+ <div class="border rounded-md p-2 bg-gray-50 flex flex-wrap gap-2 min-h-[40px] items-center">
650
+
651
+
652
+ @for (token of tokens; track $index) {
653
+ <span class="px-2 py-1 rounded bg-blue-100 text-blue-800 flex items-center gap-1">
654
+ {{ token.label | translate }}
655
+ </span>
656
+ }
657
+ </div>
658
+ </div>
659
+ <button type="button" pButton icon="pi pi-pencil" label=""
660
+ class="p-button-sm"
661
+ (click)="displayEditDialog = true"></button>
662
+ </div>
663
+
664
+ <!-- Dialog with full editor inside -->
665
+ <p-dialog [(visible)]="displayEditDialog" [modal]="false" [style]="{width: '700px'}">
666
+
667
+ <ng-template pTemplate="header">
668
+ {{ editDialogTitle | translate }}
669
+ </ng-template>
670
+
671
+ <div class="p-4 space-y-4">
672
+ <ng-container *ngTemplateOutlet="fullEditorTpl"></ng-container>
673
+ </div>
674
+
675
+ </p-dialog>
676
+ }
677
+ @else{
678
+ <ng-container *ngTemplateOutlet="fullEditorTpl"></ng-container>
679
+ }
680
+
681
+
682
+ <!-- FULL MODE -->
683
+ <ng-template #fullEditorTpl>
684
+ <!-- Your existing full UI layout here -->
685
+ <div class="flex flex-col gap-3">
686
+
687
+ <!-- Expression preview -->
688
+ <div class="border rounded-md p-2 bg-gray-50 flex flex-wrap gap-2 min-h-[40px] items-center">
689
+ @for (token of tokens; track $index) {
690
+ <span class="px-2 py-1 rounded bg-blue-100 text-blue-800 flex items-center gap-1">
691
+ {{ token.label | translate }}
692
+ <button type="button" pButton icon="pi pi-times"
693
+ class="p-button-rounded p-button-text p-button-sm"
694
+ (click)="removeToken($index)">
695
+ </button>
696
+ </span>
697
+ }
698
+ </div>
699
+
700
+ <!-- Autocomplete for suggestions -->
701
+ <p-autoComplete
702
+ [(ngModel)]="selectedSuggestion"
703
+ field="label"
704
+ [suggestions]="filteredSuggestions"
705
+ (completeMethod)="filterSuggestions($event)"
706
+ (onSelect)="onSuggestionSelected($event)"
707
+ placeholder="اكتب للبحث عن الحقول أو العمليات أو الدوال..."
708
+ [forceSelection]="false"
709
+ [dropdown]="true"
710
+ dropdownMode="current"
711
+ appendTo="body"
712
+ class="w-full"
713
+ >
714
+ <ng-template let-suggestion pTemplate="item">
715
+ <div>
716
+ <strong>{{ suggestion.label | translate}}</strong>
717
+ <small class="block text-gray-500">{{ suggestion.detail| translate }}</small>
718
+ </div>
719
+ </ng-template>
720
+ </p-autoComplete>
721
+
722
+ <!-- Add custom value -->
723
+ <div class="flex gap-2">
724
+ <input pInputText type="text" [(ngModel)]="customValue" placeholder="أدخل قيمة ثابتة..." class="flex-1">
725
+ <button pButton label="إضافة" icon="pi pi-plus" (click)="addCustomToken()" class="p-button-sm" type="button"></button>
726
+ </div>
727
+
728
+ <!-- Parameter input dialog -->
729
+ <p-dialog [(visible)]="displayDialog" [modal]="false" [closable]="false" [style]="{width: '400px'}">
730
+ <ng-template pTemplate="header">
731
+ {{ (dialogMode === 'rule' ? 'اختر القاعدة' : 'اختر الإجازة') | translate }}
732
+ </ng-template>
733
+
734
+ <div class="p-4 space-y-4">
735
+ <p-autoComplete
736
+ #autoComp
737
+ [(ngModel)]="dialogSelectedRule"
738
+ field="name"
739
+ optionLabel="name"
740
+ [suggestions]="filteredRuleSuggestions"
741
+ (completeMethod)="search($event)"
742
+ (onSelect)="onSuggestionRule($event)"
743
+ placeholder="{{ dialogMode === 'rule' ? 'ابحث عن قاعدة' : 'ابحث عن إجازة' }}"
744
+ [forceSelection]="true"
745
+ [dropdown]="true"
746
+ dropdownMode="current"
747
+ appendTo="body"
748
+ class="w-full rounded-none"
749
+ >
750
+ <ng-template let-suggestion pTemplate="item">
751
+ <div>
752
+ <strong>{{ suggestion.name | translate}}</strong>
753
+ <small class="block text-gray-500">{{ suggestion.description | translate}}</small>
754
+ </div>
755
+ </ng-template>
756
+ </p-autoComplete>
757
+ </div>
758
+
759
+ <p-footer class="flex justify-end gap-2">
760
+ <button type="button" pButton label="إلغاء" icon="pi pi-times" class="p-button-text" severity="danger" (click)="cancelDialog()"></button>
761
+ <button type="button" pButton label="موافق" icon="pi pi-check" (click)="confirmDialog()" [disabled]="!dialogSelectedRule"></button>
762
+ </p-footer>
763
+ </p-dialog>
764
+ </div>
765
+ </ng-template>
766
+ </div>
767
+ `
768
+ }]
769
+ }], ctorParameters: () => [{ type: i1.BaseService }, { type: i0.ChangeDetectorRef }], propDecorators: { autoComp: [{
770
+ type: ViewChild,
771
+ args: ['autoComp']
772
+ }], op: [{
773
+ type: ViewChild,
774
+ args: ['op']
775
+ }] } });
776
+
777
+ /**
778
+ * Generated bundle index. Do not edit.
779
+ */
780
+
781
+ export { ConditionEditorModule, ConditionExpressionBuilderType, suggestions };
782
+ //# sourceMappingURL=elite.framework-ng.ui.core-condition-editor.mjs.map