@dxos/react-ui-form 0.8.4-main.fd6878d → 0.8.4-staging.60fe92afc8

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 (318) hide show
  1. package/LICENSE +102 -5
  2. package/README.md +0 -1
  3. package/dist/lib/browser/index.mjs +4054 -2217
  4. package/dist/lib/browser/index.mjs.map +4 -4
  5. package/dist/lib/browser/meta.json +1 -1
  6. package/dist/lib/browser/translations.mjs +87 -0
  7. package/dist/lib/browser/translations.mjs.map +7 -0
  8. package/dist/lib/node-esm/index.mjs +4054 -2217
  9. package/dist/lib/node-esm/index.mjs.map +4 -4
  10. package/dist/lib/node-esm/meta.json +1 -1
  11. package/dist/lib/node-esm/translations.mjs +89 -0
  12. package/dist/lib/node-esm/translations.mjs.map +7 -0
  13. package/dist/types/src/components/FieldEditor/FieldEditor.d.ts +8 -8
  14. package/dist/types/src/components/FieldEditor/FieldEditor.d.ts.map +1 -1
  15. package/dist/types/src/components/FieldEditor/FieldEditor.stories.d.ts +89 -5
  16. package/dist/types/src/components/FieldEditor/FieldEditor.stories.d.ts.map +1 -1
  17. package/dist/types/src/components/Form/Form.d.ts +135 -25
  18. package/dist/types/src/components/Form/Form.d.ts.map +1 -1
  19. package/dist/types/src/components/Form/Form.stories.d.ts +207 -56
  20. package/dist/types/src/components/Form/Form.stories.d.ts.map +1 -1
  21. package/dist/types/src/components/Form/FormField.d.ts +52 -0
  22. package/dist/types/src/components/Form/FormField.d.ts.map +1 -0
  23. package/dist/types/src/components/Form/FormFieldComponent.d.ts +98 -0
  24. package/dist/types/src/components/Form/FormFieldComponent.d.ts.map +1 -0
  25. package/dist/types/src/components/Form/FormFieldComponent.stories.d.ts +9 -0
  26. package/dist/types/src/components/Form/FormFieldComponent.stories.d.ts.map +1 -0
  27. package/dist/types/src/components/Form/FormFieldSet.d.ts +26 -0
  28. package/dist/types/src/components/Form/FormFieldSet.d.ts.map +1 -0
  29. package/dist/types/src/components/Form/FormTooltipsContext.d.ts +19 -0
  30. package/dist/types/src/components/Form/FormTooltipsContext.d.ts.map +1 -0
  31. package/dist/types/src/components/Form/Layout/FormLayout.d.ts +50 -0
  32. package/dist/types/src/components/Form/Layout/FormLayout.d.ts.map +1 -0
  33. package/dist/types/src/components/Form/Layout/FormLayout.stories.d.ts +123 -0
  34. package/dist/types/src/components/Form/Layout/FormLayout.stories.d.ts.map +1 -0
  35. package/dist/types/src/components/Form/Layout/FormLayout.stories.test.d.ts +2 -0
  36. package/dist/types/src/components/Form/Layout/FormLayout.stories.test.d.ts.map +1 -0
  37. package/dist/types/src/components/Form/Layout/FormLayout.test.d.ts +2 -0
  38. package/dist/types/src/components/Form/Layout/FormLayout.test.d.ts.map +1 -0
  39. package/dist/types/src/components/Form/Layout/annotation.d.ts +30 -0
  40. package/dist/types/src/components/Form/Layout/annotation.d.ts.map +1 -0
  41. package/dist/types/src/components/Form/Layout/index.d.ts +4 -0
  42. package/dist/types/src/components/Form/Layout/index.d.ts.map +1 -0
  43. package/dist/types/src/components/Form/Layout/parser.d.ts +31 -0
  44. package/dist/types/src/components/Form/Layout/parser.d.ts.map +1 -0
  45. package/dist/types/src/components/Form/Layout/parser.test.d.ts +2 -0
  46. package/dist/types/src/components/Form/Layout/parser.test.d.ts.map +1 -0
  47. package/dist/types/src/components/Form/fields/ArrayField.d.ts +18 -0
  48. package/dist/types/src/components/Form/fields/ArrayField.d.ts.map +1 -0
  49. package/dist/types/src/components/Form/fields/BooleanField.d.ts +4 -0
  50. package/dist/types/src/components/Form/fields/BooleanField.d.ts.map +1 -0
  51. package/dist/types/src/components/Form/fields/DateField.d.ts +4 -0
  52. package/dist/types/src/components/Form/fields/DateField.d.ts.map +1 -0
  53. package/dist/types/src/components/Form/fields/GeoPointField.d.ts +5 -0
  54. package/dist/types/src/components/Form/fields/GeoPointField.d.ts.map +1 -0
  55. package/dist/types/src/components/Form/fields/InlineRefField.d.ts +13 -0
  56. package/dist/types/src/components/Form/fields/InlineRefField.d.ts.map +1 -0
  57. package/dist/types/src/components/Form/fields/MarkdownField.d.ts +11 -0
  58. package/dist/types/src/components/Form/fields/MarkdownField.d.ts.map +1 -0
  59. package/dist/types/src/components/Form/fields/MarkdownField.stories.d.ts +89 -0
  60. package/dist/types/src/components/Form/fields/MarkdownField.stories.d.ts.map +1 -0
  61. package/dist/types/src/components/Form/fields/NumberField.d.ts +4 -0
  62. package/dist/types/src/components/Form/fields/NumberField.d.ts.map +1 -0
  63. package/dist/types/src/components/Form/fields/RefField.d.ts +34 -0
  64. package/dist/types/src/components/Form/fields/RefField.d.ts.map +1 -0
  65. package/dist/types/src/components/Form/fields/RefField.test.d.ts +2 -0
  66. package/dist/types/src/components/Form/fields/RefField.test.d.ts.map +1 -0
  67. package/dist/types/src/components/Form/fields/SelectField.d.ts +13 -0
  68. package/dist/types/src/components/Form/fields/SelectField.d.ts.map +1 -0
  69. package/dist/types/src/components/Form/fields/SelectOptionField.d.ts +5 -0
  70. package/dist/types/src/components/Form/fields/SelectOptionField.d.ts.map +1 -0
  71. package/dist/types/src/components/Form/fields/SelectOptionField.stories.d.ts +89 -0
  72. package/dist/types/src/components/Form/fields/SelectOptionField.stories.d.ts.map +1 -0
  73. package/dist/types/src/components/Form/fields/TextAreaField.d.ts +4 -0
  74. package/dist/types/src/components/Form/fields/TextAreaField.d.ts.map +1 -0
  75. package/dist/types/src/components/Form/fields/TextField.d.ts +4 -0
  76. package/dist/types/src/components/Form/fields/TextField.d.ts.map +1 -0
  77. package/dist/types/src/components/Form/fields/TupleField.d.ts +6 -0
  78. package/dist/types/src/components/Form/fields/TupleField.d.ts.map +1 -0
  79. package/dist/types/src/components/Form/fields/index.d.ts +14 -0
  80. package/dist/types/src/components/Form/fields/index.d.ts.map +1 -0
  81. package/dist/types/src/components/Form/index.d.ts +5 -4
  82. package/dist/types/src/components/Form/index.d.ts.map +1 -1
  83. package/dist/types/src/components/Form/meta-tags.d.ts +30 -0
  84. package/dist/types/src/components/Form/meta-tags.d.ts.map +1 -0
  85. package/dist/types/src/components/Form/meta-tags.test.d.ts +2 -0
  86. package/dist/types/src/components/Form/meta-tags.test.d.ts.map +1 -0
  87. package/dist/types/src/components/ObjectForm/ObjectForm.d.ts +8 -0
  88. package/dist/types/src/components/ObjectForm/ObjectForm.d.ts.map +1 -0
  89. package/dist/types/src/components/ObjectForm/ObjectForm.stories.d.ts +87 -0
  90. package/dist/types/src/components/ObjectForm/ObjectForm.stories.d.ts.map +1 -0
  91. package/dist/types/src/components/ObjectForm/index.d.ts +2 -0
  92. package/dist/types/src/components/ObjectForm/index.d.ts.map +1 -0
  93. package/dist/types/src/components/ObjectPicker/ObjectPicker.d.ts +68 -0
  94. package/dist/types/src/components/ObjectPicker/ObjectPicker.d.ts.map +1 -0
  95. package/dist/types/src/components/ObjectPicker/ObjectPicker.stories.d.ts +92 -0
  96. package/dist/types/src/components/ObjectPicker/ObjectPicker.stories.d.ts.map +1 -0
  97. package/dist/types/src/components/ObjectPicker/index.d.ts +2 -0
  98. package/dist/types/src/components/ObjectPicker/index.d.ts.map +1 -0
  99. package/dist/types/src/components/ObjectProperties/ObjectProperties.d.ts +9 -0
  100. package/dist/types/src/components/ObjectProperties/ObjectProperties.d.ts.map +1 -0
  101. package/dist/types/src/components/ObjectProperties/ObjectProperties.stories.d.ts +132 -0
  102. package/dist/types/src/components/ObjectProperties/ObjectProperties.stories.d.ts.map +1 -0
  103. package/dist/types/src/components/ObjectProperties/ObjectProperties.test.d.ts +2 -0
  104. package/dist/types/src/components/ObjectProperties/ObjectProperties.test.d.ts.map +1 -0
  105. package/dist/types/src/components/ObjectProperties/index.d.ts +2 -0
  106. package/dist/types/src/components/ObjectProperties/index.d.ts.map +1 -0
  107. package/dist/types/src/components/ObjectTree/ObjectTree.d.ts +9 -0
  108. package/dist/types/src/components/ObjectTree/ObjectTree.d.ts.map +1 -0
  109. package/dist/types/src/components/ObjectTree/ObjectTree.stories.d.ts +91 -0
  110. package/dist/types/src/components/ObjectTree/ObjectTree.stories.d.ts.map +1 -0
  111. package/dist/types/src/components/ObjectTree/index.d.ts +2 -0
  112. package/dist/types/src/components/ObjectTree/index.d.ts.map +1 -0
  113. package/dist/types/src/components/RefEditor/RefEditor.d.ts +73 -0
  114. package/dist/types/src/components/RefEditor/RefEditor.d.ts.map +1 -0
  115. package/dist/types/src/components/RefEditor/RefEditor.stories.d.ts +92 -0
  116. package/dist/types/src/components/RefEditor/RefEditor.stories.d.ts.map +1 -0
  117. package/dist/types/src/components/RefEditor/index.d.ts +3 -0
  118. package/dist/types/src/components/RefEditor/index.d.ts.map +1 -0
  119. package/dist/types/src/components/RefEditor/ref-editor-extension.d.ts +47 -0
  120. package/dist/types/src/components/RefEditor/ref-editor-extension.d.ts.map +1 -0
  121. package/dist/types/src/components/Settings/Settings.d.ts +51 -0
  122. package/dist/types/src/components/Settings/Settings.d.ts.map +1 -0
  123. package/dist/types/src/components/Settings/Settings.stories.d.ts +89 -0
  124. package/dist/types/src/components/Settings/Settings.stories.d.ts.map +1 -0
  125. package/dist/types/src/components/Settings/SettingsFieldSet.d.ts +43 -0
  126. package/dist/types/src/components/Settings/SettingsFieldSet.d.ts.map +1 -0
  127. package/dist/types/src/components/Settings/SettingsItem.d.ts +16 -0
  128. package/dist/types/src/components/Settings/SettingsItem.d.ts.map +1 -0
  129. package/dist/types/src/components/Settings/SettingsSelectField.d.ts +18 -0
  130. package/dist/types/src/components/Settings/SettingsSelectField.d.ts.map +1 -0
  131. package/dist/types/src/components/Settings/index.d.ts +4 -0
  132. package/dist/types/src/components/Settings/index.d.ts.map +1 -0
  133. package/dist/types/src/components/ViewEditor/ViewEditor.d.ts +21 -11
  134. package/dist/types/src/components/ViewEditor/ViewEditor.d.ts.map +1 -1
  135. package/dist/types/src/components/ViewEditor/ViewEditor.stories.d.ts +91 -9
  136. package/dist/types/src/components/ViewEditor/ViewEditor.stories.d.ts.map +1 -1
  137. package/dist/types/src/components/index.d.ts +6 -2
  138. package/dist/types/src/components/index.d.ts.map +1 -1
  139. package/dist/types/src/components/testing.d.ts +14 -4
  140. package/dist/types/src/components/testing.d.ts.map +1 -1
  141. package/dist/types/src/hooks/index.d.ts +2 -3
  142. package/dist/types/src/hooks/index.d.ts.map +1 -1
  143. package/dist/types/src/hooks/useFormHandler.d.ts +82 -0
  144. package/dist/types/src/hooks/useFormHandler.d.ts.map +1 -0
  145. package/dist/types/src/hooks/useKeyHandler.d.ts +7 -0
  146. package/dist/types/src/hooks/useKeyHandler.d.ts.map +1 -0
  147. package/dist/types/src/index.d.ts +0 -2
  148. package/dist/types/src/index.d.ts.map +1 -1
  149. package/dist/types/src/translations.d.ts +70 -55
  150. package/dist/types/src/translations.d.ts.map +1 -1
  151. package/dist/types/src/util/field-type.d.ts +19 -0
  152. package/dist/types/src/util/field-type.d.ts.map +1 -0
  153. package/dist/types/src/util/field.d.ts +3 -3
  154. package/dist/types/src/util/field.d.ts.map +1 -1
  155. package/dist/types/src/util/formatting.d.ts +2 -2
  156. package/dist/types/src/util/formatting.d.ts.map +1 -1
  157. package/dist/types/src/util/index.d.ts +2 -1
  158. package/dist/types/src/util/index.d.ts.map +1 -1
  159. package/dist/types/src/util/properties.d.ts +35 -0
  160. package/dist/types/src/util/properties.d.ts.map +1 -0
  161. package/dist/types/src/util/properties.test.d.ts +2 -0
  162. package/dist/types/src/util/properties.test.d.ts.map +1 -0
  163. package/dist/types/src/util/refs.d.ts +3 -3
  164. package/dist/types/src/util/refs.d.ts.map +1 -1
  165. package/dist/types/tsconfig.tsbuildinfo +1 -1
  166. package/package.json +64 -47
  167. package/src/components/FieldEditor/FieldEditor.stories.tsx +49 -31
  168. package/src/components/FieldEditor/FieldEditor.test.tsx +4 -2
  169. package/src/components/FieldEditor/FieldEditor.tsx +100 -97
  170. package/src/components/Form/AUDIT.md +17 -0
  171. package/src/components/Form/Form.stories.tsx +151 -221
  172. package/src/components/Form/Form.tsx +461 -95
  173. package/src/components/Form/FormField.tsx +345 -0
  174. package/src/components/Form/FormFieldComponent.stories.tsx +65 -0
  175. package/src/components/Form/FormFieldComponent.tsx +253 -0
  176. package/src/components/Form/FormFieldSet.tsx +213 -0
  177. package/src/components/Form/FormTooltipsContext.ts +25 -0
  178. package/src/components/Form/Layout/FormLayout.stories.test.tsx +51 -0
  179. package/src/components/Form/Layout/FormLayout.stories.tsx +422 -0
  180. package/src/components/Form/Layout/FormLayout.test.ts +59 -0
  181. package/src/components/Form/Layout/FormLayout.tsx +251 -0
  182. package/src/components/Form/Layout/annotation.ts +38 -0
  183. package/src/components/Form/Layout/index.ts +7 -0
  184. package/src/components/Form/Layout/parser.test.ts +120 -0
  185. package/src/components/Form/Layout/parser.ts +167 -0
  186. package/src/components/Form/README.md +3 -0
  187. package/src/components/Form/fields/ArrayField.tsx +173 -0
  188. package/src/components/Form/fields/BooleanField.tsx +22 -0
  189. package/src/components/Form/fields/DateField.tsx +101 -0
  190. package/src/components/Form/fields/GeoPointField.tsx +124 -0
  191. package/src/components/Form/fields/InlineRefField.tsx +138 -0
  192. package/src/components/Form/fields/MarkdownField.stories.tsx +206 -0
  193. package/src/components/Form/fields/MarkdownField.tsx +167 -0
  194. package/src/components/Form/fields/NumberField.tsx +76 -0
  195. package/src/components/Form/fields/RefField.test.ts +45 -0
  196. package/src/components/Form/fields/RefField.tsx +266 -0
  197. package/src/components/Form/fields/SelectField.tsx +77 -0
  198. package/src/components/Form/fields/SelectOptionField.stories.tsx +66 -0
  199. package/src/components/Form/{custom/SelectOptionsInput.tsx → fields/SelectOptionField.tsx} +39 -32
  200. package/src/components/Form/fields/TextAreaField.tsx +38 -0
  201. package/src/components/Form/fields/TextField.tsx +38 -0
  202. package/src/components/Form/fields/TupleField.tsx +55 -0
  203. package/src/components/Form/fields/index.ts +17 -0
  204. package/src/components/Form/index.ts +6 -4
  205. package/src/components/Form/meta-tags.test.ts +47 -0
  206. package/src/components/Form/meta-tags.ts +33 -0
  207. package/src/components/ObjectForm/ObjectForm.stories.tsx +62 -0
  208. package/src/components/ObjectForm/ObjectForm.tsx +111 -0
  209. package/src/components/{ControlSection → ObjectForm}/index.ts +1 -1
  210. package/src/components/ObjectPicker/ObjectPicker.stories.tsx +212 -0
  211. package/src/components/ObjectPicker/ObjectPicker.tsx +202 -0
  212. package/src/components/ObjectPicker/index.ts +5 -0
  213. package/src/components/ObjectProperties/ObjectProperties.stories.tsx +350 -0
  214. package/src/components/ObjectProperties/ObjectProperties.test.tsx +111 -0
  215. package/src/components/ObjectProperties/ObjectProperties.tsx +146 -0
  216. package/src/components/ObjectProperties/index.ts +5 -0
  217. package/src/components/ObjectTree/ObjectTree.stories.tsx +134 -0
  218. package/src/components/ObjectTree/ObjectTree.tsx +190 -0
  219. package/src/components/ObjectTree/index.ts +5 -0
  220. package/src/components/RefEditor/RefEditor.stories.tsx +148 -0
  221. package/src/components/RefEditor/RefEditor.tsx +275 -0
  222. package/src/components/RefEditor/index.ts +6 -0
  223. package/src/components/RefEditor/ref-editor-extension.ts +254 -0
  224. package/src/components/Settings/AUDIT.md +51 -0
  225. package/src/components/Settings/Settings.stories.tsx +104 -0
  226. package/src/components/Settings/Settings.tsx +81 -0
  227. package/src/components/Settings/SettingsFieldSet.tsx +257 -0
  228. package/src/components/Settings/SettingsItem.tsx +58 -0
  229. package/src/components/Settings/SettingsSelectField.tsx +59 -0
  230. package/src/components/Settings/index.ts +7 -0
  231. package/src/components/ViewEditor/ViewEditor.stories.tsx +132 -64
  232. package/src/components/ViewEditor/ViewEditor.test.tsx +23 -22
  233. package/src/components/ViewEditor/ViewEditor.tsx +378 -216
  234. package/src/components/index.ts +6 -3
  235. package/src/components/testing.tsx +31 -12
  236. package/src/hooks/index.ts +2 -3
  237. package/src/hooks/useFormHandler.ts +380 -0
  238. package/src/hooks/useKeyHandler.tsx +37 -0
  239. package/src/index.ts +0 -4
  240. package/src/translations.ts +76 -59
  241. package/src/util/field-type.ts +60 -0
  242. package/src/util/field.ts +33 -43
  243. package/src/util/formatting.ts +22 -22
  244. package/src/util/index.ts +2 -1
  245. package/src/util/properties.test.ts +153 -0
  246. package/src/util/properties.ts +100 -0
  247. package/src/util/refs.ts +20 -19
  248. package/src/vite-env.d.ts +10 -0
  249. package/dist/types/src/components/ControlSection/ControlSection.d.ts +0 -23
  250. package/dist/types/src/components/ControlSection/ControlSection.d.ts.map +0 -1
  251. package/dist/types/src/components/ControlSection/ControlSection.stories.d.ts +0 -8
  252. package/dist/types/src/components/ControlSection/ControlSection.stories.d.ts.map +0 -1
  253. package/dist/types/src/components/ControlSection/index.d.ts +0 -2
  254. package/dist/types/src/components/ControlSection/index.d.ts.map +0 -1
  255. package/dist/types/src/components/Form/ArrayField.d.ts +0 -16
  256. package/dist/types/src/components/Form/ArrayField.d.ts.map +0 -1
  257. package/dist/types/src/components/Form/Defaults.d.ts +0 -14
  258. package/dist/types/src/components/Form/Defaults.d.ts.map +0 -1
  259. package/dist/types/src/components/Form/FormActions.d.ts +0 -9
  260. package/dist/types/src/components/Form/FormActions.d.ts.map +0 -1
  261. package/dist/types/src/components/Form/FormContent.d.ts +0 -57
  262. package/dist/types/src/components/Form/FormContent.d.ts.map +0 -1
  263. package/dist/types/src/components/Form/FormContext.d.ts +0 -23
  264. package/dist/types/src/components/Form/FormContext.d.ts.map +0 -1
  265. package/dist/types/src/components/Form/Input.d.ts +0 -26
  266. package/dist/types/src/components/Form/Input.d.ts.map +0 -1
  267. package/dist/types/src/components/Form/RefField.d.ts +0 -12
  268. package/dist/types/src/components/Form/RefField.d.ts.map +0 -1
  269. package/dist/types/src/components/Form/custom/GeoPointInput.d.ts +0 -4
  270. package/dist/types/src/components/Form/custom/GeoPointInput.d.ts.map +0 -1
  271. package/dist/types/src/components/Form/custom/SelectOptionsInput.d.ts +0 -4
  272. package/dist/types/src/components/Form/custom/SelectOptionsInput.d.ts.map +0 -1
  273. package/dist/types/src/components/Form/custom/SelectOptionsInput.stories.d.ts +0 -7
  274. package/dist/types/src/components/Form/custom/SelectOptionsInput.stories.d.ts.map +0 -1
  275. package/dist/types/src/components/Form/custom/TupleInput.d.ts +0 -6
  276. package/dist/types/src/components/Form/custom/TupleInput.d.ts.map +0 -1
  277. package/dist/types/src/components/Form/custom/index.d.ts +0 -4
  278. package/dist/types/src/components/Form/custom/index.d.ts.map +0 -1
  279. package/dist/types/src/components/Form/factory.d.ts +0 -8
  280. package/dist/types/src/components/Form/factory.d.ts.map +0 -1
  281. package/dist/types/src/components/deprecated/Form.d.ts +0 -15
  282. package/dist/types/src/components/deprecated/Form.d.ts.map +0 -1
  283. package/dist/types/src/components/deprecated/Form.stories.d.ts +0 -13
  284. package/dist/types/src/components/deprecated/Form.stories.d.ts.map +0 -1
  285. package/dist/types/src/components/deprecated/FormInput.d.ts +0 -16
  286. package/dist/types/src/components/deprecated/FormInput.d.ts.map +0 -1
  287. package/dist/types/src/components/deprecated/index.d.ts +0 -2
  288. package/dist/types/src/components/deprecated/index.d.ts.map +0 -1
  289. package/dist/types/src/hooks/useForm.d.ts +0 -67
  290. package/dist/types/src/hooks/useForm.d.ts.map +0 -1
  291. package/dist/types/src/hooks/useQueryRefOptions.d.ts +0 -23
  292. package/dist/types/src/hooks/useQueryRefOptions.d.ts.map +0 -1
  293. package/dist/types/src/hooks/useRefQueryLookupHandler.d.ts +0 -8
  294. package/dist/types/src/hooks/useRefQueryLookupHandler.d.ts.map +0 -1
  295. package/dist/types/src/util/schema.d.ts +0 -3
  296. package/dist/types/src/util/schema.d.ts.map +0 -1
  297. package/src/components/ControlSection/ControlSection.stories.tsx +0 -42
  298. package/src/components/ControlSection/ControlSection.tsx +0 -139
  299. package/src/components/Form/ArrayField.tsx +0 -125
  300. package/src/components/Form/Defaults.tsx +0 -204
  301. package/src/components/Form/FormActions.tsx +0 -54
  302. package/src/components/Form/FormContent.tsx +0 -241
  303. package/src/components/Form/FormContext.tsx +0 -110
  304. package/src/components/Form/Input.tsx +0 -51
  305. package/src/components/Form/RefField.tsx +0 -214
  306. package/src/components/Form/custom/GeoPointInput.tsx +0 -72
  307. package/src/components/Form/custom/SelectOptionsInput.stories.tsx +0 -62
  308. package/src/components/Form/custom/TupleInput.tsx +0 -47
  309. package/src/components/Form/custom/index.ts +0 -7
  310. package/src/components/Form/factory.tsx +0 -31
  311. package/src/components/deprecated/Form.stories.tsx +0 -63
  312. package/src/components/deprecated/Form.tsx +0 -119
  313. package/src/components/deprecated/FormInput.tsx +0 -71
  314. package/src/components/deprecated/index.ts +0 -5
  315. package/src/hooks/useForm.ts +0 -293
  316. package/src/hooks/useQueryRefOptions.ts +0 -53
  317. package/src/hooks/useRefQueryLookupHandler.ts +0 -39
  318. package/src/util/schema.ts +0 -14
@@ -0,0 +1,173 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import * as Option from 'effect/Option';
6
+ import * as SchemaAST from 'effect/SchemaAST';
7
+ import React, { useCallback } from 'react';
8
+
9
+ import { Ref } from '@dxos/echo';
10
+ import { SchemaEx } from '@dxos/effect';
11
+ import { useTranslation } from '@dxos/react-ui';
12
+
13
+ import { translationKey } from '#translations';
14
+
15
+ import { getFormProperties } from '../../../util';
16
+ import { useFormValues } from '../Form';
17
+ import { FormField, IconBlock, type FormFieldProps } from '../FormField';
18
+ import { FormFieldLabel, type FormFieldStateProps } from '../FormFieldComponent';
19
+
20
+ export type ArrayFieldProps = {
21
+ label: string;
22
+ fieldProps: FormFieldStateProps;
23
+ } & FormFieldProps;
24
+
25
+ export const ArrayField = ({
26
+ type,
27
+ path,
28
+ label,
29
+ readonly,
30
+ layout,
31
+ fieldProps: inputProps,
32
+ ...props
33
+ }: ArrayFieldProps) => {
34
+ const { t } = useTranslation(translationKey);
35
+ const elementType = SchemaEx.getArrayElementType(type);
36
+ const { onValueChange } = inputProps;
37
+ const values = useFormValues(ArrayField.displayName, path, () => []);
38
+
39
+ const getDefaultObjectValue = (typeNode: SchemaAST.AST): any => {
40
+ const baseNode = SchemaEx.findNode(typeNode, SchemaEx.isDiscriminatedUnion);
41
+ const typeLiteral = baseNode
42
+ ? SchemaEx.getDiscriminatedType(baseNode, {})
43
+ : SchemaEx.findNode(typeNode, SchemaAST.isTypeLiteral);
44
+ if (!typeLiteral) {
45
+ return {};
46
+ }
47
+
48
+ return Object.fromEntries(
49
+ getFormProperties(typeLiteral).map((prop) => {
50
+ const defaultValue = SchemaAST.getDefaultAnnotation(prop.type).pipe((annotation) =>
51
+ Option.getOrUndefined(annotation),
52
+ );
53
+ return [prop.name, defaultValue];
54
+ }),
55
+ );
56
+ };
57
+
58
+ const handleAdd = useCallback(() => {
59
+ const defaultValue =
60
+ SchemaEx.isNestedType(type) && elementType ? getDefaultObjectValue(elementType) : getDefaultValue(elementType);
61
+ // `values` is `undefined` on first render for arrays whose parent path
62
+ // hasn't been materialised in the form values yet (e.g. `package.repos`
63
+ // when the form starts with no `package`). `useFormValues`'s default-
64
+ // value effect would eventually backfill it to `[]`, but until then the
65
+ // old `values && ...` guard silently swallowed the click. Treat a
66
+ // missing array as empty so Add always produces `[defaultValue]`.
67
+ onValueChange(type, [...(values ?? []), defaultValue]);
68
+ }, [onValueChange, type, elementType, values]);
69
+
70
+ const handleDelete = useCallback(
71
+ (idx: number) => {
72
+ onValueChange(
73
+ type,
74
+ values?.filter((_, i) => i !== idx),
75
+ );
76
+ },
77
+ [onValueChange, type, values],
78
+ );
79
+
80
+ if (!elementType || ((readonly || layout === 'static') && values && values.length < 1)) {
81
+ return null;
82
+ }
83
+
84
+ const renderItemAsObject = elementType && SchemaEx.isNestedType(elementType) && !Ref.isRefType(elementType);
85
+
86
+ return (
87
+ <>
88
+ {(layout !== 'static' || (values && values.length > 0)) && (
89
+ <div className='flex items-center gap-2'>
90
+ <div className='flex-1 min-w-0'>
91
+ <FormFieldLabel readonly={readonly} label={label} path={SchemaEx.createJsonPath(path ?? [])} asChild />
92
+ </div>
93
+ {!readonly && layout !== 'static' && (
94
+ <IconBlock inline icon='ph--plus--regular' label={t('add-item.button')} onClick={handleAdd} />
95
+ )}
96
+ </div>
97
+ )}
98
+
99
+ <div className='flex flex-col'>
100
+ {values?.map((_, index) => {
101
+ const isLast = index === values.length - 1;
102
+
103
+ // Object items: each row contains a recursively-rendered FormField
104
+ // (multiple sub-rows for the object's fields) wrapped in a border,
105
+ // with the delete button bottom-aligned next to it.
106
+ // Scalar items: a single-row inline FormField with a center-aligned
107
+ // delete button. Refs and primitive arrays use this layout.
108
+ const fieldField = (
109
+ <FormField
110
+ {...props}
111
+ autoFocus={isLast}
112
+ type={elementType}
113
+ // Suppress the per-item header for object items only — the recursive
114
+ // form already renders labels for each sub-field. Scalar items
115
+ // (refs, primitives) keep the parent name so inline-layout
116
+ // children (e.g. RefField) have a real label to use as a
117
+ // fallback placeholder.
118
+ {...(renderItemAsObject && { name: null })}
119
+ path={[...(path ?? []), index]}
120
+ readonly={readonly || layout === 'static'}
121
+ layout={renderItemAsObject ? (layout === 'static' ? 'static' : undefined) : 'inline'}
122
+ />
123
+ );
124
+
125
+ return (
126
+ <div key={index} className='grid grid-cols-[1fr_min-content] items-center mb-1 last:mb-form-gap'>
127
+ {fieldField}
128
+ {!readonly && layout !== 'static' && (
129
+ <IconBlock
130
+ inline={!renderItemAsObject}
131
+ icon='ph--x--regular'
132
+ label={t('remove-item.button')}
133
+ onClick={() => handleDelete(index)}
134
+ />
135
+ )}
136
+ </div>
137
+ );
138
+ })}
139
+ </div>
140
+ </>
141
+ );
142
+ };
143
+
144
+ ArrayField.displayName = 'Form.ArrayField';
145
+
146
+ /**
147
+ * Returns the default empty value for a given AST.
148
+ * Used for initializing new array values etc.
149
+ */
150
+ // TODO(wittjosiah): Factor out?
151
+ export const getDefaultValue = (ast?: SchemaAST.AST): any => {
152
+ switch (ast?._tag) {
153
+ case 'StringKeyword': {
154
+ return '';
155
+ }
156
+ case 'NumberKeyword': {
157
+ return 0;
158
+ }
159
+ case 'BooleanKeyword': {
160
+ return false;
161
+ }
162
+ case 'Suspend': {
163
+ return getDefaultValue(ast.f());
164
+ }
165
+ default: {
166
+ if (ast && SchemaEx.isNestedType(ast)) {
167
+ return {};
168
+ } else {
169
+ throw new Error(`Unsupported type: ${ast?._tag}`);
170
+ }
171
+ }
172
+ }
173
+ };
@@ -0,0 +1,22 @@
1
+ //
2
+ // Copyright 2024 DXOS.org
3
+ //
4
+
5
+ import React, { useCallback } from 'react';
6
+
7
+ import { Input, type SwitchProps } from '@dxos/react-ui';
8
+
9
+ import { type FormFieldComponentProps, FormFieldWrapper } from '../FormFieldComponent';
10
+
11
+ export const BooleanField = ({ type, readonly, onValueChange, ...props }: FormFieldComponentProps<boolean>) => {
12
+ const handleChange = useCallback<NonNullable<SwitchProps['onCheckedChange']>>(
13
+ (value) => onValueChange?.(type, value),
14
+ [type, onValueChange],
15
+ );
16
+
17
+ return (
18
+ <FormFieldWrapper<boolean> readonly={readonly} {...props}>
19
+ {({ value }) => <Input.Switch disabled={!!readonly} checked={value} onCheckedChange={handleChange} />}
20
+ </FormFieldWrapper>
21
+ );
22
+ };
@@ -0,0 +1,101 @@
1
+ //
2
+ // Copyright 2026 DXOS.org
3
+ //
4
+
5
+ import { format as formatDate } from 'date-fns';
6
+ import React, { useCallback } from 'react';
7
+
8
+ import { Format } from '@dxos/echo';
9
+ import { Input } from '@dxos/react-ui';
10
+
11
+ import { type FormFieldComponentProps, FormFieldWrapper } from '../FormFieldComponent';
12
+
13
+ /**
14
+ * Stored value shapes:
15
+ * - `Format.DateTime` -> ISO 8601 (`2018-11-13T20:20:39.000Z`).
16
+ * - `Format.Date` -> `YYYY-MM-DD`.
17
+ * - `Format.Time` -> `HH:mm:ss`.
18
+ *
19
+ * Segmented input value shapes (react-aria-components-backed):
20
+ * - `Input.DateTime` -> `YYYY-MM-DDTHH:mm` in local time.
21
+ * - `Input.Date` -> `YYYY-MM-DD`.
22
+ * - `Input.Time` -> `HH:mm`.
23
+ */
24
+
25
+ /** ISO 8601 → `YYYY-MM-DDTHH:mm` in the user's local timezone. */
26
+ const isoToLocalDateTime = (value: string | undefined): string => {
27
+ if (!value) {
28
+ return '';
29
+ }
30
+ const date = new Date(value);
31
+ if (Number.isNaN(date.getTime())) {
32
+ return '';
33
+ }
34
+ return formatDate(date, "yyyy-MM-dd'T'HH:mm");
35
+ };
36
+
37
+ /** `YYYY-MM-DDTHH:mm` (local) → ISO 8601 with timezone. */
38
+ const localDateTimeToIso = (value: string): string | undefined => {
39
+ if (!value) {
40
+ return undefined;
41
+ }
42
+ // Treat the input as local time. `new Date('YYYY-MM-DDTHH:mm')` parses as local.
43
+ const date = new Date(value);
44
+ return Number.isNaN(date.getTime()) ? undefined : date.toISOString();
45
+ };
46
+
47
+ export const DateField = ({
48
+ type,
49
+ format,
50
+ readonly,
51
+ placeholder: _placeholder,
52
+ onValueChange,
53
+ onBlur: _onBlur,
54
+ ...props
55
+ }: FormFieldComponentProps<string>) => {
56
+ const handleSimpleChange = useCallback((next: string) => onValueChange(type, next), [type, onValueChange]);
57
+
58
+ const handleDateTimeChange = useCallback(
59
+ (next: string) => {
60
+ const iso = localDateTimeToIso(next);
61
+ onValueChange(type, iso as string);
62
+ },
63
+ [type, onValueChange],
64
+ );
65
+
66
+ return (
67
+ <FormFieldWrapper<string> readonly={readonly} format={format} {...props}>
68
+ {({ value }) => {
69
+ switch (format) {
70
+ case Format.TypeFormat.Date:
71
+ return (
72
+ <div className='grid grid-cols-[minmax(0,1fr)_min-content] items-stretch gap-1'>
73
+ <Input.Date
74
+ classNames='min-w-0 overflow-hidden'
75
+ disabled={!!readonly}
76
+ value={value ?? ''}
77
+ onValueChange={handleSimpleChange}
78
+ />
79
+ <Input.TriggerIcon classNames='h-full' />
80
+ </div>
81
+ );
82
+ case Format.TypeFormat.Time:
83
+ return <Input.Time disabled={!!readonly} value={value ?? ''} onValueChange={handleSimpleChange} />;
84
+ case Format.TypeFormat.DateTime:
85
+ default:
86
+ return (
87
+ <div className='grid grid-cols-[minmax(0,1fr)_min-content] items-stretch gap-1'>
88
+ <Input.DateTime
89
+ classNames='min-w-0 overflow-hidden'
90
+ disabled={!!readonly}
91
+ value={isoToLocalDateTime(value)}
92
+ onValueChange={handleDateTimeChange}
93
+ />
94
+ <Input.TriggerIcon classNames='h-full' />
95
+ </div>
96
+ );
97
+ }
98
+ }}
99
+ </FormFieldWrapper>
100
+ );
101
+ };
@@ -0,0 +1,124 @@
1
+ //
2
+ // Copyright 2024 DXOS.org
3
+ //
4
+
5
+ import React, { type ChangeEvent, useCallback, useEffect, useMemo, useState } from 'react';
6
+
7
+ import { GeoLocation, type GeoPoint } from '@dxos/echo/Format';
8
+ import { Input, useTranslation } from '@dxos/react-ui';
9
+ import { safeParseFloat } from '@dxos/util';
10
+
11
+ import { translationKey } from '#translations';
12
+
13
+ import { type FormFieldComponentProps, FormFieldLabel } from '../FormFieldComponent';
14
+
15
+ export const GeoPointField = ({
16
+ type,
17
+ label,
18
+ jsonPath,
19
+ readonly,
20
+ layout,
21
+ getStatus,
22
+ getValue,
23
+ onValueChange,
24
+ onBlur,
25
+ }: FormFieldComponentProps<GeoPoint>) => {
26
+ const { t } = useTranslation(translationKey);
27
+ const { status, error } = getStatus();
28
+ const geoPoint = useMemo<GeoPoint>(() => getValue() ?? [0, 0], [getValue]);
29
+ const value = useMemo(() => GeoLocation.fromGeoPoint(geoPoint), [geoPoint]);
30
+
31
+ const [longitudeText, setLongitudeText] = useState(value.longitude?.toString());
32
+ const [latitudeText, setLatitudeText] = useState(value.latitude?.toString());
33
+ useEffect(() => {
34
+ const location = GeoLocation.fromGeoPoint(geoPoint);
35
+ setLongitudeText(location.longitude?.toString());
36
+ setLatitudeText(location.latitude?.toString());
37
+ }, [geoPoint]);
38
+
39
+ const handleChange = useCallback(
40
+ (coordinateType: keyof Pick<GeoLocation, 'longitude' | 'latitude'>, setText: (text: string) => void) =>
41
+ (event: ChangeEvent<HTMLInputElement>) => {
42
+ const inputText = event.target.value;
43
+ setText(inputText);
44
+ if (inputText !== '' && inputText !== '-') {
45
+ const coord = safeParseFloat(inputText);
46
+ if (coord !== undefined && !isNaN(coord)) {
47
+ const currentLocation = GeoLocation.fromGeoPoint(getValue() ?? [0, 0]);
48
+ const newLocation = { ...currentLocation, [coordinateType]: coord };
49
+ const newValue = GeoLocation.toGeoPoint(newLocation);
50
+ onValueChange(type, newValue);
51
+ }
52
+ }
53
+ },
54
+ [type, getValue, onValueChange],
55
+ );
56
+
57
+ if ((readonly || layout === 'static') && !value?.latitude && !value?.longitude) {
58
+ return null;
59
+ }
60
+
61
+ return (
62
+ <Input.Root validationValence={status}>
63
+ {layout !== 'inline' && (
64
+ <FormFieldLabel error={error} readonly={readonly} label={label} path={jsonPath} asChild />
65
+ )}
66
+ {layout === 'static' ? (
67
+ <LatLng {...value} />
68
+ ) : (
69
+ <div className='grid grid-cols-2 gap-form-gap'>
70
+ <div>
71
+ <Input.Root>
72
+ {layout !== 'inline' && <Input.Label>{t('latitude.label')}</Input.Label>}
73
+ <Input.TextInput
74
+ type='number'
75
+ step='0.00001'
76
+ min='-90'
77
+ max='90'
78
+ disabled={!!readonly}
79
+ placeholder={t('latitude.placeholder')}
80
+ value={latitudeText ?? ''}
81
+ onChange={handleChange('latitude', setLatitudeText)}
82
+ onBlur={onBlur}
83
+ />
84
+ </Input.Root>
85
+ </div>
86
+ <div>
87
+ <Input.Root>
88
+ {layout !== 'inline' && <Input.Label>{t('longitude.label')}</Input.Label>}
89
+ <Input.TextInput
90
+ type='number'
91
+ step='0.00001'
92
+ min='-180'
93
+ max='180'
94
+ disabled={!!readonly}
95
+ placeholder={t('longitude.placeholder')}
96
+ value={longitudeText ?? ''}
97
+ onChange={handleChange('longitude', setLongitudeText)}
98
+ onBlur={onBlur}
99
+ />
100
+ </Input.Root>
101
+ </div>
102
+ </div>
103
+ )}
104
+ </Input.Root>
105
+ );
106
+ };
107
+
108
+ const LatLng = ({ latitude = 0, longitude = 0 }: GeoLocation) => {
109
+ const latHem = latitude >= 0 ? 'N' : 'S';
110
+ const lngHem = longitude >= 0 ? 'E' : 'W';
111
+
112
+ return (
113
+ <span className='inline-flex items-center gap-form-gap'>
114
+ <span>
115
+ <span>{Math.abs(latitude).toFixed(5)}</span>
116
+ <span className='text-subdued'>°{latHem}</span>
117
+ </span>
118
+ <span>
119
+ <span>{Math.abs(longitude).toFixed(5)}</span>
120
+ <span className='text-subdued'>°{lngHem}</span>
121
+ </span>
122
+ </span>
123
+ );
124
+ };
@@ -0,0 +1,138 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { useAtomValue } from '@effect-atom/atom-react';
6
+ import React, { useCallback, useMemo } from 'react';
7
+
8
+ import { type Database, Obj, Ref, Type } from '@dxos/echo';
9
+ import { useType as defaultUseType } from '@dxos/echo-react';
10
+ import { ReferenceAnnotationId, type ReferenceAnnotationValue } from '@dxos/echo/Annotation';
11
+ import { SchemaEx } from '@dxos/effect';
12
+ import { DXN, URI } from '@dxos/keys';
13
+ import { Button, Icon, Input, useTranslation } from '@dxos/react-ui';
14
+
15
+ import { translationKey } from '#translations';
16
+
17
+ import { Form, omitId } from '../Form';
18
+ import { FormFieldLabel } from '../FormFieldComponent';
19
+ import { type RefFieldProps } from './RefField';
20
+
21
+ /**
22
+ * Renders a referenced object's own fields inline (a nested form bound to the
23
+ * target) rather than the {@link RefField} picker. Activated by
24
+ * `FormInlineAnnotation.set(true)` on the `Ref` property.
25
+ *
26
+ * The nested form edits the target object directly: each changed path is
27
+ * written back via `Obj.setValue` within an `Obj.update`, mirroring
28
+ * `ObjectProperties` (without the synthetic meta-tags row).
29
+ */
30
+ export const InlineRefField = (props: RefFieldProps) => {
31
+ const {
32
+ type,
33
+ readonly,
34
+ label,
35
+ jsonPath,
36
+ layout,
37
+ db,
38
+ getValue,
39
+ onValueChange,
40
+ onCreate,
41
+ useType = defaultUseType,
42
+ } = props;
43
+ const { t } = useTranslation(translationKey);
44
+
45
+ const reference = getValue() as Ref.Ref<any> | undefined;
46
+ const typename = useMemo(
47
+ () => (type ? SchemaEx.findAnnotation<ReferenceAnnotationValue>(type, ReferenceAnnotationId)?.typename : undefined),
48
+ [type],
49
+ );
50
+
51
+ // Empty ref: offer to create the referenced object so the inline form has a target.
52
+ const createType = useType(db, typename ? DXN.make(typename) : undefined);
53
+ const handleCreate = useCallback(async () => {
54
+ if (!createType || !onCreate) {
55
+ return;
56
+ }
57
+ const newObject = await onCreate(createType, {});
58
+ if (newObject) {
59
+ onValueChange(type, Ref.make(newObject));
60
+ }
61
+ }, [createType, onCreate, type, onValueChange]);
62
+
63
+ if (readonly && !reference) {
64
+ return null;
65
+ }
66
+
67
+ return (
68
+ <Input.Root>
69
+ {layout !== 'inline' && <FormFieldLabel readonly={readonly} label={label} path={jsonPath} />}
70
+ {reference ? (
71
+ <InlineForm reference={reference} db={db} readonly={readonly} useType={useType} />
72
+ ) : (
73
+ !readonly &&
74
+ onCreate && (
75
+ <Button classNames='w-full gap-form-gap' disabled={!createType || !db} onClick={() => void handleCreate()}>
76
+ <Icon icon='ph--plus--regular' size={4} />
77
+ <span>{label || t('ref-field.placeholder')}</span>
78
+ </Button>
79
+ )
80
+ )}
81
+ </Input.Root>
82
+ );
83
+ };
84
+
85
+ type InlineFormProps = {
86
+ reference: Ref.Ref<any>;
87
+ db?: Database.Database;
88
+ readonly?: boolean;
89
+ // Accepts both the generic `defaultUseType` and `RefFieldProps['useType']`.
90
+ useType?: (db?: Database.Database, typeUri?: URI.URI) => Type.AnyEntity | undefined;
91
+ };
92
+
93
+ const InlineForm = ({ reference, db, readonly, useType = defaultUseType }: InlineFormProps) => {
94
+ const target = useAtomValue(useMemo(() => reference.atom, [reference]));
95
+ const typeUri = target ? Obj.getTypeURI(target) : undefined;
96
+ const typeFromRegistry = useType(db, typeUri);
97
+ const targetType = (target && Obj.getType(target)) || typeFromRegistry;
98
+ // Drop the ECHO `id` property (mirrors `ObjectProperties` via `withMetaTags`);
99
+ // otherwise the nested form renders an "Id" field. Hidden fields
100
+ // (`FormInputAnnotation.set(false)`) are already filtered by the field set.
101
+ const formSchema = useMemo(() => (targetType ? omitId(Type.getSchema(targetType)) : undefined), [targetType]);
102
+ const defaultValues = useMemo(() => (target ? { ...target } : {}), [target]);
103
+
104
+ // `formSchema` is resolved at runtime (the referenced object's schema), so the
105
+ // form's value type is not statically known here — `any` at this form-value
106
+ // boundary mirrors `ObjectProperties`. Each changed path is written back to the
107
+ // live target via `Obj.setValue`.
108
+ const handleChange = useCallback(
109
+ (values: any, { isValid, changed }: { isValid: boolean; changed: Record<SchemaEx.JsonPath, boolean> }) => {
110
+ if (!isValid || !target) {
111
+ return;
112
+ }
113
+ const changedPaths = (Object.keys(changed) as SchemaEx.JsonPath[]).filter((path) => changed[path]);
114
+ if (changedPaths.length === 0) {
115
+ return;
116
+ }
117
+ Obj.update(target, () => {
118
+ for (const path of changedPaths) {
119
+ const parts = SchemaEx.splitJsonPath(path);
120
+ Obj.setValue(target, parts, Obj.getValue(values, parts));
121
+ }
122
+ });
123
+ },
124
+ [target],
125
+ );
126
+
127
+ if (!target || !formSchema) {
128
+ return null;
129
+ }
130
+
131
+ return (
132
+ <Form.Root db={db} schema={formSchema} defaultValues={defaultValues as any} onValuesChanged={handleChange}>
133
+ <Form.Content>
134
+ <Form.FieldSet collapsible readonly={readonly} />
135
+ </Form.Content>
136
+ </Form.Root>
137
+ );
138
+ };