@wordpress/edit-site 5.12.6 → 5.12.8

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 (209) hide show
  1. package/build/components/block-editor/editor-canvas.js +1 -1
  2. package/build/components/block-editor/editor-canvas.js.map +1 -1
  3. package/build/components/block-editor/use-site-editor-settings.js +10 -5
  4. package/build/components/block-editor/use-site-editor-settings.js.map +1 -1
  5. package/build/components/create-pattern-modal/index.js +8 -4
  6. package/build/components/create-pattern-modal/index.js.map +1 -1
  7. package/build/components/global-styles/palette.js +1 -1
  8. package/build/components/global-styles/palette.js.map +1 -1
  9. package/build/components/header-edit-mode/index.js +6 -2
  10. package/build/components/header-edit-mode/index.js.map +1 -1
  11. package/build/components/layout/index.js +1 -1
  12. package/build/components/layout/index.js.map +1 -1
  13. package/build/components/page/header.js +1 -1
  14. package/build/components/page/header.js.map +1 -1
  15. package/build/components/page-content-focus-manager/disable-non-page-content-blocks.js +5 -5
  16. package/build/components/page-content-focus-manager/disable-non-page-content-blocks.js.map +1 -1
  17. package/build/components/page-patterns/duplicate-menu-item.js +163 -0
  18. package/build/components/page-patterns/duplicate-menu-item.js.map +1 -0
  19. package/build/components/page-patterns/grid-item.js +84 -60
  20. package/build/components/page-patterns/grid-item.js.map +1 -1
  21. package/build/components/page-patterns/grid.js +21 -13
  22. package/build/components/page-patterns/grid.js.map +1 -1
  23. package/build/components/page-patterns/header.js +69 -0
  24. package/build/components/page-patterns/header.js.map +1 -0
  25. package/build/components/page-patterns/index.js +3 -1
  26. package/build/components/page-patterns/index.js.map +1 -1
  27. package/build/components/page-patterns/patterns-list.js +67 -27
  28. package/build/components/page-patterns/patterns-list.js.map +1 -1
  29. package/build/components/page-patterns/rename-menu-item.js +109 -0
  30. package/build/components/page-patterns/rename-menu-item.js.map +1 -0
  31. package/build/components/page-patterns/use-patterns.js +99 -126
  32. package/build/components/page-patterns/use-patterns.js.map +1 -1
  33. package/build/components/page-template-parts/index.js +1 -0
  34. package/build/components/page-template-parts/index.js.map +1 -1
  35. package/build/components/page-templates/index.js +1 -0
  36. package/build/components/page-templates/index.js.map +1 -1
  37. package/build/components/sidebar-edit-mode/page-panels/page-content.js +4 -3
  38. package/build/components/sidebar-edit-mode/page-panels/page-content.js.map +1 -1
  39. package/build/components/sidebar-navigation-screen/index.js +1 -1
  40. package/build/components/sidebar-navigation-screen/index.js.map +1 -1
  41. package/build/components/sidebar-navigation-screen-global-styles/index.js +57 -17
  42. package/build/components/sidebar-navigation-screen-global-styles/index.js.map +1 -1
  43. package/build/components/sidebar-navigation-screen-main/index.js +4 -2
  44. package/build/components/sidebar-navigation-screen-main/index.js.map +1 -1
  45. package/build/components/sidebar-navigation-screen-main/template-part-hint.js +45 -0
  46. package/build/components/sidebar-navigation-screen-main/template-part-hint.js.map +1 -0
  47. package/build/components/sidebar-navigation-screen-navigation-menu/edit-button.js +10 -11
  48. package/build/components/sidebar-navigation-screen-navigation-menu/edit-button.js.map +1 -1
  49. package/build/components/sidebar-navigation-screen-navigation-menu/single-navigation-menu.js +6 -2
  50. package/build/components/sidebar-navigation-screen-navigation-menu/single-navigation-menu.js.map +1 -1
  51. package/build/components/sidebar-navigation-screen-page/status-label.js +2 -35
  52. package/build/components/sidebar-navigation-screen-page/status-label.js.map +1 -1
  53. package/build/components/sidebar-navigation-screen-pattern/use-pattern-details.js +3 -3
  54. package/build/components/sidebar-navigation-screen-pattern/use-pattern-details.js.map +1 -1
  55. package/build/components/sidebar-navigation-screen-patterns/index.js +68 -43
  56. package/build/components/sidebar-navigation-screen-patterns/index.js.map +1 -1
  57. package/build/components/sidebar-navigation-screen-patterns/use-my-patterns.js +9 -5
  58. package/build/components/sidebar-navigation-screen-patterns/use-my-patterns.js.map +1 -1
  59. package/build/components/sidebar-navigation-screen-patterns/use-template-part-areas.js +20 -9
  60. package/build/components/sidebar-navigation-screen-patterns/use-template-part-areas.js.map +1 -1
  61. package/build/components/site-hub/index.js +2 -2
  62. package/build/components/site-hub/index.js.map +1 -1
  63. package/build/components/template-actions/index.js +25 -7
  64. package/build/components/template-actions/index.js.map +1 -1
  65. package/build/components/template-actions/rename-menu-item.js +9 -6
  66. package/build/components/template-actions/rename-menu-item.js.map +1 -1
  67. package/build/components/welcome-guide/page.js +2 -2
  68. package/build/components/welcome-guide/page.js.map +1 -1
  69. package/build/components/welcome-guide/template.js +2 -2
  70. package/build/components/welcome-guide/template.js.map +1 -1
  71. package/build/hooks/commands/use-edit-mode-commands.js +1 -2
  72. package/build/hooks/commands/use-edit-mode-commands.js.map +1 -1
  73. package/build/hooks/push-changes-to-global-styles/index.js +3 -1
  74. package/build/hooks/push-changes-to-global-styles/index.js.map +1 -1
  75. package/build/store/private-actions.js +7 -1
  76. package/build/store/private-actions.js.map +1 -1
  77. package/build/utils/use-activate-theme.js +1 -1
  78. package/build/utils/use-activate-theme.js.map +1 -1
  79. package/build-module/components/block-editor/editor-canvas.js +1 -1
  80. package/build-module/components/block-editor/editor-canvas.js.map +1 -1
  81. package/build-module/components/block-editor/use-site-editor-settings.js +10 -5
  82. package/build-module/components/block-editor/use-site-editor-settings.js.map +1 -1
  83. package/build-module/components/create-pattern-modal/index.js +7 -4
  84. package/build-module/components/create-pattern-modal/index.js.map +1 -1
  85. package/build-module/components/global-styles/palette.js +1 -1
  86. package/build-module/components/global-styles/palette.js.map +1 -1
  87. package/build-module/components/header-edit-mode/index.js +6 -2
  88. package/build-module/components/header-edit-mode/index.js.map +1 -1
  89. package/build-module/components/layout/index.js +1 -1
  90. package/build-module/components/layout/index.js.map +1 -1
  91. package/build-module/components/page/header.js +1 -1
  92. package/build-module/components/page/header.js.map +1 -1
  93. package/build-module/components/page-content-focus-manager/disable-non-page-content-blocks.js +5 -3
  94. package/build-module/components/page-content-focus-manager/disable-non-page-content-blocks.js.map +1 -1
  95. package/build-module/components/page-patterns/duplicate-menu-item.js +147 -0
  96. package/build-module/components/page-patterns/duplicate-menu-item.js.map +1 -0
  97. package/build-module/components/page-patterns/grid-item.js +85 -66
  98. package/build-module/components/page-patterns/grid-item.js.map +1 -1
  99. package/build-module/components/page-patterns/grid.js +22 -15
  100. package/build-module/components/page-patterns/grid.js.map +1 -1
  101. package/build-module/components/page-patterns/header.js +54 -0
  102. package/build-module/components/page-patterns/header.js.map +1 -0
  103. package/build-module/components/page-patterns/index.js +3 -1
  104. package/build-module/components/page-patterns/index.js.map +1 -1
  105. package/build-module/components/page-patterns/patterns-list.js +70 -31
  106. package/build-module/components/page-patterns/patterns-list.js.map +1 -1
  107. package/build-module/components/page-patterns/rename-menu-item.js +97 -0
  108. package/build-module/components/page-patterns/rename-menu-item.js.map +1 -0
  109. package/build-module/components/page-patterns/use-patterns.js +100 -127
  110. package/build-module/components/page-patterns/use-patterns.js.map +1 -1
  111. package/build-module/components/page-template-parts/index.js +1 -0
  112. package/build-module/components/page-template-parts/index.js.map +1 -1
  113. package/build-module/components/page-templates/index.js +1 -0
  114. package/build-module/components/page-templates/index.js.map +1 -1
  115. package/build-module/components/sidebar-edit-mode/page-panels/page-content.js +5 -2
  116. package/build-module/components/sidebar-edit-mode/page-panels/page-content.js.map +1 -1
  117. package/build-module/components/sidebar-navigation-screen/index.js +1 -1
  118. package/build-module/components/sidebar-navigation-screen/index.js.map +1 -1
  119. package/build-module/components/sidebar-navigation-screen-global-styles/index.js +57 -17
  120. package/build-module/components/sidebar-navigation-screen-global-styles/index.js.map +1 -1
  121. package/build-module/components/sidebar-navigation-screen-main/index.js +4 -3
  122. package/build-module/components/sidebar-navigation-screen-main/index.js.map +1 -1
  123. package/build-module/components/sidebar-navigation-screen-main/template-part-hint.js +33 -0
  124. package/build-module/components/sidebar-navigation-screen-main/template-part-hint.js.map +1 -0
  125. package/build-module/components/sidebar-navigation-screen-navigation-menu/edit-button.js +10 -9
  126. package/build-module/components/sidebar-navigation-screen-navigation-menu/edit-button.js.map +1 -1
  127. package/build-module/components/sidebar-navigation-screen-navigation-menu/single-navigation-menu.js +6 -3
  128. package/build-module/components/sidebar-navigation-screen-navigation-menu/single-navigation-menu.js.map +1 -1
  129. package/build-module/components/sidebar-navigation-screen-page/status-label.js +2 -33
  130. package/build-module/components/sidebar-navigation-screen-page/status-label.js.map +1 -1
  131. package/build-module/components/sidebar-navigation-screen-pattern/use-pattern-details.js +3 -3
  132. package/build-module/components/sidebar-navigation-screen-pattern/use-pattern-details.js.map +1 -1
  133. package/build-module/components/sidebar-navigation-screen-patterns/index.js +71 -44
  134. package/build-module/components/sidebar-navigation-screen-patterns/index.js.map +1 -1
  135. package/build-module/components/sidebar-navigation-screen-patterns/use-my-patterns.js +9 -5
  136. package/build-module/components/sidebar-navigation-screen-patterns/use-my-patterns.js.map +1 -1
  137. package/build-module/components/sidebar-navigation-screen-patterns/use-template-part-areas.js +18 -9
  138. package/build-module/components/sidebar-navigation-screen-patterns/use-template-part-areas.js.map +1 -1
  139. package/build-module/components/site-hub/index.js +2 -2
  140. package/build-module/components/site-hub/index.js.map +1 -1
  141. package/build-module/components/template-actions/index.js +26 -8
  142. package/build-module/components/template-actions/index.js.map +1 -1
  143. package/build-module/components/template-actions/rename-menu-item.js +8 -6
  144. package/build-module/components/template-actions/rename-menu-item.js.map +1 -1
  145. package/build-module/components/welcome-guide/page.js +2 -2
  146. package/build-module/components/welcome-guide/page.js.map +1 -1
  147. package/build-module/components/welcome-guide/template.js +2 -2
  148. package/build-module/components/welcome-guide/template.js.map +1 -1
  149. package/build-module/hooks/commands/use-edit-mode-commands.js +1 -2
  150. package/build-module/hooks/commands/use-edit-mode-commands.js.map +1 -1
  151. package/build-module/hooks/push-changes-to-global-styles/index.js +4 -2
  152. package/build-module/hooks/push-changes-to-global-styles/index.js.map +1 -1
  153. package/build-module/store/private-actions.js +7 -1
  154. package/build-module/store/private-actions.js.map +1 -1
  155. package/build-module/utils/use-activate-theme.js +1 -1
  156. package/build-module/utils/use-activate-theme.js.map +1 -1
  157. package/build-style/style-rtl.css +149 -50
  158. package/build-style/style.css +149 -50
  159. package/package.json +19 -19
  160. package/src/components/block-editor/editor-canvas.js +1 -1
  161. package/src/components/block-editor/use-site-editor-settings.js +8 -4
  162. package/src/components/create-pattern-modal/index.js +6 -3
  163. package/src/components/global-styles/palette.js +10 -9
  164. package/src/components/header-edit-mode/document-actions/style.scss +12 -0
  165. package/src/components/header-edit-mode/index.js +17 -9
  166. package/src/components/layout/index.js +1 -1
  167. package/src/components/layout/style.scss +0 -11
  168. package/src/components/page/header.js +1 -1
  169. package/src/components/page-content-focus-manager/disable-non-page-content-blocks.js +12 -3
  170. package/src/components/page-patterns/duplicate-menu-item.js +196 -0
  171. package/src/components/page-patterns/grid-item.js +187 -132
  172. package/src/components/page-patterns/grid.js +35 -22
  173. package/src/components/page-patterns/header.js +69 -0
  174. package/src/components/page-patterns/index.js +6 -1
  175. package/src/components/page-patterns/patterns-list.js +89 -47
  176. package/src/components/page-patterns/rename-menu-item.js +115 -0
  177. package/src/components/page-patterns/style.scss +86 -26
  178. package/src/components/page-patterns/use-patterns.js +99 -176
  179. package/src/components/page-template-parts/index.js +1 -1
  180. package/src/components/page-templates/index.js +1 -1
  181. package/src/components/sidebar-edit-mode/page-panels/page-content.js +7 -5
  182. package/src/components/sidebar-navigation-screen/index.js +1 -1
  183. package/src/components/sidebar-navigation-screen/style.scss +19 -1
  184. package/src/components/sidebar-navigation-screen-global-styles/index.js +56 -39
  185. package/src/components/sidebar-navigation-screen-main/index.js +44 -40
  186. package/src/components/sidebar-navigation-screen-main/template-part-hint.js +36 -0
  187. package/src/components/sidebar-navigation-screen-navigation-menu/edit-button.js +8 -11
  188. package/src/components/sidebar-navigation-screen-navigation-menu/single-navigation-menu.js +10 -6
  189. package/src/components/sidebar-navigation-screen-page/status-label.js +2 -36
  190. package/src/components/sidebar-navigation-screen-pattern/use-pattern-details.js +3 -3
  191. package/src/components/sidebar-navigation-screen-patterns/index.js +79 -75
  192. package/src/components/sidebar-navigation-screen-patterns/style.scss +23 -1
  193. package/src/components/sidebar-navigation-screen-patterns/use-my-patterns.js +7 -6
  194. package/src/components/sidebar-navigation-screen-patterns/use-template-part-areas.js +31 -9
  195. package/src/components/site-hub/index.js +2 -2
  196. package/src/components/template-actions/index.js +40 -9
  197. package/src/components/template-actions/rename-menu-item.js +8 -6
  198. package/src/components/welcome-guide/page.js +2 -2
  199. package/src/components/welcome-guide/template.js +2 -2
  200. package/src/hooks/commands/use-edit-mode-commands.js +0 -1
  201. package/src/hooks/push-changes-to-global-styles/index.js +8 -1
  202. package/src/store/private-actions.js +5 -1
  203. package/src/style.scss +10 -12
  204. package/src/utils/use-activate-theme.js +1 -1
  205. package/build/components/page-content-focus-manager/constants.js +0 -9
  206. package/build/components/page-content-focus-manager/constants.js.map +0 -1
  207. package/build-module/components/page-content-focus-manager/constants.js +0 -2
  208. package/build-module/components/page-content-focus-manager/constants.js.map +0 -1
  209. package/src/components/page-content-focus-manager/constants.js +0 -5
@@ -8,87 +8,103 @@ import classnames from 'classnames';
8
8
  */
9
9
  import { BlockPreview } from '@wordpress/block-editor';
10
10
  import {
11
+ Button,
11
12
  __experimentalConfirmDialog as ConfirmDialog,
12
13
  DropdownMenu,
13
14
  MenuGroup,
14
15
  MenuItem,
15
16
  __experimentalHeading as Heading,
16
17
  __experimentalHStack as HStack,
17
- __unstableCompositeItem as CompositeItem,
18
18
  Tooltip,
19
19
  Flex,
20
20
  } from '@wordpress/components';
21
21
  import { useDispatch } from '@wordpress/data';
22
- import { useState, useId } from '@wordpress/element';
22
+ import { useState, useId, memo } from '@wordpress/element';
23
23
  import { __, sprintf } from '@wordpress/i18n';
24
24
  import {
25
25
  Icon,
26
26
  header,
27
27
  footer,
28
- symbolFilled,
28
+ symbolFilled as uncategorized,
29
+ symbol,
29
30
  moreHorizontal,
30
31
  lockSmall,
31
32
  } from '@wordpress/icons';
32
33
  import { store as noticesStore } from '@wordpress/notices';
33
34
  import { store as reusableBlocksStore } from '@wordpress/reusable-blocks';
34
- import { DELETE, BACKSPACE } from '@wordpress/keycodes';
35
35
 
36
36
  /**
37
37
  * Internal dependencies
38
38
  */
39
- import { PATTERNS, USER_PATTERNS } from './utils';
39
+ import RenameMenuItem from './rename-menu-item';
40
+ import DuplicateMenuItem from './duplicate-menu-item';
41
+ import { PATTERNS, TEMPLATE_PARTS, USER_PATTERNS, SYNC_TYPES } from './utils';
42
+ import { store as editSiteStore } from '../../store';
40
43
  import { useLink } from '../routes/link';
41
44
 
42
- const THEME_PATTERN_TOOLTIP = __( 'Theme patterns cannot be edited.' );
45
+ const templatePartIcons = { header, footer, uncategorized };
43
46
 
44
- export default function GridItem( { categoryId, composite, icon, item } ) {
47
+ function GridItem( { categoryId, item, ...props } ) {
45
48
  const descriptionId = useId();
46
49
  const [ isDeleteDialogOpen, setIsDeleteDialogOpen ] = useState( false );
47
50
 
51
+ const { removeTemplate } = useDispatch( editSiteStore );
48
52
  const { __experimentalDeleteReusableBlock } =
49
53
  useDispatch( reusableBlocksStore );
50
54
  const { createErrorNotice, createSuccessNotice } =
51
55
  useDispatch( noticesStore );
52
56
 
57
+ const isUserPattern = item.type === USER_PATTERNS;
58
+ const isNonUserPattern = item.type === PATTERNS;
59
+ const isTemplatePart = item.type === TEMPLATE_PARTS;
60
+
53
61
  const { onClick } = useLink( {
54
62
  postType: item.type,
55
- postId: item.type === USER_PATTERNS ? item.id : item.name,
63
+ postId: isUserPattern ? item.id : item.name,
56
64
  categoryId,
57
65
  categoryType: item.type,
58
66
  } );
59
67
 
60
- const onKeyDown = ( event ) => {
61
- if ( DELETE === event.keyCode || BACKSPACE === event.keyCode ) {
62
- setIsDeleteDialogOpen( true );
63
- }
64
- };
65
-
66
68
  const isEmpty = ! item.blocks?.length;
67
69
  const patternClassNames = classnames( 'edit-site-patterns__pattern', {
68
70
  'is-placeholder': isEmpty,
69
71
  } );
70
72
  const previewClassNames = classnames( 'edit-site-patterns__preview', {
71
- 'is-inactive': item.type === PATTERNS,
73
+ 'is-inactive': isNonUserPattern,
72
74
  } );
73
75
 
74
76
  const deletePattern = async () => {
75
77
  try {
76
78
  await __experimentalDeleteReusableBlock( item.id );
77
- createSuccessNotice( __( 'Pattern successfully deleted.' ), {
78
- type: 'snackbar',
79
- } );
79
+ createSuccessNotice(
80
+ sprintf(
81
+ // translators: %s: The pattern's title e.g. 'Call to action'.
82
+ __( '"%s" deleted.' ),
83
+ item.title
84
+ ),
85
+ { type: 'snackbar', id: 'edit-site-patterns-success' }
86
+ );
80
87
  } catch ( error ) {
81
88
  const errorMessage =
82
89
  error.message && error.code !== 'unknown_error'
83
90
  ? error.message
84
91
  : __( 'An error occurred while deleting the pattern.' );
85
- createErrorNotice( errorMessage, { type: 'snackbar' } );
92
+ createErrorNotice( errorMessage, {
93
+ type: 'snackbar',
94
+ id: 'edit-site-patterns-error',
95
+ } );
86
96
  }
87
97
  };
98
+ const deleteItem = () =>
99
+ isTemplatePart ? removeTemplate( item ) : deletePattern();
88
100
 
89
- const isUserPattern = item.type === USER_PATTERNS;
101
+ // Only custom patterns or custom template parts can be renamed or deleted.
102
+ const isCustomPattern =
103
+ isUserPattern || ( isTemplatePart && item.isCustom );
104
+ const hasThemeFile = isTemplatePart && item.templatePart.has_theme_file;
90
105
  const ariaDescriptions = [];
91
- if ( isUserPattern ) {
106
+
107
+ if ( isCustomPattern ) {
92
108
  // User patterns don't have descriptions, but can be edited and deleted, so include some help text.
93
109
  ariaDescriptions.push(
94
110
  __( 'Press Enter to edit, or Delete to delete the pattern.' )
@@ -96,134 +112,173 @@ export default function GridItem( { categoryId, composite, icon, item } ) {
96
112
  } else if ( item.description ) {
97
113
  ariaDescriptions.push( item.description );
98
114
  }
99
- if ( item.type === PATTERNS ) {
100
- ariaDescriptions.push( THEME_PATTERN_TOOLTIP );
101
- }
102
115
 
103
- let itemIcon = icon;
104
- if ( categoryId === 'header' ) {
105
- itemIcon = header;
106
- } else if ( categoryId === 'footer' ) {
107
- itemIcon = footer;
108
- } else if ( categoryId === 'uncategorized' ) {
109
- itemIcon = symbolFilled;
116
+ if ( isNonUserPattern ) {
117
+ ariaDescriptions.push( __( 'Theme patterns cannot be edited.' ) );
110
118
  }
111
119
 
120
+ const itemIcon =
121
+ templatePartIcons[ categoryId ] ||
122
+ ( item.syncStatus === SYNC_TYPES.full ? symbol : undefined );
123
+
124
+ const confirmButtonText = hasThemeFile ? __( 'Clear' ) : __( 'Delete' );
125
+ const confirmPrompt = hasThemeFile
126
+ ? __( 'Are you sure you want to clear these customizations?' )
127
+ : sprintf(
128
+ // translators: %s: The pattern or template part's title e.g. 'Call to action'.
129
+ __( 'Are you sure you want to delete "%s"?' ),
130
+ item.title
131
+ );
132
+
112
133
  return (
113
- <>
114
- <div className={ patternClassNames }>
115
- <CompositeItem
116
- className={ previewClassNames }
117
- role="option"
118
- as="div"
119
- { ...composite }
120
- onClick={ item.type !== PATTERNS ? onClick : undefined }
121
- onKeyDown={ isUserPattern ? onKeyDown : undefined }
122
- aria-label={ item.title }
123
- aria-describedby={
124
- ariaDescriptions.length
125
- ? ariaDescriptions.join( ' ' )
126
- : undefined
127
- }
134
+ <li className={ patternClassNames }>
135
+ <button
136
+ className={ previewClassNames }
137
+ // Even though still incomplete, passing ids helps performance.
138
+ // @see https://reakit.io/docs/composite/#performance.
139
+ id={ `edit-site-patterns-${ item.name }` }
140
+ { ...props }
141
+ onClick={ item.type !== PATTERNS ? onClick : undefined }
142
+ aria-disabled={ item.type !== PATTERNS ? 'false' : 'true' }
143
+ aria-label={ item.title }
144
+ aria-describedby={
145
+ ariaDescriptions.length
146
+ ? ariaDescriptions
147
+ .map(
148
+ ( _, index ) =>
149
+ `${ descriptionId }-${ index }`
150
+ )
151
+ .join( ' ' )
152
+ : undefined
153
+ }
154
+ >
155
+ { isEmpty && __( 'Empty pattern' ) }
156
+ { ! isEmpty && <BlockPreview blocks={ item.blocks } /> }
157
+ </button>
158
+ { ariaDescriptions.map( ( ariaDescription, index ) => (
159
+ <div
160
+ key={ index }
161
+ hidden
162
+ id={ `${ descriptionId }-${ index }` }
128
163
  >
129
- { isEmpty && __( 'Empty pattern' ) }
130
- { ! isEmpty && <BlockPreview blocks={ item.blocks } /> }
131
- </CompositeItem>
132
- { ariaDescriptions.map( ( ariaDescription, index ) => (
133
- <div
134
- key={ index }
135
- hidden
136
- id={ `${ descriptionId }-${ index }` }
137
- >
138
- { ariaDescription }
139
- </div>
140
- ) ) }
164
+ { ariaDescription }
165
+ </div>
166
+ ) ) }
167
+ <HStack
168
+ className="edit-site-patterns__footer"
169
+ justify="space-between"
170
+ >
141
171
  <HStack
142
- aria-hidden="true"
143
- className="edit-site-patterns__footer"
144
- justify="space-between"
172
+ alignment="center"
173
+ justify="left"
174
+ spacing={ 3 }
175
+ className="edit-site-patterns__pattern-title"
145
176
  >
146
- <HStack
147
- alignment="center"
148
- justify="left"
149
- spacing={ 3 }
150
- className="edit-site-patterns__pattern-title"
151
- >
152
- { icon && (
153
- <Icon
154
- className="edit-site-patterns__pattern-icon"
155
- icon={ itemIcon }
156
- />
157
- ) }
158
- <Flex
159
- as={ Heading }
160
- level={ 5 }
161
- gap={ 0 }
162
- justify="left"
177
+ { itemIcon && (
178
+ <Tooltip
179
+ position="top center"
180
+ text={ __(
181
+ 'Editing this pattern will also update anywhere it is used'
182
+ ) }
163
183
  >
164
- { item.title }
165
- { item.type === PATTERNS && (
166
- <Tooltip
167
- position="top center"
168
- text={ __(
169
- 'Theme patterns cannot be edited.'
170
- ) }
184
+ <span>
185
+ <Icon
186
+ className="edit-site-patterns__pattern-icon"
187
+ icon={ itemIcon }
188
+ />
189
+ </span>
190
+ </Tooltip>
191
+ ) }
192
+ <Flex as="span" gap={ 0 } justify="left">
193
+ { item.type === PATTERNS ? (
194
+ item.title
195
+ ) : (
196
+ <Heading level={ 5 }>
197
+ <Button
198
+ variant="link"
199
+ onClick={ onClick }
200
+ // Required for the grid's roving tab index system.
201
+ // See https://github.com/WordPress/gutenberg/pull/51898#discussion_r1243399243.
202
+ tabIndex="-1"
171
203
  >
172
- <span className="edit-site-patterns__pattern-lock-icon">
173
- <Icon
174
- style={ { fill: 'currentcolor' } }
175
- icon={ lockSmall }
176
- size={ 24 }
177
- />
178
- </span>
179
- </Tooltip>
204
+ { item.title }
205
+ </Button>
206
+ </Heading>
207
+ ) }
208
+ { item.type === PATTERNS && (
209
+ <Tooltip
210
+ position="top center"
211
+ text={ __(
212
+ 'Theme patterns cannot be edited.'
213
+ ) }
214
+ >
215
+ <span className="edit-site-patterns__pattern-lock-icon">
216
+ <Icon icon={ lockSmall } size={ 24 } />
217
+ </span>
218
+ </Tooltip>
219
+ ) }
220
+ </Flex>
221
+ </HStack>
222
+ <DropdownMenu
223
+ icon={ moreHorizontal }
224
+ label={ __( 'Actions' ) }
225
+ className="edit-site-patterns__dropdown"
226
+ popoverProps={ { placement: 'bottom-end' } }
227
+ toggleProps={ {
228
+ className: 'edit-site-patterns__button',
229
+ isSmall: true,
230
+ describedBy: sprintf(
231
+ /* translators: %s: pattern name */
232
+ __( 'Action menu for %s pattern' ),
233
+ item.title
234
+ ),
235
+ } }
236
+ >
237
+ { ( { onClose } ) => (
238
+ <MenuGroup>
239
+ { isCustomPattern && ! hasThemeFile && (
240
+ <RenameMenuItem
241
+ item={ item }
242
+ onClose={ onClose }
243
+ />
180
244
  ) }
181
- </Flex>
182
- </HStack>
183
- { item.type === USER_PATTERNS && (
184
- <DropdownMenu
185
- icon={ moreHorizontal }
186
- label={ __( 'Actions' ) }
187
- className="edit-site-patterns__dropdown"
188
- popoverProps={ { placement: 'bottom-end' } }
189
- toggleProps={ {
190
- className: 'edit-site-patterns__button',
191
- isSmall: true,
192
- describedBy: sprintf(
193
- /* translators: %s: pattern name */
194
- __( 'Action menu for %s pattern' ),
195
- item.title
196
- ),
197
- // The dropdown menu is not focusable using the
198
- // keyboard as this would interfere with the grid's
199
- // roving tab index system. Instead, keyboard users
200
- // use keyboard shortcuts to trigger actions.
201
- tabIndex: -1,
202
- } }
203
- >
204
- { () => (
205
- <MenuGroup>
206
- <MenuItem
207
- onClick={ () =>
208
- setIsDeleteDialogOpen( true )
209
- }
210
- >
211
- { __( 'Delete' ) }
212
- </MenuItem>
213
- </MenuGroup>
245
+ <DuplicateMenuItem
246
+ categoryId={ categoryId }
247
+ item={ item }
248
+ onClose={ onClose }
249
+ label={
250
+ isNonUserPattern
251
+ ? __( 'Copy to My patterns' )
252
+ : __( 'Duplicate' )
253
+ }
254
+ />
255
+ { isCustomPattern && (
256
+ <MenuItem
257
+ onClick={ () =>
258
+ setIsDeleteDialogOpen( true )
259
+ }
260
+ >
261
+ { hasThemeFile
262
+ ? __( 'Clear customizations' )
263
+ : __( 'Delete' ) }
264
+ </MenuItem>
214
265
  ) }
215
- </DropdownMenu>
266
+ </MenuGroup>
216
267
  ) }
217
- </HStack>
218
- </div>
268
+ </DropdownMenu>
269
+ </HStack>
270
+
219
271
  { isDeleteDialogOpen && (
220
272
  <ConfirmDialog
221
- onConfirm={ deletePattern }
273
+ confirmButtonText={ confirmButtonText }
274
+ onConfirm={ deleteItem }
222
275
  onCancel={ () => setIsDeleteDialogOpen( false ) }
223
276
  >
224
- { __( 'Are you sure you want to delete this pattern?' ) }
277
+ { confirmPrompt }
225
278
  </ConfirmDialog>
226
279
  ) }
227
- </>
280
+ </li>
228
281
  );
229
282
  }
283
+
284
+ export default memo( GridItem );
@@ -1,39 +1,52 @@
1
1
  /**
2
2
  * WordPress dependencies
3
3
  */
4
- import {
5
- __unstableComposite as Composite,
6
- __unstableUseCompositeState as useCompositeState,
7
- } from '@wordpress/components';
4
+ import { __experimentalText as Text } from '@wordpress/components';
5
+ import { useRef } from '@wordpress/element';
6
+ import { __, sprintf } from '@wordpress/i18n';
8
7
 
9
8
  /**
10
9
  * Internal dependencies
11
10
  */
12
11
  import GridItem from './grid-item';
13
12
 
14
- export default function Grid( { categoryId, label, icon, items } ) {
15
- const composite = useCompositeState( { orientation: 'vertical' } );
13
+ const PAGE_SIZE = 100;
14
+
15
+ export default function Grid( { categoryId, items, ...props } ) {
16
+ const gridRef = useRef();
16
17
 
17
18
  if ( ! items?.length ) {
18
19
  return null;
19
20
  }
20
21
 
22
+ const list = items.slice( 0, PAGE_SIZE );
23
+ const restLength = items.length - PAGE_SIZE;
24
+
21
25
  return (
22
- <Composite
23
- { ...composite }
24
- role="listbox"
25
- className="edit-site-patterns__grid"
26
- aria-label={ label }
27
- >
28
- { items.map( ( item ) => (
29
- <GridItem
30
- key={ item.name }
31
- icon={ icon }
32
- item={ item }
33
- categoryId={ categoryId }
34
- composite={ composite }
35
- />
36
- ) ) }
37
- </Composite>
26
+ <>
27
+ <ul
28
+ role="listbox"
29
+ className="edit-site-patterns__grid"
30
+ { ...props }
31
+ ref={ gridRef }
32
+ >
33
+ { list.map( ( item ) => (
34
+ <GridItem
35
+ key={ item.name }
36
+ item={ item }
37
+ categoryId={ categoryId }
38
+ />
39
+ ) ) }
40
+ </ul>
41
+ { restLength > 0 && (
42
+ <Text variant="muted" as="p" align="center">
43
+ { sprintf(
44
+ /* translators: %d: number of patterns */
45
+ __( '+ %d more patterns discoverable by searching' ),
46
+ restLength
47
+ ) }
48
+ </Text>
49
+ ) }
50
+ </>
38
51
  );
39
52
  }
@@ -0,0 +1,69 @@
1
+ /**
2
+ * WordPress dependencies
3
+ */
4
+ import {
5
+ __experimentalVStack as VStack,
6
+ __experimentalHeading as Heading,
7
+ __experimentalText as Text,
8
+ } from '@wordpress/components';
9
+ import { __ } from '@wordpress/i18n';
10
+ import { store as editorStore } from '@wordpress/editor';
11
+ import { useSelect } from '@wordpress/data';
12
+
13
+ /**
14
+ * Internal dependencies
15
+ */
16
+ import usePatternCategories from '../sidebar-navigation-screen-patterns/use-pattern-categories';
17
+ import {
18
+ USER_PATTERN_CATEGORY,
19
+ USER_PATTERNS,
20
+ TEMPLATE_PARTS,
21
+ PATTERNS,
22
+ } from './utils';
23
+
24
+ export default function PatternsHeader( {
25
+ categoryId,
26
+ type,
27
+ titleId,
28
+ descriptionId,
29
+ } ) {
30
+ const { patternCategories } = usePatternCategories();
31
+ const templatePartAreas = useSelect(
32
+ ( select ) =>
33
+ select( editorStore ).__experimentalGetDefaultTemplatePartAreas(),
34
+ []
35
+ );
36
+
37
+ let title, description;
38
+ if ( categoryId === USER_PATTERN_CATEGORY && type === USER_PATTERNS ) {
39
+ title = __( 'My Patterns' );
40
+ description = '';
41
+ } else if ( type === TEMPLATE_PARTS ) {
42
+ const templatePartArea = templatePartAreas.find(
43
+ ( area ) => area.area === categoryId
44
+ );
45
+ title = templatePartArea?.label;
46
+ description = templatePartArea?.description;
47
+ } else if ( type === PATTERNS ) {
48
+ const patternCategory = patternCategories.find(
49
+ ( category ) => category.name === categoryId
50
+ );
51
+ title = patternCategory?.label;
52
+ description = patternCategory?.description;
53
+ }
54
+
55
+ if ( ! title ) return null;
56
+
57
+ return (
58
+ <VStack className="edit-site-patterns__section-header">
59
+ <Heading as="h2" level={ 4 } id={ titleId }>
60
+ { title }
61
+ </Heading>
62
+ { description ? (
63
+ <Text variant="muted" as="p" id={ descriptionId }>
64
+ { description }
65
+ </Text>
66
+ ) : null }
67
+ </VStack>
68
+ );
69
+ }
@@ -32,7 +32,12 @@ export default function PagePatterns() {
32
32
  title={ __( 'Patterns content' ) }
33
33
  hideTitleFromUI
34
34
  >
35
- <PatternsList type={ type } categoryId={ category } />
35
+ <PatternsList
36
+ // Reset the states when switching between categories and types.
37
+ key={ `${ type }-${ category }` }
38
+ type={ type }
39
+ categoryId={ category }
40
+ />
36
41
  </Page>
37
42
  </ExperimentalBlockEditorProvider>
38
43
  );