@alepha/ui 0.18.2 → 0.18.3

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 (231) hide show
  1. package/dist/admin/{AdminApiKeys-BJhIwfD6.js → AdminApiKeys-Dy_k-4Vd.js} +2 -2
  2. package/dist/admin/{AdminApiKeys-BJhIwfD6.js.map → AdminApiKeys-Dy_k-4Vd.js.map} +1 -1
  3. package/dist/admin/{AdminAudits-DzD_4cDt.js → AdminAudits-CKiFMSSU.js} +2 -2
  4. package/dist/admin/{AdminAudits-DzD_4cDt.js.map → AdminAudits-CKiFMSSU.js.map} +1 -1
  5. package/dist/admin/{AdminDashboard-C92tIc6x.js → AdminDashboard-PhC_dZqo.js} +2 -2
  6. package/dist/admin/{AdminDashboard-C92tIc6x.js.map → AdminDashboard-PhC_dZqo.js.map} +1 -1
  7. package/dist/admin/{AdminFiles-DLpfhBkf.js → AdminFiles-DFTjijGp.js} +2 -2
  8. package/dist/admin/{AdminFiles-DLpfhBkf.js.map → AdminFiles-DFTjijGp.js.map} +1 -1
  9. package/dist/admin/{AdminJobDashboard-KIOkeMgE.js → AdminJobDashboard-BL8gGPDp.js} +2 -2
  10. package/dist/admin/{AdminJobDashboard-KIOkeMgE.js.map → AdminJobDashboard-BL8gGPDp.js.map} +1 -1
  11. package/dist/admin/{AdminJobExecutions-D0Yo_PU0.js → AdminJobExecutions-D9E-CS-U.js} +2 -2
  12. package/dist/admin/{AdminJobExecutions-D0Yo_PU0.js.map → AdminJobExecutions-D9E-CS-U.js.map} +1 -1
  13. package/dist/admin/{AdminJobRegistry-PFajqaGK.js → AdminJobRegistry-Ci9ue1zC.js} +2 -2
  14. package/dist/admin/{AdminJobRegistry-PFajqaGK.js.map → AdminJobRegistry-Ci9ue1zC.js.map} +1 -1
  15. package/dist/admin/{AdminLayout-B1DXZHDn.js → AdminLayout-I6TlUMPc.js} +2 -2
  16. package/dist/admin/{AdminLayout-B1DXZHDn.js.map → AdminLayout-I6TlUMPc.js.map} +1 -1
  17. package/dist/admin/AdminNotifications-ZPHCYrv7.js +542 -0
  18. package/dist/admin/AdminNotifications-ZPHCYrv7.js.map +1 -0
  19. package/dist/admin/{AdminParameters-BspPeqp_.js → AdminParameters-CqgvhRsb.js} +120 -105
  20. package/dist/admin/AdminParameters-CqgvhRsb.js.map +1 -0
  21. package/dist/admin/{AdminSessions-BnH5CZQl.js → AdminSessions-Bz5NRuoW.js} +2 -2
  22. package/dist/admin/{AdminSessions-BnH5CZQl.js.map → AdminSessions-Bz5NRuoW.js.map} +1 -1
  23. package/dist/admin/{AdminUserLayout-DUbC6-BI.js → AdminUserLayout-lXT6I0Qq.js} +14 -8
  24. package/dist/admin/AdminUserLayout-lXT6I0Qq.js.map +1 -0
  25. package/dist/admin/{AdminUserProfile-DuTUnjdG.js → AdminUserProfile-vFBLoJ3h.js} +3 -3
  26. package/dist/admin/{AdminUserProfile-DuTUnjdG.js.map → AdminUserProfile-vFBLoJ3h.js.map} +1 -1
  27. package/dist/admin/{AdminUserSessions-DvZdAGpL.js → AdminUserSessions-CT_YDim0.js} +2 -2
  28. package/dist/admin/{AdminUserSessions-DvZdAGpL.js.map → AdminUserSessions-CT_YDim0.js.map} +1 -1
  29. package/dist/admin/{AdminUsers-CR9z0g_5.js → AdminUsers-D1UfGya9.js} +2 -2
  30. package/dist/admin/{AdminUsers-CR9z0g_5.js.map → AdminUsers-D1UfGya9.js.map} +1 -1
  31. package/dist/admin/{AuthLayout-DsUfp9RG.js → AuthLayout-_frhdgOO.js} +2 -2
  32. package/dist/admin/{AuthLayout-DsUfp9RG.js.map → AuthLayout-_frhdgOO.js.map} +1 -1
  33. package/dist/admin/Login-xtNmQtGh.js +275 -0
  34. package/dist/admin/Login-xtNmQtGh.js.map +1 -0
  35. package/dist/admin/{Profile-B2EcIDB9.js → Profile-_AtPUwAP.js} +31 -27
  36. package/dist/admin/Profile-_AtPUwAP.js.map +1 -0
  37. package/dist/admin/{Register-Z3fxRbUF.js → Register-JcCjHUUn.js} +198 -142
  38. package/dist/admin/Register-JcCjHUUn.js.map +1 -0
  39. package/dist/admin/{ResetPassword-_Y1qTTKh.js → ResetPassword-CwGBPLJO.js} +7 -7
  40. package/dist/admin/ResetPassword-CwGBPLJO.js.map +1 -0
  41. package/dist/admin/{VerifyEmail-Bg22bwcC.js → VerifyEmail-hNxWejWf.js} +23 -8
  42. package/dist/admin/VerifyEmail-hNxWejWf.js.map +1 -0
  43. package/dist/admin/{core-BVO_TQxb.js → core-CYaRQ8O-.js} +709 -556
  44. package/dist/admin/core-CYaRQ8O-.js.map +1 -0
  45. package/dist/admin/index.d.ts +83 -44
  46. package/dist/admin/index.d.ts.map +1 -1
  47. package/dist/admin/index.js +58 -39
  48. package/dist/admin/index.js.map +1 -1
  49. package/dist/auth/{AuthLayout-C161NeF6.js → AuthLayout-AvLlcLjS.js} +2 -2
  50. package/dist/auth/{AuthLayout-C161NeF6.js.map → AuthLayout-AvLlcLjS.js.map} +1 -1
  51. package/dist/auth/Login-BA1E8IZl.js +275 -0
  52. package/dist/auth/Login-BA1E8IZl.js.map +1 -0
  53. package/dist/auth/{Profile-BMpXJ0oi.js → Profile-YcWdeuFz.js} +31 -27
  54. package/dist/auth/Profile-YcWdeuFz.js.map +1 -0
  55. package/dist/auth/{Register-2gx8qll-.js → Register-CPhEO5MG.js} +198 -142
  56. package/dist/auth/Register-CPhEO5MG.js.map +1 -0
  57. package/dist/{demo/ResetPassword-CAPj8MO3.js → auth/ResetPassword-DCtGcneA.js} +7 -7
  58. package/dist/auth/ResetPassword-DCtGcneA.js.map +1 -0
  59. package/dist/{demo/VerifyEmail-DFmdCdYs.js → auth/VerifyEmail-DkH7NBfn.js} +23 -8
  60. package/dist/auth/VerifyEmail-DkH7NBfn.js.map +1 -0
  61. package/dist/auth/{core-DyfeVr5c.js → core-D5jIAVF2.js} +386 -294
  62. package/dist/auth/core-D5jIAVF2.js.map +1 -0
  63. package/dist/auth/index.d.ts +93 -48
  64. package/dist/auth/index.d.ts.map +1 -1
  65. package/dist/auth/index.js +28 -24
  66. package/dist/auth/index.js.map +1 -1
  67. package/dist/core/index.d.ts +116 -61
  68. package/dist/core/index.d.ts.map +1 -1
  69. package/dist/core/index.js +873 -701
  70. package/dist/core/index.js.map +1 -1
  71. package/dist/demo/{AuthLayout-DN-ClJQk.js → AuthLayout-Brri4A-L.js} +2 -2
  72. package/dist/demo/{AuthLayout-DN-ClJQk.js.map → AuthLayout-Brri4A-L.js.map} +1 -1
  73. package/dist/demo/DemoButton-wiCxZZ_L.js +182 -0
  74. package/dist/demo/DemoButton-wiCxZZ_L.js.map +1 -0
  75. package/dist/demo/DemoControlSelect-D7ILObVg.js +305 -0
  76. package/dist/demo/DemoControlSelect-D7ILObVg.js.map +1 -0
  77. package/dist/demo/DemoDataTable-DZ5Y8pFX.js +362 -0
  78. package/dist/demo/DemoDataTable-DZ5Y8pFX.js.map +1 -0
  79. package/dist/demo/{DemoDialog-DW8QEvD1.js → DemoDialog-CUWdLHim.js} +2 -2
  80. package/dist/demo/{DemoDialog-DW8QEvD1.js.map → DemoDialog-CUWdLHim.js.map} +1 -1
  81. package/dist/demo/{DemoFlex-CAhLUanT.js → DemoFlex-a8OhMMvq.js} +3 -3
  82. package/dist/demo/{DemoFlex-CAhLUanT.js.map → DemoFlex-a8OhMMvq.js.map} +1 -1
  83. package/dist/demo/{DemoHeading-yIFmNjHB.js → DemoHeading-C13OVDfS.js} +3 -3
  84. package/dist/demo/{DemoHeading-yIFmNjHB.js.map → DemoHeading-C13OVDfS.js.map} +1 -1
  85. package/dist/demo/{DemoHome-BSGuBHus.js → DemoHome-D_De3UiT.js} +2 -2
  86. package/dist/demo/{DemoHome-BSGuBHus.js.map → DemoHome-D_De3UiT.js.map} +1 -1
  87. package/dist/demo/{DemoJsonViewer-DsA2IpgV.js → DemoJsonViewer-B50s9aGM.js} +3 -3
  88. package/dist/demo/{DemoJsonViewer-DsA2IpgV.js.map → DemoJsonViewer-B50s9aGM.js.map} +1 -1
  89. package/dist/demo/{DemoLayout-Cy6xjn6P.js → DemoLayout-CHU8WTwO.js} +14 -5
  90. package/dist/demo/DemoLayout-CHU8WTwO.js.map +1 -0
  91. package/dist/demo/{DemoLogin-vqxgTu4P.js → DemoLogin-BBlrWpml.js} +49 -32
  92. package/dist/demo/DemoLogin-BBlrWpml.js.map +1 -0
  93. package/dist/demo/{DemoRegister-YHPvPg77.js → DemoRegister-BuNE3_-f.js} +49 -50
  94. package/dist/demo/DemoRegister-BuNE3_-f.js.map +1 -0
  95. package/dist/demo/{DemoResetPassword-mOW18Zlm.js → DemoResetPassword-D_IjjjOJ.js} +12 -16
  96. package/dist/demo/DemoResetPassword-D_IjjjOJ.js.map +1 -0
  97. package/dist/demo/{DemoSidebar-od7aLjP_.js → DemoSidebar-Giy2HRBD.js} +3 -3
  98. package/dist/demo/{DemoSidebar-od7aLjP_.js.map → DemoSidebar-Giy2HRBD.js.map} +1 -1
  99. package/dist/demo/{DemoText-DU3JeRS0.js → DemoText-ubcw-vog.js} +3 -3
  100. package/dist/demo/{DemoText-DU3JeRS0.js.map → DemoText-ubcw-vog.js.map} +1 -1
  101. package/dist/demo/{DemoToast-CUJEiPRa.js → DemoToast-9die_dYT.js} +2 -2
  102. package/dist/demo/{DemoToast-CUJEiPRa.js.map → DemoToast-9die_dYT.js.map} +1 -1
  103. package/dist/demo/{DemoTypeForm-C1dNkahD.js → DemoTypeForm-D_d6OVKL.js} +8 -4
  104. package/dist/demo/DemoTypeForm-D_d6OVKL.js.map +1 -0
  105. package/dist/demo/DemoVerifyEmail-B43KlF4F.js +34 -0
  106. package/dist/demo/DemoVerifyEmail-B43KlF4F.js.map +1 -0
  107. package/dist/demo/Login-C12N4oGs.js +275 -0
  108. package/dist/demo/Login-C12N4oGs.js.map +1 -0
  109. package/dist/demo/{Profile-BE_Y3co2.js → Profile-DS5q4vOh.js} +31 -27
  110. package/dist/demo/Profile-DS5q4vOh.js.map +1 -0
  111. package/dist/demo/{Register-fXHmBpr3.js → Register-B4hLBeEv.js} +198 -142
  112. package/dist/demo/Register-B4hLBeEv.js.map +1 -0
  113. package/dist/{auth/ResetPassword-DBxt9hKk.js → demo/ResetPassword-D8g9ha1N.js} +7 -7
  114. package/dist/demo/ResetPassword-D8g9ha1N.js.map +1 -0
  115. package/dist/demo/{Showcase-BtEU0pY9.js → Showcase-D6Fxt4X4.js} +64 -65
  116. package/dist/demo/Showcase-D6Fxt4X4.js.map +1 -0
  117. package/dist/{auth/VerifyEmail-Z80Ubajk.js → demo/VerifyEmail-BjDo0cZA.js} +23 -8
  118. package/dist/demo/VerifyEmail-BjDo0cZA.js.map +1 -0
  119. package/dist/demo/{auth-Djd7SKiw.js → auth-ByVTreDl.js} +8 -8
  120. package/dist/demo/{auth-Djd7SKiw.js.map → auth-ByVTreDl.js.map} +1 -1
  121. package/dist/demo/{core-B7LNjM78.js → core-DFgB3yU4.js} +741 -573
  122. package/dist/demo/core-DFgB3yU4.js.map +1 -0
  123. package/dist/demo/index.d.ts +1 -0
  124. package/dist/demo/index.d.ts.map +1 -1
  125. package/dist/demo/index.js +24 -18
  126. package/dist/demo/index.js.map +1 -1
  127. package/package.json +7 -7
  128. package/src/admin/AdminRouter.tsx +24 -1
  129. package/src/admin/components/notifications/AdminNotifications.tsx +519 -0
  130. package/src/admin/components/parameters/ParameterDetails.tsx +12 -270
  131. package/src/admin/components/parameters/ParameterDetailsConfigForm.tsx +238 -0
  132. package/src/admin/components/parameters/ParameterDetailsLoading.tsx +24 -0
  133. package/src/admin/components/parameters/ParameterHistory.tsx +10 -11
  134. package/src/admin/components/parameters/ParameterTree.tsx +28 -184
  135. package/src/admin/components/parameters/ParameterTreeNode.tsx +151 -0
  136. package/src/admin/components/shared/AdminResourceHeader.tsx +2 -25
  137. package/src/admin/components/shared/AdminResourceHeaderMenuItem.tsx +37 -0
  138. package/src/admin/components/shared/AdminResourceTabs.tsx +2 -26
  139. package/src/admin/components/shared/AdminResourceTabsItem.tsx +36 -0
  140. package/src/auth/components/Login.tsx +188 -121
  141. package/src/auth/components/Profile.tsx +1 -22
  142. package/src/auth/components/ProfileField.tsx +39 -0
  143. package/src/auth/components/Register.tsx +215 -158
  144. package/src/auth/components/ResetPassword.tsx +7 -11
  145. package/src/auth/components/VerifyEmail.tsx +35 -10
  146. package/src/auth/components/buttons/UserButton.tsx +19 -21
  147. package/src/auth/index.ts +1 -0
  148. package/src/core/components/Flex.tsx +10 -0
  149. package/src/core/components/buttons/ActionButton.tsx +104 -78
  150. package/src/core/components/data/DetailDrawer.tsx +102 -96
  151. package/src/core/components/data/DetailList.tsx +2 -1
  152. package/src/core/components/layout/Breadcrumb.tsx +3 -6
  153. package/src/core/components/layout/DashboardShell.tsx +18 -4
  154. package/src/core/components/layout/Sidebar.tsx +16 -241
  155. package/src/core/components/layout/SidebarCollapsedItem.tsx +91 -0
  156. package/src/core/components/layout/SidebarItem.tsx +146 -0
  157. package/src/core/components/layout/index.ts +3 -1
  158. package/src/core/form/components/Control.tsx +31 -29
  159. package/src/core/form/components/ControlArray.tsx +13 -39
  160. package/src/core/form/components/ControlDate.tsx +10 -21
  161. package/src/core/form/components/ControlNumber.tsx +4 -33
  162. package/src/core/form/components/ControlQueryBuilder.tsx +12 -175
  163. package/src/core/form/components/ControlQueryBuilderHelp.tsx +165 -0
  164. package/src/core/form/components/ControlSelect.browser.spec.tsx +343 -0
  165. package/src/core/form/components/ControlSelect.tsx +294 -92
  166. package/src/core/form/components/TypeForm.browser.spec.tsx +3 -3
  167. package/src/core/form/components/TypeForm.tsx +5 -2
  168. package/src/core/form/index.ts +8 -1
  169. package/src/core/form/utils/parseInput.ts +7 -3
  170. package/src/core/index.ts +3 -1
  171. package/src/core/json/components/JsonViewer.tsx +103 -319
  172. package/src/core/json/components/JsonViewerCopyButton.tsx +46 -0
  173. package/src/core/json/components/JsonViewerRowNode.tsx +120 -0
  174. package/src/core/json/components/JsonViewerShared.ts +76 -0
  175. package/src/core/styles.css +12 -2
  176. package/src/core/table/components/ColumnPicker.tsx +3 -3
  177. package/src/core/table/components/DataTable.tsx +89 -29
  178. package/src/core/table/components/DataTableFilters.tsx +6 -11
  179. package/src/core/table/components/DataTablePagination.tsx +9 -3
  180. package/src/core/table/components/DataTableToolbar.tsx +7 -3
  181. package/src/core/table/components/FilterPicker.tsx +3 -3
  182. package/src/core/table/interfaces/types.ts +29 -0
  183. package/src/core/utils/icons.tsx +2 -2
  184. package/src/demo/DemoRouter.ts +8 -1
  185. package/src/demo/components/DemoLayout.tsx +12 -2
  186. package/src/demo/components/auth/DemoLogin.tsx +35 -28
  187. package/src/demo/components/auth/DemoRegister.tsx +35 -49
  188. package/src/demo/components/auth/DemoResetPassword.tsx +5 -9
  189. package/src/demo/components/auth/DemoVerifyEmail.tsx +7 -6
  190. package/src/demo/components/core/DemoButton.tsx +123 -103
  191. package/src/demo/components/core/DemoControlSelect.tsx +325 -0
  192. package/src/demo/components/core/DemoDataTable.tsx +255 -237
  193. package/src/demo/components/core/DemoTypeForm.tsx +7 -2
  194. package/src/demo/components/shared/MacWindow.tsx +5 -11
  195. package/src/demo/components/shared/Showcase.tsx +28 -42
  196. package/dist/admin/AdminParameters-BspPeqp_.js.map +0 -1
  197. package/dist/admin/AdminUserLayout-DUbC6-BI.js.map +0 -1
  198. package/dist/admin/Login-DHbYJKwg.js +0 -219
  199. package/dist/admin/Login-DHbYJKwg.js.map +0 -1
  200. package/dist/admin/Profile-B2EcIDB9.js.map +0 -1
  201. package/dist/admin/Register-Z3fxRbUF.js.map +0 -1
  202. package/dist/admin/ResetPassword-_Y1qTTKh.js.map +0 -1
  203. package/dist/admin/VerifyEmail-Bg22bwcC.js.map +0 -1
  204. package/dist/admin/core-BVO_TQxb.js.map +0 -1
  205. package/dist/auth/Login-C7jIqf00.js +0 -219
  206. package/dist/auth/Login-C7jIqf00.js.map +0 -1
  207. package/dist/auth/Profile-BMpXJ0oi.js.map +0 -1
  208. package/dist/auth/Register-2gx8qll-.js.map +0 -1
  209. package/dist/auth/ResetPassword-DBxt9hKk.js.map +0 -1
  210. package/dist/auth/VerifyEmail-Z80Ubajk.js.map +0 -1
  211. package/dist/auth/core-DyfeVr5c.js.map +0 -1
  212. package/dist/demo/DemoButton-CGUyR9eM.js +0 -178
  213. package/dist/demo/DemoButton-CGUyR9eM.js.map +0 -1
  214. package/dist/demo/DemoDataTable-QFG-xXSx.js +0 -358
  215. package/dist/demo/DemoDataTable-QFG-xXSx.js.map +0 -1
  216. package/dist/demo/DemoLayout-Cy6xjn6P.js.map +0 -1
  217. package/dist/demo/DemoLogin-vqxgTu4P.js.map +0 -1
  218. package/dist/demo/DemoRegister-YHPvPg77.js.map +0 -1
  219. package/dist/demo/DemoResetPassword-mOW18Zlm.js.map +0 -1
  220. package/dist/demo/DemoTypeForm-C1dNkahD.js.map +0 -1
  221. package/dist/demo/DemoVerifyEmail-D9EcXZ38.js +0 -30
  222. package/dist/demo/DemoVerifyEmail-D9EcXZ38.js.map +0 -1
  223. package/dist/demo/Login-CoYf_P_F.js +0 -219
  224. package/dist/demo/Login-CoYf_P_F.js.map +0 -1
  225. package/dist/demo/Profile-BE_Y3co2.js.map +0 -1
  226. package/dist/demo/Register-fXHmBpr3.js.map +0 -1
  227. package/dist/demo/ResetPassword-CAPj8MO3.js.map +0 -1
  228. package/dist/demo/Showcase-BtEU0pY9.js.map +0 -1
  229. package/dist/demo/VerifyEmail-DFmdCdYs.js.map +0 -1
  230. package/dist/demo/core-B7LNjM78.js.map +0 -1
  231. package/src/demo/styles.css +0 -0
@@ -19,7 +19,7 @@ import type {
19
19
  DateTimePickerProps,
20
20
  TimeInputProps,
21
21
  } from "@mantine/dates";
22
- import { useFormState } from "alepha/react/form";
22
+ import { useFieldValue, useFormState } from "alepha/react/form";
23
23
  import type { ComponentType } from "react";
24
24
  import { type GenericControlProps, parseInput } from "../utils/parseInput.ts";
25
25
  import ControlArray, { type ControlArrayProps } from "./ControlArray.tsx";
@@ -76,6 +76,7 @@ export interface ControlProps extends GenericControlProps {
76
76
  */
77
77
  const Control = (_props: ControlProps) => {
78
78
  const form = useFormState(_props.input, ["error"]);
79
+ const [value, setValue] = useFieldValue(_props.input);
79
80
 
80
81
  // Early return if input is not properly initialized
81
82
  if (!_props.input?.props) {
@@ -93,12 +94,11 @@ const Control = (_props: ControlProps) => {
93
94
  if (props.query) {
94
95
  return (
95
96
  <ControlQueryBuilder
96
- {...props.input.props}
97
97
  {...inputProps}
98
98
  schema={props.query}
99
- value={props.input.props.value}
100
- onChange={(value) => {
101
- props.input.set(value);
99
+ value={value}
100
+ onChange={(val) => {
101
+ setValue(val);
102
102
  }}
103
103
  />
104
104
  );
@@ -112,9 +112,9 @@ const Control = (_props: ControlProps) => {
112
112
  <Input.Wrapper {...inputProps}>
113
113
  <Flex flex={1} mt={"calc(var(--mantine-spacing-xs) / 2)"}>
114
114
  <Custom
115
- defaultValue={props.input.props.defaultValue}
116
- onChange={(value) => {
117
- props.input.set(value);
115
+ value={value}
116
+ onChange={(val) => {
117
+ setValue(val);
118
118
  }}
119
119
  />
120
120
  </Flex>
@@ -137,7 +137,7 @@ const Control = (_props: ControlProps) => {
137
137
  return (
138
138
  <ControlObject
139
139
  input={props.input}
140
- title={props.title}
140
+ label={props.label}
141
141
  description={props.description}
142
142
  {...controlObjectProps}
143
143
  />
@@ -165,7 +165,7 @@ const Control = (_props: ControlProps) => {
165
165
  return (
166
166
  <ControlArray
167
167
  input={props.input}
168
- title={props.title}
168
+ label={props.label}
169
169
  description={props.description}
170
170
  {...controlArrayProps}
171
171
  />
@@ -176,7 +176,8 @@ const Control = (_props: ControlProps) => {
176
176
  //region <NumberInput/>
177
177
  if (
178
178
  props.number ||
179
- (props.input.schema &&
179
+ (!props.select &&
180
+ props.input.schema &&
180
181
  "type" in props.input.schema &&
181
182
  (props.input.schema.type === "number" ||
182
183
  props.input.schema.type === "integer"))
@@ -190,7 +191,7 @@ const Control = (_props: ControlProps) => {
190
191
  <ControlNumber
191
192
  size={props.size}
192
193
  input={props.input}
193
- title={props.title}
194
+ label={props.label}
194
195
  description={props.description}
195
196
  icon={icon}
196
197
  {...controlNumberProps}
@@ -208,9 +209,7 @@ const Control = (_props: ControlProps) => {
208
209
  size={props.size}
209
210
  id={id}
210
211
  leftSection={icon}
211
- onChange={(file) => {
212
- props.input.set(file);
213
- }}
212
+ onChange={(file) => setValue(file)}
214
213
  {...fileInputProps}
215
214
  />
216
215
  );
@@ -226,7 +225,8 @@ const Control = (_props: ControlProps) => {
226
225
  size={props.size}
227
226
  id={id}
228
227
  leftSection={icon}
229
- {...props.input.props}
228
+ value={value ?? ""}
229
+ onChange={(val) => setValue(val)}
230
230
  {...colorInputProps}
231
231
  />
232
232
  );
@@ -244,13 +244,13 @@ const Control = (_props: ControlProps) => {
244
244
  if (isEnum || (isArray && !isArrayOfObjects) || props.select) {
245
245
  const opts = typeof props.select === "object" ? props.select : {};
246
246
  if (props.segmented) {
247
- opts.segmented ??= {};
247
+ opts.segmentedProps ??= {};
248
248
  }
249
249
  return (
250
250
  <ControlSelect
251
251
  size={props.size}
252
252
  input={props.input}
253
- title={props.title}
253
+ label={props.label}
254
254
  description={props.description}
255
255
  icon={icon}
256
256
  {...opts}
@@ -273,9 +273,9 @@ const Control = (_props: ControlProps) => {
273
273
  size={props.size}
274
274
  id={id}
275
275
  color={"blue"}
276
- defaultChecked={props.input.props.defaultValue}
276
+ checked={Boolean(value)}
277
277
  onChange={(event) => {
278
- props.input.set(event.currentTarget.checked);
278
+ setValue(event.currentTarget.checked);
279
279
  }}
280
280
  {...switchProps}
281
281
  />
@@ -284,7 +284,7 @@ const Control = (_props: ControlProps) => {
284
284
 
285
285
  const opts: ControlSelectProps = {
286
286
  input: props.input,
287
- select: {
287
+ selectProps: {
288
288
  data: [
289
289
  { value: "true", label: "Yes" },
290
290
  { value: "false", label: "No" },
@@ -295,7 +295,7 @@ const Control = (_props: ControlProps) => {
295
295
  return (
296
296
  <ControlSelect
297
297
  size={props.size}
298
- title={props.title}
298
+ label={props.label}
299
299
  description={props.description}
300
300
  icon={icon}
301
301
  {...opts}
@@ -314,7 +314,8 @@ const Control = (_props: ControlProps) => {
314
314
  size={props.size}
315
315
  id={id}
316
316
  leftSection={icon}
317
- {...props.input.props}
317
+ value={value ?? ""}
318
+ onChange={(ev) => setValue(ev.target.value)}
318
319
  {...passwordInputProps}
319
320
  />
320
321
  );
@@ -330,7 +331,8 @@ const Control = (_props: ControlProps) => {
330
331
  size={props.size}
331
332
  id={id}
332
333
  leftSection={icon}
333
- {...props.input.props}
334
+ value={value ?? ""}
335
+ onChange={(ev) => setValue(ev.target.value)}
334
336
  {...textAreaProps}
335
337
  />
336
338
  );
@@ -351,7 +353,7 @@ const Control = (_props: ControlProps) => {
351
353
  <ControlDate
352
354
  size={props.size}
353
355
  input={props.input}
354
- title={props.title}
356
+ label={props.label}
355
357
  description={props.description}
356
358
  icon={icon}
357
359
  date={props.date}
@@ -377,7 +379,7 @@ const Control = (_props: ControlProps) => {
377
379
  case "phone":
378
380
  return "tel";
379
381
  default:
380
- return undefined;
382
+ return props.input.props.type ?? "text";
381
383
  }
382
384
  };
383
385
 
@@ -388,9 +390,9 @@ const Control = (_props: ControlProps) => {
388
390
  id={id}
389
391
  leftSection={icon}
390
392
  type={getInputType()}
391
- {...props.input.props}
393
+ value={value ?? ""}
394
+ onChange={(ev) => setValue(ev.target.value)}
392
395
  {...textInputProps}
393
- inputWrapperOrder={["label", "input", "description", "error"]}
394
396
  />
395
397
  );
396
398
  //endregion
@@ -399,6 +401,6 @@ const Control = (_props: ControlProps) => {
399
401
  export default Control;
400
402
 
401
403
  export type CustomControlProps = {
402
- defaultValue: any;
404
+ value: any;
403
405
  onChange: (value: any) => void;
404
406
  };
@@ -88,11 +88,11 @@ const useArrayItems = (
88
88
  const alepha = useAlepha();
89
89
  const keyCounter = useRef(0);
90
90
 
91
- // Initialize from defaultValue
91
+ // Initialize from initialValue
92
92
  const [items, setItemsState] = useState<ArrayItem[]>(() => {
93
- const defaultValue = input?.props?.defaultValue;
94
- if (Array.isArray(defaultValue)) {
95
- return defaultValue.map((value) => ({
93
+ const initial = input?.initialValue;
94
+ if (Array.isArray(initial)) {
95
+ return initial.map((value) => ({
96
96
  key: keyCounter.current++,
97
97
  value,
98
98
  }));
@@ -126,46 +126,20 @@ const useArrayItems = (
126
126
  });
127
127
  }, []);
128
128
 
129
- // Listen for form changes and reset events
129
+ // Listen for form changes
130
130
  useEffect(() => {
131
131
  if (!input?.form) return;
132
132
 
133
133
  const formId = input.form.id;
134
134
  const fieldPath = input.path;
135
135
 
136
- const listeners = [
137
- // Handle form reset
138
- alepha.events.on("form:reset", (event) => {
139
- if (event.id === formId) {
140
- const defaultValue = input.props?.defaultValue;
141
- keyCounter.current = 0;
142
- if (Array.isArray(defaultValue)) {
143
- setItemsState(
144
- defaultValue.map((value) => ({
145
- key: keyCounter.current++,
146
- value,
147
- })),
148
- );
149
- } else {
150
- setItemsState([]);
151
- }
152
- }
153
- }),
154
-
155
- // Handle external value changes (e.g., programmatic updates)
156
- alepha.events.on("form:change", (event) => {
157
- if (event.id === formId && event.path === fieldPath) {
158
- // Value was changed externally, sync our state
159
- syncFromFormValue(event.value);
160
- }
161
- }),
162
- ];
163
-
164
- return () => {
165
- for (const unsub of listeners) {
166
- unsub();
136
+ const unsub = alepha.events.on("form:change", (event) => {
137
+ if (event.id === formId && event.path === fieldPath) {
138
+ syncFromFormValue(event.value);
167
139
  }
168
- };
140
+ });
141
+
142
+ return unsub;
169
143
  }, [alepha, input, syncFromFormValue]);
170
144
 
171
145
  // Update form when items change
@@ -200,10 +174,10 @@ const createArrayItemInput = (
200
174
  path: `${parentInput.path}/${index}`,
201
175
  required: false,
202
176
  form: parentInput.form,
177
+ initialValue: value,
203
178
  props: {
204
179
  id: `${parentInput.props.id}-${index}`,
205
180
  name: `${parentInput.props.name}[${index}]`,
206
- defaultValue: value,
207
181
  },
208
182
  set: onValueChange,
209
183
  };
@@ -228,10 +202,10 @@ const createArrayItemFieldInput = (
228
202
  path: `${parentInput.path}/${index}/${fieldName}`,
229
203
  required: itemSchema.required?.includes(fieldName) ?? false,
230
204
  form: parentInput.form,
205
+ initialValue: itemValue?.[fieldName],
231
206
  props: {
232
207
  id: `${parentInput.props.id}-${index}-${fieldName}`,
233
208
  name: `${parentInput.props.name}[${index}].${fieldName}`,
234
- defaultValue: itemValue?.[fieldName],
235
209
  },
236
210
  set: (value: any) => onFieldChange(fieldName, value),
237
211
  };
@@ -6,7 +6,7 @@ import {
6
6
  TimeInput,
7
7
  type TimeInputProps,
8
8
  } from "@mantine/dates";
9
- import { useFormState } from "alepha/react/form";
9
+ import { useFieldValue, useFormState } from "alepha/react/form";
10
10
  import { type GenericControlProps, parseInput } from "../utils/parseInput.ts";
11
11
 
12
12
  export interface ControlDateProps extends GenericControlProps {
@@ -27,6 +27,7 @@ export interface ControlDateProps extends GenericControlProps {
27
27
  */
28
28
  const ControlDate = (props: ControlDateProps) => {
29
29
  const form = useFormState(props.input);
30
+ const [value, setValue] = useFieldValue(props.input);
30
31
  const { inputProps, id, icon, format } = parseInput(props, form);
31
32
  if (!props.input?.props) {
32
33
  return null;
@@ -41,14 +42,10 @@ const ControlDate = (props: ControlDateProps) => {
41
42
  {...inputProps}
42
43
  id={id}
43
44
  leftSection={icon}
44
- defaultValue={
45
- props.input.props.defaultValue
46
- ? new Date(props.input.props.defaultValue)
47
- : undefined
45
+ value={value ? new Date(value) : null}
46
+ onChange={(val) =>
47
+ setValue(val ? new Date(val).toISOString() : undefined)
48
48
  }
49
- onChange={(value) => {
50
- props.input.set(value ? new Date(value).toISOString() : undefined);
51
- }}
52
49
  {...dateTimePickerProps}
53
50
  />
54
51
  );
@@ -63,16 +60,10 @@ const ControlDate = (props: ControlDateProps) => {
63
60
  {...inputProps}
64
61
  id={id}
65
62
  leftSection={icon}
66
- defaultValue={
67
- props.input.props.defaultValue
68
- ? new Date(props.input.props.defaultValue)
69
- : undefined
63
+ value={value ? new Date(value) : null}
64
+ onChange={(val) =>
65
+ setValue(val ? new Date(val).toISOString().slice(0, 10) : undefined)
70
66
  }
71
- onChange={(value) => {
72
- props.input.set(
73
- value ? new Date(value).toISOString().slice(0, 10) : undefined,
74
- );
75
- }}
76
67
  {...dateInputProps}
77
68
  />
78
69
  );
@@ -87,10 +78,8 @@ const ControlDate = (props: ControlDateProps) => {
87
78
  {...inputProps}
88
79
  id={id}
89
80
  leftSection={icon}
90
- defaultValue={props.input.props.defaultValue}
91
- onChange={(event) => {
92
- props.input.set(event.currentTarget.value);
93
- }}
81
+ value={value ?? ""}
82
+ onChange={(event) => setValue(event.currentTarget.value)}
94
83
  {...timeInputProps}
95
84
  />
96
85
  );
@@ -5,9 +5,7 @@ import {
5
5
  Slider,
6
6
  type SliderProps,
7
7
  } from "@mantine/core";
8
- import { useEvents } from "alepha/react";
9
- import { useFormState } from "alepha/react/form";
10
- import { useRef, useState } from "react";
8
+ import { useFieldValue, useFormState } from "alepha/react/form";
11
9
  import { type GenericControlProps, parseInput } from "../utils/parseInput.ts";
12
10
 
13
11
  export interface ControlNumberProps extends GenericControlProps {
@@ -20,32 +18,13 @@ export interface ControlNumberProps extends GenericControlProps {
20
18
  */
21
19
  const ControlNumber = (props: ControlNumberProps) => {
22
20
  const form = useFormState(props.input);
21
+ const [value, setValue] = useFieldValue(props.input);
23
22
  const { inputProps, id, icon } = parseInput(props, form);
24
- const ref = useRef<HTMLInputElement | null>(null);
25
-
26
- // HTML Reset doesn't trigger on <NumberInput /> so we handle it manually
27
-
28
- const [value, setValue] = useState<number | undefined>(
29
- props.input.props.defaultValue,
30
- );
31
-
32
- useEvents(
33
- {
34
- "form:reset": (event) => {
35
- if (event.id === props.input?.form.id && ref.current) {
36
- setValue(props.input.props.defaultValue);
37
- }
38
- },
39
- },
40
- [props.input],
41
- );
42
23
 
43
24
  if (!props.input?.props) {
44
25
  return null;
45
26
  }
46
27
 
47
- const { type, ...inputPropsWithoutType } = props.input.props;
48
-
49
28
  if (props.sliderProps) {
50
29
  const min = props.sliderProps.min ?? inputProps.minimum ?? 0;
51
30
  const max = props.sliderProps.max ?? inputProps.maximum ?? 100;
@@ -59,18 +38,13 @@ const ControlNumber = (props: ControlNumberProps) => {
59
38
  >
60
39
  <Slider
61
40
  {...inputProps}
62
- ref={ref}
63
41
  id={id}
64
- {...inputPropsWithoutType}
65
42
  {...props.sliderProps}
66
- value={value}
43
+ value={value ?? 0}
67
44
  min={min}
68
45
  max={max}
69
46
  label={() => value}
70
- onChange={(val) => {
71
- setValue(val);
72
- props.input.set(val);
73
- }}
47
+ onChange={(val) => setValue(val)}
74
48
  />
75
49
  </div>
76
50
  </Input.Wrapper>
@@ -80,16 +54,13 @@ const ControlNumber = (props: ControlNumberProps) => {
80
54
  return (
81
55
  <NumberInput
82
56
  {...inputProps}
83
- ref={ref}
84
57
  id={id}
85
58
  leftSection={icon}
86
- {...inputPropsWithoutType}
87
59
  {...props.numberInputProps}
88
60
  value={value ?? ""}
89
61
  onChange={(val) => {
90
62
  const newValue = val !== null ? Number(val) : undefined;
91
63
  setValue(newValue);
92
- props.input.set(newValue);
93
64
  }}
94
65
  />
95
66
  );
@@ -1,17 +1,7 @@
1
- import {
2
- ActionButton,
3
- extractSchemaFields,
4
- OPERATOR_INFO,
5
- type SchemaField,
6
- ui,
7
- } from "@alepha/ui";
1
+ import { extractSchemaFields, ui } from "@alepha/ui";
8
2
  import {
9
3
  ActionIcon,
10
- Badge,
11
- Divider,
12
- Flex,
13
4
  Popover,
14
- Text,
15
5
  TextInput,
16
6
  type TextInputProps,
17
7
  } from "@mantine/core";
@@ -20,6 +10,7 @@ import type { TObject } from "alepha";
20
10
  import { parseQueryString } from "alepha/orm";
21
11
  import { useEvents } from "alepha/react";
22
12
  import { useRef, useState } from "react";
13
+ import ControlQueryBuilderHelp from "./ControlQueryBuilderHelp.tsx";
23
14
 
24
15
  export interface ControlQueryBuilderProps
25
16
  extends Omit<TextInputProps, "value" | "onChange"> {
@@ -33,13 +24,15 @@ export interface ControlQueryBuilderProps
33
24
  * Query builder with text input and help popover.
34
25
  * Generates query strings for parseQueryString syntax.
35
26
  */
36
- const ControlQueryBuilder = ({
37
- schema,
38
- value = "",
39
- onChange,
40
- placeholder = "Enter query or click for assistance...",
41
- ...textInputProps
42
- }: ControlQueryBuilderProps) => {
27
+ const ControlQueryBuilder = (props: ControlQueryBuilderProps) => {
28
+ const {
29
+ schema,
30
+ value = "",
31
+ onChange,
32
+ placeholder = "Enter query or click for assistance...",
33
+ ...textInputProps
34
+ } = props;
35
+
43
36
  const [helpOpened, setHelpOpened] = useState(false);
44
37
  const [textValue, setTextValue] = useState(value);
45
38
  const inputRef = useRef<HTMLInputElement>(null);
@@ -146,166 +139,10 @@ const ControlQueryBuilder = ({
146
139
  backdropFilter: "blur(20px)",
147
140
  }}
148
141
  >
149
- <QueryHelp fields={fields} onInsert={handleInsert} />
142
+ <ControlQueryBuilderHelp fields={fields} onInsert={handleInsert} />
150
143
  </Popover.Dropdown>
151
144
  </Popover>
152
145
  );
153
146
  };
154
147
 
155
- // ---------------------------------------------------------------------------------------------------------------------
156
- // Query Help Component
157
- // ---------------------------------------------------------------------------------------------------------------------
158
-
159
- interface QueryHelpProps {
160
- fields: SchemaField[];
161
- onInsert: (text: string) => void;
162
- }
163
-
164
- function QueryHelp({ fields, onInsert }: QueryHelpProps) {
165
- return (
166
- <Flex
167
- gap="md"
168
- align="flex-start"
169
- wrap="nowrap"
170
- bg={ui.colors.surface}
171
- p={"sm"}
172
- bdrs={"sm"}
173
- >
174
- {/* Left Column: Operators */}
175
- <Flex direction="column" gap="md" style={{ flex: 1 }}>
176
- {/* Available Operators */}
177
- <Flex direction="column" gap="xs">
178
- <Text size="sm" fw={600}>
179
- Operators
180
- </Text>
181
- <Flex direction="column" gap={4}>
182
- {Object.entries(OPERATOR_INFO).map(([key, info]) => (
183
- <Flex key={key} gap="xs" wrap="nowrap">
184
- <ActionButton
185
- px={"xs"}
186
- size={"xs"}
187
- h={24}
188
- variant={"default"}
189
- justify={"center"}
190
- miw={48}
191
- onClick={() => onInsert(info.symbol)}
192
- >
193
- {info.symbol}
194
- </ActionButton>
195
- <Text size="xs" c="dimmed" style={{ flex: 1 }}>
196
- {info.label}
197
- </Text>
198
- </Flex>
199
- ))}
200
- </Flex>
201
- </Flex>
202
-
203
- <Divider />
204
-
205
- {/* Logic Operators */}
206
- <Flex direction="column" gap="xs">
207
- <Text size="sm" fw={600}>
208
- Logic
209
- </Text>
210
- <Flex direction="column" gap={4}>
211
- <Flex gap="xs" wrap="nowrap">
212
- <ActionButton
213
- px={"xs"}
214
- size={"xs"}
215
- h={24}
216
- variant={"default"}
217
- justify={"center"}
218
- miw={48}
219
- onClick={() => onInsert("&")}
220
- >
221
- &
222
- </ActionButton>
223
- <Text size="xs" c="dimmed">
224
- AND
225
- </Text>
226
- </Flex>
227
- <Flex gap="xs" wrap="nowrap">
228
- <ActionButton
229
- px={"xs"}
230
- size={"xs"}
231
- h={24}
232
- variant={"default"}
233
- justify={"center"}
234
- miw={48}
235
- onClick={() => onInsert("|")}
236
- >
237
- |
238
- </ActionButton>
239
- <Text size="xs" c="dimmed">
240
- OR
241
- </Text>
242
- </Flex>
243
- </Flex>
244
- </Flex>
245
- </Flex>
246
-
247
- {/* Divider */}
248
- {fields.length > 0 && <Divider orientation="vertical" />}
249
-
250
- {/* Right Column: Fields */}
251
- {fields.length > 0 && (
252
- <Flex direction={"column"} gap="xs" style={{ flex: 2 }}>
253
- <Text size="sm" fw={600}>
254
- Fields
255
- </Text>
256
- <Flex
257
- direction={"column"}
258
- gap={4}
259
- style={{ maxHeight: 300, overflowY: "auto" }}
260
- >
261
- {fields.map((field) => (
262
- <Flex key={field.path} gap="xs" wrap="nowrap" align="flex-start">
263
- <ActionButton
264
- px={"xs"}
265
- size={"xs"}
266
- h={24}
267
- variant={"default"}
268
- justify={"end"}
269
- miw={120}
270
- onClick={() => onInsert(field.path)}
271
- >
272
- {field.path}
273
- </ActionButton>
274
- <Flex
275
- mt={3}
276
- direction={"column"}
277
- gap={2}
278
- style={{ flex: 1, minWidth: 0 }}
279
- >
280
- <Text size="xs" c="dimmed" lineClamp={1}>
281
- {field.description || field.type}
282
- </Text>
283
- {field.enum && (
284
- <Flex gap={0} wrap="wrap">
285
- {field.enum.map((enumValue) => (
286
- <ActionButton
287
- px={"xs"}
288
- size={"xs"}
289
- h={24}
290
- key={enumValue}
291
- onClick={() => onInsert(enumValue)}
292
- >
293
- {enumValue}
294
- </ActionButton>
295
- ))}
296
- </Flex>
297
- )}
298
- </Flex>
299
- <Badge size="xs" variant="light" style={{ flexShrink: 0 }}>
300
- {field.type}
301
- </Badge>
302
- </Flex>
303
- ))}
304
- </Flex>
305
- </Flex>
306
- )}
307
- </Flex>
308
- );
309
- }
310
-
311
148
  export default ControlQueryBuilder;