@wordpress/dataviews 8.0.1-next.e256d081a.0 → 9.0.1-next.6870dfe5b.0

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 (269) hide show
  1. package/CHANGELOG.md +24 -1
  2. package/README.md +96 -1
  3. package/build/components/dataform-context/index.js +1 -0
  4. package/build/components/dataform-context/index.js.map +1 -1
  5. package/build/components/dataviews/index.js +11 -1
  6. package/build/components/dataviews/index.js.map +1 -1
  7. package/build/components/dataviews-context/index.js +1 -0
  8. package/build/components/dataviews-context/index.js.map +1 -1
  9. package/build/components/dataviews-layout/index.js +2 -1
  10. package/build/components/dataviews-layout/index.js.map +1 -1
  11. package/build/components/dataviews-picker/footer.js +145 -0
  12. package/build/components/dataviews-picker/footer.js.map +1 -0
  13. package/build/components/dataviews-picker/index.js +201 -0
  14. package/build/components/dataviews-picker/index.js.map +1 -0
  15. package/build/components/dataviews-selection-checkbox/index.js +4 -2
  16. package/build/components/dataviews-selection-checkbox/index.js.map +1 -1
  17. package/build/components/dataviews-view-config/index.js +1 -0
  18. package/build/components/dataviews-view-config/index.js.map +1 -1
  19. package/build/constants.js +4 -1
  20. package/build/constants.js.map +1 -1
  21. package/build/dataform-controls/checkbox.js +23 -2
  22. package/build/dataform-controls/checkbox.js.map +1 -1
  23. package/build/dataform-controls/color.js +128 -0
  24. package/build/dataform-controls/color.js.map +1 -0
  25. package/build/dataform-controls/email.js +10 -45
  26. package/build/dataform-controls/email.js.map +1 -1
  27. package/build/dataform-controls/index.js +8 -2
  28. package/build/dataform-controls/index.js.map +1 -1
  29. package/build/dataform-controls/telephone.js +34 -0
  30. package/build/dataform-controls/telephone.js.map +1 -0
  31. package/build/dataform-controls/text.js +7 -48
  32. package/build/dataform-controls/text.js.map +1 -1
  33. package/build/dataform-controls/{boolean.js → toggle.js} +6 -4
  34. package/build/dataform-controls/toggle.js.map +1 -0
  35. package/build/dataform-controls/url.js +34 -0
  36. package/build/dataform-controls/url.js.map +1 -0
  37. package/build/dataform-controls/utils/validated-text.js +76 -0
  38. package/build/dataform-controls/utils/validated-text.js.map +1 -0
  39. package/build/dataforms-layouts/card/index.js +6 -7
  40. package/build/dataforms-layouts/card/index.js.map +1 -1
  41. package/build/dataforms-layouts/data-form-layout.js +16 -4
  42. package/build/dataforms-layouts/data-form-layout.js.map +1 -1
  43. package/build/dataforms-layouts/index.js +31 -1
  44. package/build/dataforms-layouts/index.js.map +1 -1
  45. package/build/dataforms-layouts/row/index.js +113 -0
  46. package/build/dataforms-layouts/row/index.js.map +1 -0
  47. package/build/dataviews-layouts/grid/index.js +16 -11
  48. package/build/dataviews-layouts/grid/index.js.map +1 -1
  49. package/build/dataviews-layouts/index.js +9 -1
  50. package/build/dataviews-layouts/index.js.map +1 -1
  51. package/build/dataviews-layouts/picker-grid/index.js +357 -0
  52. package/build/dataviews-layouts/picker-grid/index.js.map +1 -0
  53. package/build/dataviews-layouts/utils/grid-items.js +37 -0
  54. package/build/dataviews-layouts/utils/grid-items.js.map +1 -0
  55. package/build/dataviews-layouts/utils/preview-size-picker.js +81 -0
  56. package/build/dataviews-layouts/utils/preview-size-picker.js.map +1 -0
  57. package/build/field-types/boolean.js +1 -1
  58. package/build/field-types/boolean.js.map +1 -1
  59. package/build/field-types/color.js +113 -0
  60. package/build/field-types/color.js.map +1 -0
  61. package/build/field-types/index.js +12 -0
  62. package/build/field-types/index.js.map +1 -1
  63. package/build/field-types/telephone.js +57 -0
  64. package/build/field-types/telephone.js.map +1 -0
  65. package/build/field-types/url.js +57 -0
  66. package/build/field-types/url.js.map +1 -0
  67. package/build/normalize-form-fields.js +6 -0
  68. package/build/normalize-form-fields.js.map +1 -1
  69. package/build/types.js.map +1 -1
  70. package/build/validation.js +1 -1
  71. package/build/validation.js.map +1 -1
  72. package/build-module/components/dataform-context/index.js +1 -0
  73. package/build-module/components/dataform-context/index.js.map +1 -1
  74. package/build-module/components/dataviews/index.js +11 -1
  75. package/build-module/components/dataviews/index.js.map +1 -1
  76. package/build-module/components/dataviews-context/index.js +1 -0
  77. package/build-module/components/dataviews-context/index.js.map +1 -1
  78. package/build-module/components/dataviews-layout/index.js +2 -1
  79. package/build-module/components/dataviews-layout/index.js.map +1 -1
  80. package/build-module/components/dataviews-picker/footer.js +136 -0
  81. package/build-module/components/dataviews-picker/footer.js.map +1 -0
  82. package/build-module/components/dataviews-picker/index.js +191 -0
  83. package/build-module/components/dataviews-picker/index.js.map +1 -0
  84. package/build-module/components/dataviews-selection-checkbox/index.js +4 -2
  85. package/build-module/components/dataviews-selection-checkbox/index.js.map +1 -1
  86. package/build-module/components/dataviews-view-config/index.js +1 -0
  87. package/build-module/components/dataviews-view-config/index.js.map +1 -1
  88. package/build-module/constants.js +3 -0
  89. package/build-module/constants.js.map +1 -1
  90. package/build-module/dataform-controls/checkbox.js +25 -3
  91. package/build-module/dataform-controls/checkbox.js.map +1 -1
  92. package/build-module/dataform-controls/color.js +122 -0
  93. package/build-module/dataform-controls/color.js.map +1 -0
  94. package/build-module/dataform-controls/email.js +9 -45
  95. package/build-module/dataform-controls/email.js.map +1 -1
  96. package/build-module/dataform-controls/index.js +8 -2
  97. package/build-module/dataform-controls/index.js.map +1 -1
  98. package/build-module/dataform-controls/telephone.js +27 -0
  99. package/build-module/dataform-controls/telephone.js.map +1 -0
  100. package/build-module/dataform-controls/text.js +6 -48
  101. package/build-module/dataform-controls/text.js.map +1 -1
  102. package/build-module/dataform-controls/{boolean.js → toggle.js} +5 -3
  103. package/build-module/dataform-controls/toggle.js.map +1 -0
  104. package/build-module/dataform-controls/url.js +27 -0
  105. package/build-module/dataform-controls/url.js.map +1 -0
  106. package/build-module/dataform-controls/utils/validated-text.js +70 -0
  107. package/build-module/dataform-controls/utils/validated-text.js.map +1 -0
  108. package/build-module/dataforms-layouts/card/index.js +6 -7
  109. package/build-module/dataforms-layouts/card/index.js.map +1 -1
  110. package/build-module/dataforms-layouts/data-form-layout.js +14 -4
  111. package/build-module/dataforms-layouts/data-form-layout.js.map +1 -1
  112. package/build-module/dataforms-layouts/index.js +32 -1
  113. package/build-module/dataforms-layouts/index.js.map +1 -1
  114. package/build-module/dataforms-layouts/row/index.js +106 -0
  115. package/build-module/dataforms-layouts/row/index.js.map +1 -0
  116. package/build-module/dataviews-layouts/grid/index.js +16 -11
  117. package/build-module/dataviews-layouts/grid/index.js.map +1 -1
  118. package/build-module/dataviews-layouts/index.js +10 -2
  119. package/build-module/dataviews-layouts/index.js.map +1 -1
  120. package/build-module/dataviews-layouts/picker-grid/index.js +348 -0
  121. package/build-module/dataviews-layouts/picker-grid/index.js.map +1 -0
  122. package/build-module/dataviews-layouts/utils/grid-items.js +29 -0
  123. package/build-module/dataviews-layouts/utils/grid-items.js.map +1 -0
  124. package/build-module/dataviews-layouts/utils/preview-size-picker.js +73 -0
  125. package/build-module/dataviews-layouts/utils/preview-size-picker.js.map +1 -0
  126. package/build-module/field-types/boolean.js +1 -1
  127. package/build-module/field-types/boolean.js.map +1 -1
  128. package/build-module/field-types/color.js +107 -0
  129. package/build-module/field-types/color.js.map +1 -0
  130. package/build-module/field-types/index.js +12 -0
  131. package/build-module/field-types/index.js.map +1 -1
  132. package/build-module/field-types/telephone.js +51 -0
  133. package/build-module/field-types/telephone.js.map +1 -0
  134. package/build-module/field-types/url.js +51 -0
  135. package/build-module/field-types/url.js.map +1 -0
  136. package/build-module/normalize-form-fields.js +6 -0
  137. package/build-module/normalize-form-fields.js.map +1 -1
  138. package/build-module/types.js.map +1 -1
  139. package/build-module/validation.js +1 -1
  140. package/build-module/validation.js.map +1 -1
  141. package/build-style/style-rtl.css +252 -12
  142. package/build-style/style.css +252 -12
  143. package/build-types/components/dataform/stories/index.story.d.ts +19 -4
  144. package/build-types/components/dataform/stories/index.story.d.ts.map +1 -1
  145. package/build-types/components/dataform-context/index.d.ts.map +1 -1
  146. package/build-types/components/dataviews/index.d.ts +1 -1
  147. package/build-types/components/dataviews/index.d.ts.map +1 -1
  148. package/build-types/components/dataviews/stories/index.story.d.ts.map +1 -1
  149. package/build-types/components/dataviews-context/index.d.ts +1 -0
  150. package/build-types/components/dataviews-context/index.d.ts.map +1 -1
  151. package/build-types/components/dataviews-layout/index.d.ts.map +1 -1
  152. package/build-types/components/dataviews-picker/footer.d.ts +4 -0
  153. package/build-types/components/dataviews-picker/footer.d.ts.map +1 -0
  154. package/build-types/components/dataviews-picker/index.d.ts +55 -0
  155. package/build-types/components/dataviews-picker/index.d.ts.map +1 -0
  156. package/build-types/components/dataviews-picker/stories/index.story.d.ts +42 -0
  157. package/build-types/components/dataviews-picker/stories/index.story.d.ts.map +1 -0
  158. package/build-types/components/dataviews-selection-checkbox/index.d.ts +2 -1
  159. package/build-types/components/dataviews-selection-checkbox/index.d.ts.map +1 -1
  160. package/build-types/components/dataviews-view-config/index.d.ts.map +1 -1
  161. package/build-types/constants.d.ts +1 -0
  162. package/build-types/constants.d.ts.map +1 -1
  163. package/build-types/dataform-controls/checkbox.d.ts.map +1 -1
  164. package/build-types/dataform-controls/color.d.ts +6 -0
  165. package/build-types/dataform-controls/color.d.ts.map +1 -0
  166. package/build-types/dataform-controls/email.d.ts.map +1 -1
  167. package/build-types/dataform-controls/index.d.ts.map +1 -1
  168. package/build-types/dataform-controls/telephone.d.ts +6 -0
  169. package/build-types/dataform-controls/telephone.d.ts.map +1 -0
  170. package/build-types/dataform-controls/text.d.ts.map +1 -1
  171. package/build-types/dataform-controls/toggle.d.ts +6 -0
  172. package/build-types/dataform-controls/toggle.d.ts.map +1 -0
  173. package/build-types/dataform-controls/url.d.ts +6 -0
  174. package/build-types/dataform-controls/url.d.ts.map +1 -0
  175. package/build-types/dataform-controls/utils/validated-text.d.ts +16 -0
  176. package/build-types/dataform-controls/utils/validated-text.d.ts.map +1 -0
  177. package/build-types/dataforms-layouts/card/index.d.ts +0 -3
  178. package/build-types/dataforms-layouts/card/index.d.ts.map +1 -1
  179. package/build-types/dataforms-layouts/data-form-layout.d.ts +4 -1
  180. package/build-types/dataforms-layouts/data-form-layout.d.ts.map +1 -1
  181. package/build-types/dataforms-layouts/index.d.ts +10 -0
  182. package/build-types/dataforms-layouts/index.d.ts.map +1 -1
  183. package/build-types/dataforms-layouts/row/index.d.ts +6 -0
  184. package/build-types/dataforms-layouts/row/index.d.ts.map +1 -0
  185. package/build-types/dataviews-layouts/grid/index.d.ts.map +1 -1
  186. package/build-types/dataviews-layouts/index.d.ts +12 -1
  187. package/build-types/dataviews-layouts/index.d.ts.map +1 -1
  188. package/build-types/dataviews-layouts/picker-grid/index.d.ts +4 -0
  189. package/build-types/dataviews-layouts/picker-grid/index.d.ts.map +1 -0
  190. package/build-types/dataviews-layouts/utils/grid-items.d.ts +5 -0
  191. package/build-types/dataviews-layouts/utils/grid-items.d.ts.map +1 -0
  192. package/build-types/dataviews-layouts/utils/preview-size-picker.d.ts +2 -0
  193. package/build-types/dataviews-layouts/utils/preview-size-picker.d.ts.map +1 -0
  194. package/build-types/field-types/color.d.ts +20 -0
  195. package/build-types/field-types/color.d.ts.map +1 -0
  196. package/build-types/field-types/index.d.ts.map +1 -1
  197. package/build-types/field-types/stories/index.story.d.ts +81 -0
  198. package/build-types/field-types/stories/index.story.d.ts.map +1 -0
  199. package/build-types/field-types/telephone.d.ts +20 -0
  200. package/build-types/field-types/telephone.d.ts.map +1 -0
  201. package/build-types/field-types/url.d.ts +20 -0
  202. package/build-types/field-types/url.d.ts.map +1 -0
  203. package/build-types/normalize-form-fields.d.ts.map +1 -1
  204. package/build-types/test/dataviews-picker.d.ts +2 -0
  205. package/build-types/test/dataviews-picker.d.ts.map +1 -0
  206. package/build-types/types.d.ts +36 -5
  207. package/build-types/types.d.ts.map +1 -1
  208. package/build-types/validation.d.ts.map +1 -1
  209. package/build-wp/index.js +5061 -4013
  210. package/package.json +16 -15
  211. package/src/components/dataform/stories/index.story.tsx +333 -11
  212. package/src/components/dataform-context/index.tsx +1 -0
  213. package/src/components/dataviews/index.tsx +25 -1
  214. package/src/components/dataviews/stories/fixtures.tsx +1 -1
  215. package/src/components/dataviews/stories/index.story.tsx +14 -0
  216. package/src/components/dataviews/style.scss +4 -2
  217. package/src/components/dataviews-context/index.ts +3 -0
  218. package/src/components/dataviews-layout/index.tsx +4 -2
  219. package/src/components/dataviews-picker/footer.tsx +207 -0
  220. package/src/components/dataviews-picker/index.tsx +284 -0
  221. package/src/components/dataviews-picker/stories/index.story.tsx +251 -0
  222. package/src/components/dataviews-picker/style.scss +10 -0
  223. package/src/components/dataviews-selection-checkbox/index.tsx +3 -0
  224. package/src/components/dataviews-view-config/index.tsx +1 -0
  225. package/src/constants.ts +3 -0
  226. package/src/dataform-controls/checkbox.tsx +33 -3
  227. package/src/dataform-controls/color.tsx +139 -0
  228. package/src/dataform-controls/email.tsx +10 -52
  229. package/src/dataform-controls/index.tsx +8 -2
  230. package/src/dataform-controls/telephone.tsx +30 -0
  231. package/src/dataform-controls/text.tsx +2 -57
  232. package/src/dataform-controls/{boolean.tsx → toggle.tsx} +3 -2
  233. package/src/dataform-controls/url.tsx +30 -0
  234. package/src/dataform-controls/utils/validated-text.tsx +96 -0
  235. package/src/dataforms-layouts/card/index.tsx +5 -4
  236. package/src/dataforms-layouts/card/style.scss +7 -0
  237. package/src/dataforms-layouts/data-form-layout.tsx +15 -3
  238. package/src/dataforms-layouts/index.tsx +35 -0
  239. package/src/dataforms-layouts/row/index.tsx +115 -0
  240. package/src/dataforms-layouts/row/style.scss +3 -0
  241. package/src/dataviews-layouts/grid/index.tsx +38 -33
  242. package/src/dataviews-layouts/grid/style.scss +42 -20
  243. package/src/dataviews-layouts/index.ts +16 -2
  244. package/src/dataviews-layouts/picker-grid/index.tsx +490 -0
  245. package/src/dataviews-layouts/picker-grid/style.scss +171 -0
  246. package/src/dataviews-layouts/utils/grid-items.scss +21 -0
  247. package/src/dataviews-layouts/utils/grid-items.tsx +35 -0
  248. package/src/dataviews-layouts/utils/preview-size-picker.tsx +87 -0
  249. package/src/field-types/boolean.tsx +1 -1
  250. package/src/field-types/color.tsx +115 -0
  251. package/src/field-types/index.tsx +15 -0
  252. package/src/field-types/stories/index.story.tsx +719 -0
  253. package/src/field-types/telephone.tsx +71 -0
  254. package/src/field-types/url.tsx +71 -0
  255. package/src/normalize-form-fields.ts +6 -0
  256. package/src/style.scss +4 -0
  257. package/src/test/dataform.tsx +2 -2
  258. package/src/test/dataviews-picker.tsx +478 -0
  259. package/src/test/dataviews.tsx +86 -0
  260. package/src/types.ts +56 -4
  261. package/src/validation.ts +3 -0
  262. package/tsconfig.tsbuildinfo +1 -1
  263. package/build/dataform-controls/boolean.js.map +0 -1
  264. package/build-module/dataform-controls/boolean.js.map +0 -1
  265. package/build-types/components/stories/index.story.d.ts +0 -63
  266. package/build-types/components/stories/index.story.d.ts.map +0 -1
  267. package/build-types/dataform-controls/boolean.d.ts +0 -6
  268. package/build-types/dataform-controls/boolean.d.ts.map +0 -1
  269. package/src/components/stories/index.story.tsx +0 -372
@@ -1,16 +1,8 @@
1
- /**
2
- * WordPress dependencies
3
- */
4
- import { privateApis } from '@wordpress/components';
5
- import { useCallback, useState } from '@wordpress/element';
6
-
7
1
  /**
8
2
  * Internal dependencies
9
3
  */
10
4
  import type { DataFormControlProps } from '../types';
11
- import { unlock } from '../lock-unlock';
12
-
13
- const { ValidatedTextControl } = unlock( privateApis );
5
+ import ValidatedText from './utils/validated-text';
14
6
 
15
7
  export default function Text< Item >( {
16
8
  data,
@@ -18,54 +10,7 @@ export default function Text< Item >( {
18
10
  onChange,
19
11
  hideLabelFromVision,
20
12
  }: DataFormControlProps< Item > ) {
21
- const { id, label, placeholder, description } = field;
22
- const value = field.getValue( { item: data } );
23
- const [ customValidity, setCustomValidity ] =
24
- useState<
25
- React.ComponentProps<
26
- typeof ValidatedTextControl
27
- >[ 'customValidity' ]
28
- >( undefined );
29
-
30
- const onChangeControl = useCallback(
31
- ( newValue: string ) =>
32
- onChange( {
33
- [ id ]: newValue,
34
- } ),
35
- [ id, onChange ]
36
- );
37
-
38
13
  return (
39
- <ValidatedTextControl
40
- required={ !! field.isValid?.required }
41
- onValidate={ ( newValue: any ) => {
42
- const message = field.isValid?.custom?.(
43
- {
44
- ...data,
45
- [ id ]: newValue,
46
- },
47
- field
48
- );
49
-
50
- if ( message ) {
51
- setCustomValidity( {
52
- type: 'invalid',
53
- message,
54
- } );
55
- return;
56
- }
57
-
58
- setCustomValidity( undefined );
59
- } }
60
- customValidity={ customValidity }
61
- label={ label }
62
- placeholder={ placeholder }
63
- value={ value ?? '' }
64
- help={ description }
65
- onChange={ onChangeControl }
66
- __next40pxDefaultSize
67
- __nextHasNoMarginBottom
68
- hideLabelFromVision={ hideLabelFromVision }
69
- />
14
+ <ValidatedText { ...{ data, field, onChange, hideLabelFromVision } } />
70
15
  );
71
16
  }
@@ -12,13 +12,13 @@ import { unlock } from '../lock-unlock';
12
12
 
13
13
  const { ValidatedToggleControl } = unlock( privateApis );
14
14
 
15
- export default function Boolean< Item >( {
15
+ export default function Toggle< Item >( {
16
16
  field,
17
17
  onChange,
18
18
  data,
19
19
  hideLabelFromVision,
20
20
  }: DataFormControlProps< Item > ) {
21
- const { id, getValue, label } = field;
21
+ const { id, getValue, label, description } = field;
22
22
  const [ customValidity, setCustomValidity ] =
23
23
  useState<
24
24
  React.ComponentProps<
@@ -52,6 +52,7 @@ export default function Boolean< Item >( {
52
52
  hidden={ hideLabelFromVision }
53
53
  __nextHasNoMarginBottom
54
54
  label={ label }
55
+ help={ description }
55
56
  checked={ getValue( { item: data } ) }
56
57
  onChange={ () =>
57
58
  onChange( { [ id ]: ! getValue( { item: data } ) } )
@@ -0,0 +1,30 @@
1
+ /**
2
+ * WordPress dependencies
3
+ */
4
+ import { link } from '@wordpress/icons';
5
+
6
+ /**
7
+ * Internal dependencies
8
+ */
9
+ import type { DataFormControlProps } from '../types';
10
+ import ValidatedText from './utils/validated-text';
11
+
12
+ export default function Url< Item >( {
13
+ data,
14
+ field,
15
+ onChange,
16
+ hideLabelFromVision,
17
+ }: DataFormControlProps< Item > ) {
18
+ return (
19
+ <ValidatedText
20
+ { ...{
21
+ data,
22
+ field,
23
+ onChange,
24
+ hideLabelFromVision,
25
+ type: 'url',
26
+ icon: link,
27
+ } }
28
+ />
29
+ );
30
+ }
@@ -0,0 +1,96 @@
1
+ /**
2
+ * WordPress dependencies
3
+ */
4
+ import {
5
+ Icon,
6
+ privateApis,
7
+ __experimentalInputControlPrefixWrapper as InputControlPrefixWrapper,
8
+ } from '@wordpress/components';
9
+ import { useCallback, useState } from '@wordpress/element';
10
+
11
+ /**
12
+ * Internal dependencies
13
+ */
14
+ import type { DataFormControlProps } from '../../types';
15
+ import { unlock } from '../../lock-unlock';
16
+
17
+ const { ValidatedInputControl } = unlock( privateApis );
18
+
19
+ export type DataFormValidatedTextControlProps< Item > =
20
+ DataFormControlProps< Item > & {
21
+ /**
22
+ * The input type of the control.
23
+ */
24
+ type?: 'text' | 'email' | 'tel' | 'url';
25
+ /**
26
+ * Optional icon to display as prefix.
27
+ */
28
+ icon?: React.ComponentType | React.ReactElement;
29
+ };
30
+
31
+ export default function ValidatedText< Item >( {
32
+ data,
33
+ field,
34
+ onChange,
35
+ hideLabelFromVision,
36
+ type,
37
+ icon,
38
+ }: DataFormValidatedTextControlProps< Item > ) {
39
+ const { id, label, placeholder, description } = field;
40
+ const value = field.getValue( { item: data } );
41
+ const [ customValidity, setCustomValidity ] =
42
+ useState<
43
+ React.ComponentProps<
44
+ typeof ValidatedInputControl
45
+ >[ 'customValidity' ]
46
+ >( undefined );
47
+
48
+ const onChangeControl = useCallback(
49
+ ( newValue: string ) =>
50
+ onChange( {
51
+ [ id ]: newValue,
52
+ } ),
53
+ [ id, onChange ]
54
+ );
55
+
56
+ return (
57
+ <ValidatedInputControl
58
+ required={ !! field.isValid?.required }
59
+ onValidate={ ( newValue: any ) => {
60
+ const message = field.isValid?.custom?.(
61
+ {
62
+ ...data,
63
+ [ id ]: newValue,
64
+ },
65
+ field
66
+ );
67
+
68
+ if ( message ) {
69
+ setCustomValidity( {
70
+ type: 'invalid',
71
+ message,
72
+ } );
73
+ return;
74
+ }
75
+
76
+ setCustomValidity( undefined );
77
+ } }
78
+ customValidity={ customValidity }
79
+ label={ label }
80
+ placeholder={ placeholder }
81
+ value={ value ?? '' }
82
+ help={ description }
83
+ onChange={ onChangeControl }
84
+ hideLabelFromVision={ hideLabelFromVision }
85
+ type={ type }
86
+ prefix={
87
+ icon ? (
88
+ <InputControlPrefixWrapper variant="icon">
89
+ <Icon icon={ icon } />
90
+ </InputControlPrefixWrapper>
91
+ ) : undefined
92
+ }
93
+ __next40pxDefaultSize
94
+ />
95
+ );
96
+ }
@@ -1,7 +1,3 @@
1
- /**
2
- * External dependencies
3
- */
4
-
5
1
  /**
6
2
  * WordPress dependencies
7
3
  */
@@ -104,6 +100,11 @@ export default function FormCardField< Item >( {
104
100
  // If it doesn't have a header, keep it open.
105
101
  // Otherwise, the card will not be visible.
106
102
  <CardBody className="dataforms-layouts-card__field-control">
103
+ { field.description && (
104
+ <div className="dataforms-layouts-card__field-description">
105
+ { field.description }
106
+ </div>
107
+ ) }
107
108
  <DataFormLayout
108
109
  data={ data }
109
110
  form={ form }
@@ -1,3 +1,10 @@
1
1
  .dataforms-layouts-card__field {
2
2
  width: 100%;
3
3
  }
4
+
5
+ .dataforms-layouts-card__field-description {
6
+ color: $gray-700;
7
+ display: block;
8
+ font-size: $font-size-medium;
9
+ margin-bottom: $grid-unit-20;
10
+ }
@@ -11,13 +11,18 @@ import type { Form, FormField, SimpleFormField } from '../types';
11
11
  import { getFormFieldLayout } from './index';
12
12
  import DataFormContext from '../components/dataform-context';
13
13
  import { isCombinedField } from './is-combined-field';
14
- import normalizeFormFields from '../normalize-form-fields';
14
+ import normalizeFormFields, { normalizeLayout } from '../normalize-form-fields';
15
+
16
+ const DEFAULT_WRAPPER = ( { children }: { children: React.ReactNode } ) => (
17
+ <VStack spacing={ 4 }>{ children }</VStack>
18
+ );
15
19
 
16
20
  export function DataFormLayout< Item >( {
17
21
  data,
18
22
  form,
19
23
  onChange,
20
24
  children,
25
+ as,
21
26
  }: {
22
27
  data: Item;
23
28
  form: Form;
@@ -31,6 +36,7 @@ export function DataFormLayout< Item >( {
31
36
  } ) => React.JSX.Element | null,
32
37
  field: FormField
33
38
  ) => React.JSX.Element;
39
+ as?: React.ComponentType< { children: React.ReactNode } >;
34
40
  } ) {
35
41
  const { fields: fieldDefinitions } = useContext( DataFormContext );
36
42
 
@@ -47,8 +53,14 @@ export function DataFormLayout< Item >( {
47
53
  [ form ]
48
54
  );
49
55
 
56
+ const normalizedFormLayout = normalizeLayout( form.layout );
57
+ const Wrapper =
58
+ as ??
59
+ getFormFieldLayout( normalizedFormLayout.type )?.wrapper ??
60
+ DEFAULT_WRAPPER;
61
+
50
62
  return (
51
- <VStack spacing={ form.layout?.type === 'panel' ? 2 : 4 }>
63
+ <Wrapper layout={ normalizedFormLayout }>
52
64
  { normalizedFormFields.map( ( formField ) => {
53
65
  const FieldLayout = getFormFieldLayout( formField.layout.type )
54
66
  ?.component;
@@ -82,6 +94,6 @@ export function DataFormLayout< Item >( {
82
94
  />
83
95
  );
84
96
  } ) }
85
- </VStack>
97
+ </Wrapper>
86
98
  );
87
99
  }
@@ -1,9 +1,19 @@
1
+ /**
2
+ * WordPress dependencies
3
+ */
4
+ import {
5
+ __experimentalVStack as VStack,
6
+ __experimentalHStack as HStack,
7
+ } from '@wordpress/components';
8
+
1
9
  /**
2
10
  * Internal dependencies
3
11
  */
12
+ import type { Layout, RowLayout } from '../types';
4
13
  import FormRegularField from './regular';
5
14
  import FormPanelField from './panel';
6
15
  import FormCardField from './card';
16
+ import FormRowField from './row';
7
17
 
8
18
  const FORM_FIELD_LAYOUTS = [
9
19
  {
@@ -13,11 +23,36 @@ const FORM_FIELD_LAYOUTS = [
13
23
  {
14
24
  type: 'panel',
15
25
  component: FormPanelField,
26
+ wrapper: ( { children }: { children: React.ReactNode } ) => (
27
+ <VStack spacing={ 2 }>{ children }</VStack>
28
+ ),
16
29
  },
17
30
  {
18
31
  type: 'card',
19
32
  component: FormCardField,
20
33
  },
34
+ {
35
+ type: 'row',
36
+ component: FormRowField,
37
+ wrapper: ( {
38
+ children,
39
+ layout,
40
+ }: {
41
+ children: React.ReactNode;
42
+ layout: Layout;
43
+ } ) => (
44
+ <VStack spacing={ 4 }>
45
+ <div className="dataforms-layouts-row__field">
46
+ <HStack
47
+ spacing={ 4 }
48
+ alignment={ ( layout as RowLayout ).alignment }
49
+ >
50
+ { children }
51
+ </HStack>
52
+ </div>
53
+ </VStack>
54
+ ),
55
+ },
21
56
  ];
22
57
 
23
58
  export function getFormFieldLayout( type: string ) {
@@ -0,0 +1,115 @@
1
+ /**
2
+ * WordPress dependencies
3
+ */
4
+ import {
5
+ __experimentalHStack as HStack,
6
+ __experimentalSpacer as Spacer,
7
+ __experimentalVStack as VStack,
8
+ __experimentalHeading as Heading,
9
+ } from '@wordpress/components';
10
+ import { useContext } from '@wordpress/element';
11
+
12
+ /**
13
+ * Internal dependencies
14
+ */
15
+ import type { FieldLayoutProps, Form, NormalizedRowLayout } from '../../types';
16
+ import DataFormContext from '../../components/dataform-context';
17
+ import { DataFormLayout } from '../data-form-layout';
18
+ import { isCombinedField } from '../is-combined-field';
19
+ import { normalizeLayout } from '../../normalize-form-fields';
20
+ import { getFormFieldLayout } from '..';
21
+
22
+ function Header( { title }: { title: string } ) {
23
+ return (
24
+ <VStack className="dataforms-layouts-row__header" spacing={ 4 }>
25
+ <HStack alignment="center">
26
+ <Heading level={ 2 } size={ 13 }>
27
+ { title }
28
+ </Heading>
29
+ <Spacer />
30
+ </HStack>
31
+ </VStack>
32
+ );
33
+ }
34
+
35
+ const EMPTY_WRAPPER = ( { children }: { children: React.ReactNode } ) => (
36
+ <>{ children }</>
37
+ );
38
+
39
+ export default function FormRowField< Item >( {
40
+ data,
41
+ field,
42
+ onChange,
43
+ hideLabelFromVision,
44
+ }: FieldLayoutProps< Item > ) {
45
+ const { fields } = useContext( DataFormContext );
46
+
47
+ const layout = normalizeLayout( {
48
+ ...field.layout,
49
+ type: 'row',
50
+ } ) as NormalizedRowLayout;
51
+
52
+ if ( isCombinedField( field ) ) {
53
+ const form: Form = {
54
+ fields: field.children.map( ( child ) => {
55
+ if ( typeof child === 'string' ) {
56
+ return { id: child };
57
+ }
58
+ return child;
59
+ } ),
60
+ };
61
+
62
+ return (
63
+ <div className="dataforms-layouts-row__field">
64
+ { ! hideLabelFromVision && field.label && (
65
+ <Header title={ field.label } />
66
+ ) }
67
+ <HStack alignment={ layout.alignment } spacing={ 4 }>
68
+ <DataFormLayout
69
+ data={ data }
70
+ form={ form }
71
+ onChange={ onChange }
72
+ as={ EMPTY_WRAPPER }
73
+ >
74
+ { ( FieldLayout, nestedField ) => (
75
+ <div
76
+ key={ nestedField.id }
77
+ className="dataforms-layouts-row__field-control"
78
+ >
79
+ <FieldLayout
80
+ data={ data }
81
+ field={ nestedField }
82
+ onChange={ onChange }
83
+ hideLabelFromVision={ hideLabelFromVision }
84
+ />
85
+ </div>
86
+ ) }
87
+ </DataFormLayout>
88
+ </HStack>
89
+ </div>
90
+ );
91
+ }
92
+
93
+ const fieldDefinition = fields.find( ( f ) => f.id === field.id );
94
+
95
+ if ( ! fieldDefinition || ! fieldDefinition.Edit ) {
96
+ return null;
97
+ }
98
+
99
+ const RegularLayout = getFormFieldLayout( 'regular' )?.component;
100
+ if ( ! RegularLayout ) {
101
+ return null;
102
+ }
103
+
104
+ return (
105
+ <>
106
+ <div className="dataforms-layouts-row__field-control">
107
+ <RegularLayout
108
+ data={ data }
109
+ field={ fieldDefinition }
110
+ onChange={ onChange }
111
+ />
112
+ </div>
113
+ </>
114
+ );
115
+ }
@@ -0,0 +1,3 @@
1
+ .dataforms-layouts-row__field-control {
2
+ width: 100%;
3
+ }
@@ -40,6 +40,7 @@ import type {
40
40
  } from '../../types';
41
41
  import type { SetSelection } from '../../private-types';
42
42
  import { ItemClickWrapper } from '../utils/item-click-wrapper';
43
+ import { GridItems } from '../utils/grid-items';
43
44
  const { Badge } = unlock( componentsPrivateApis );
44
45
 
45
46
  interface GridItemProps< Item > {
@@ -108,6 +109,7 @@ function GridItem< Item >( {
108
109
  showTitle && titleField?.render ? (
109
110
  <titleField.render item={ item } field={ titleField } />
110
111
  ) : null;
112
+ const shouldRenderMedia = showMedia && renderedMediaField;
111
113
 
112
114
  let mediaA11yProps;
113
115
  let titleA11yProps;
@@ -154,7 +156,7 @@ function GridItem< Item >( {
154
156
  }
155
157
  aria-posinset={ posinset }
156
158
  >
157
- { showMedia && renderedMediaField && (
159
+ { shouldRenderMedia && (
158
160
  <ItemClickWrapper
159
161
  item={ item }
160
162
  isItemClickable={ isItemClickable }
@@ -166,7 +168,7 @@ function GridItem< Item >( {
166
168
  { renderedMediaField }
167
169
  </ItemClickWrapper>
168
170
  ) }
169
- { hasBulkActions && showMedia && renderedMediaField && (
171
+ { hasBulkActions && shouldRenderMedia && (
170
172
  <DataViewsSelectionCheckbox
171
173
  item={ item }
172
174
  selection={ selection }
@@ -176,24 +178,35 @@ function GridItem< Item >( {
176
178
  disabled={ ! hasBulkAction }
177
179
  />
178
180
  ) }
179
- <HStack
180
- justify="space-between"
181
- className="dataviews-view-grid__title-actions"
182
- >
183
- <ItemClickWrapper
184
- item={ item }
185
- isItemClickable={ isItemClickable }
186
- onClickItem={ onClickItem }
187
- renderItemLink={ renderItemLink }
188
- className="dataviews-view-grid__title-field dataviews-title-field"
189
- { ...titleA11yProps }
190
- >
191
- { renderedTitleField }
192
- </ItemClickWrapper>
193
- { !! actions?.length && (
181
+ { ! showTitle && shouldRenderMedia && !! actions?.length && (
182
+ <div className="dataviews-view-grid__media-actions">
194
183
  <ItemActions item={ item } actions={ actions } isCompact />
195
- ) }
196
- </HStack>
184
+ </div>
185
+ ) }
186
+ { showTitle && (
187
+ <HStack
188
+ justify="space-between"
189
+ className="dataviews-view-grid__title-actions"
190
+ >
191
+ <ItemClickWrapper
192
+ item={ item }
193
+ isItemClickable={ isItemClickable }
194
+ onClickItem={ onClickItem }
195
+ renderItemLink={ renderItemLink }
196
+ className="dataviews-view-grid__title-field dataviews-title-field"
197
+ { ...titleA11yProps }
198
+ >
199
+ { renderedTitleField }
200
+ </ItemClickWrapper>
201
+ { !! actions?.length && (
202
+ <ItemActions
203
+ item={ item }
204
+ actions={ actions }
205
+ isCompact
206
+ />
207
+ ) }
208
+ </HStack>
209
+ ) }
197
210
  <VStack spacing={ 1 }>
198
211
  { showDescription && descriptionField?.render && (
199
212
  <descriptionField.render
@@ -357,16 +370,12 @@ function ViewGrid< Item >( {
357
370
  groupName
358
371
  ) }
359
372
  </h3>
360
- <div
373
+ <GridItems
361
374
  className={ clsx(
362
375
  'dataviews-view-grid',
363
376
  className
364
377
  ) }
365
- style={ {
366
- gridTemplateColumns:
367
- usedPreviewSize &&
368
- `repeat(auto-fill, minmax(${ usedPreviewSize }px, 1fr))`,
369
- } }
378
+ previewSize={ usedPreviewSize }
370
379
  aria-busy={ isLoading }
371
380
  ref={ resizeObserverRef }
372
381
  >
@@ -407,7 +416,7 @@ function ViewGrid< Item >( {
407
416
  />
408
417
  );
409
418
  } ) }
410
- </div>
419
+ </GridItems>
411
420
  </VStack>
412
421
  )
413
422
  ) }
@@ -418,13 +427,9 @@ function ViewGrid< Item >( {
418
427
  {
419
428
  // Render a single grid with all data.
420
429
  hasData && ! dataByGroup && (
421
- <div
430
+ <GridItems
422
431
  className={ clsx( 'dataviews-view-grid', className ) }
423
- style={ {
424
- gridTemplateColumns:
425
- usedPreviewSize &&
426
- `repeat(auto-fill, minmax(${ usedPreviewSize }px, 1fr))`,
427
- } }
432
+ previewSize={ usedPreviewSize }
428
433
  aria-busy={ isLoading }
429
434
  ref={ resizeObserverRef }
430
435
  role={ isInfiniteScroll ? 'feed' : undefined }
@@ -457,7 +462,7 @@ function ViewGrid< Item >( {
457
462
  />
458
463
  );
459
464
  } ) }
460
- </div>
465
+ </GridItems>
461
466
  )
462
467
  }
463
468
  {