117 if ( $has_named_font_size ) { |
121 if ( $has_named_font_size ) { |
118 // Add the font size class. |
122 // Add the font size class. |
119 $font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] ); |
123 $font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] ); |
120 } elseif ( $has_custom_font_size ) { |
124 } elseif ( $has_custom_font_size ) { |
121 // Add the custom font size inline style. |
125 // Add the custom font size inline style. |
122 $font_sizes['inline_styles'] = sprintf( 'font-size: %s;', $context['style']['typography']['fontSize'] ); |
126 $font_sizes['inline_styles'] = sprintf( |
|
127 'font-size: %s;', |
|
128 wp_get_typography_font_size_value( |
|
129 array( |
|
130 'size' => $context['style']['typography']['fontSize'], |
|
131 ) |
|
132 ) |
|
133 ); |
123 } |
134 } |
124 |
135 |
125 return $font_sizes; |
136 return $font_sizes; |
126 } |
137 } |
127 |
138 |
128 /** |
139 /** |
129 * Outputs Page list markup from an array of pages with nested children. |
140 * Outputs Page list markup from an array of pages with nested children. |
|
141 * |
|
142 * @since 5.8.0 |
130 * |
143 * |
131 * @param boolean $open_submenus_on_click Whether to open submenus on click instead of hover. |
144 * @param boolean $open_submenus_on_click Whether to open submenus on click instead of hover. |
132 * @param boolean $show_submenu_icons Whether to show submenu indicator icons. |
145 * @param boolean $show_submenu_icons Whether to show submenu indicator icons. |
133 * @param boolean $is_navigation_child If block is a child of Navigation block. |
146 * @param boolean $is_navigation_child If block is a child of Navigation block. |
134 * @param array $nested_pages The array of nested pages. |
147 * @param array $nested_pages The array of nested pages. |
|
148 * @param boolean $is_nested Whether the submenu is nested or not. |
135 * @param array $active_page_ancestor_ids An array of ancestor ids for active page. |
149 * @param array $active_page_ancestor_ids An array of ancestor ids for active page. |
136 * @param array $colors Color information for overlay styles. |
150 * @param array $colors Color information for overlay styles. |
137 * @param integer $depth The nesting depth. |
151 * @param integer $depth The nesting depth. |
138 * |
152 * |
139 * @return string List markup. |
153 * @return string List markup. |
140 */ |
154 */ |
141 function block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $nested_pages, $active_page_ancestor_ids = array(), $colors = array(), $depth = 0 ) { |
155 function block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $nested_pages, $is_nested, $active_page_ancestor_ids = array(), $colors = array(), $depth = 0 ) { |
142 if ( empty( $nested_pages ) ) { |
156 if ( empty( $nested_pages ) ) { |
143 return; |
157 return; |
144 } |
158 } |
145 $markup = ''; |
159 $front_page_id = (int) get_option( 'page_on_front' ); |
|
160 $markup = ''; |
146 foreach ( (array) $nested_pages as $page ) { |
161 foreach ( (array) $nested_pages as $page ) { |
147 $css_class = $page['is_active'] ? ' current-menu-item' : ''; |
162 $css_class = $page['is_active'] ? ' current-menu-item' : ''; |
148 $aria_current = $page['is_active'] ? ' aria-current="page"' : ''; |
163 $aria_current = $page['is_active'] ? ' aria-current="page"' : ''; |
149 $style_attribute = ''; |
164 $style_attribute = ''; |
150 |
165 |
164 } |
179 } |
165 |
180 |
166 $navigation_child_content_class = $is_navigation_child ? ' wp-block-navigation-item__content' : ''; |
181 $navigation_child_content_class = $is_navigation_child ? ' wp-block-navigation-item__content' : ''; |
167 |
182 |
168 // If this is the first level of submenus, include the overlay colors. |
183 // If this is the first level of submenus, include the overlay colors. |
169 if ( 1 === $depth && isset( $colors['overlay_css_classes'], $colors['overlay_inline_styles'] ) ) { |
184 if ( ( ( 0 < $depth && ! $is_nested ) || $is_nested ) && isset( $colors['overlay_css_classes'], $colors['overlay_inline_styles'] ) ) { |
170 $css_class .= ' ' . trim( implode( ' ', $colors['overlay_css_classes'] ) ); |
185 $css_class .= ' ' . trim( implode( ' ', $colors['overlay_css_classes'] ) ); |
171 if ( '' !== $colors['overlay_inline_styles'] ) { |
186 if ( '' !== $colors['overlay_inline_styles'] ) { |
172 $style_attribute = sprintf( ' style="%s"', esc_attr( $colors['overlay_inline_styles'] ) ); |
187 $style_attribute = sprintf( ' style="%s"', esc_attr( $colors['overlay_inline_styles'] ) ); |
173 } |
188 } |
174 } |
189 } |
175 |
190 |
176 $front_page_id = (int) get_option( 'page_on_front' ); |
|
177 if ( (int) $page['page_id'] === $front_page_id ) { |
191 if ( (int) $page['page_id'] === $front_page_id ) { |
178 $css_class .= ' menu-item-home'; |
192 $css_class .= ' menu-item-home'; |
179 } |
193 } |
180 |
194 |
181 $title = wp_kses_post( $page['title'] ); |
195 $title = wp_kses_post( $page['title'] ); |
187 |
201 |
188 $markup .= '<li class="wp-block-pages-list__item' . esc_attr( $css_class ) . '"' . $style_attribute . '>'; |
202 $markup .= '<li class="wp-block-pages-list__item' . esc_attr( $css_class ) . '"' . $style_attribute . '>'; |
189 |
203 |
190 if ( isset( $page['children'] ) && $is_navigation_child && $open_submenus_on_click ) { |
204 if ( isset( $page['children'] ) && $is_navigation_child && $open_submenus_on_click ) { |
191 $markup .= '<button aria-label="' . esc_attr( $aria_label ) . '" class="' . esc_attr( $navigation_child_content_class ) . ' wp-block-navigation-submenu__toggle" aria-expanded="false">' . esc_html( $title ) . |
205 $markup .= '<button aria-label="' . esc_attr( $aria_label ) . '" class="' . esc_attr( $navigation_child_content_class ) . ' wp-block-navigation-submenu__toggle" aria-expanded="false">' . esc_html( $title ) . |
192 '</button>' . '<span class="wp-block-page-list__submenu-icon wp-block-navigation__submenu-icon"><svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg></span>'; |
206 '</button><span class="wp-block-page-list__submenu-icon wp-block-navigation__submenu-icon"><svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg></span>'; |
193 } else { |
207 } else { |
194 $markup .= '<a class="wp-block-pages-list__item__link' . esc_attr( $navigation_child_content_class ) . '" href="' . esc_url( $page['link'] ) . '"' . $aria_current . '>' . $title . '</a>'; |
208 $markup .= '<a class="wp-block-pages-list__item__link' . esc_attr( $navigation_child_content_class ) . '" href="' . esc_url( $page['link'] ) . '"' . $aria_current . '>' . $title . '</a>'; |
195 } |
209 } |
196 |
210 |
197 if ( isset( $page['children'] ) ) { |
211 if ( isset( $page['children'] ) ) { |
198 if ( $is_navigation_child && $show_submenu_icons && ! $open_submenus_on_click ) { |
212 if ( $is_navigation_child && $show_submenu_icons && ! $open_submenus_on_click ) { |
199 $markup .= '<button aria-label="' . esc_attr( $aria_label ) . '" class="wp-block-navigation__submenu-icon wp-block-navigation-submenu__toggle" aria-expanded="false">'; |
213 $markup .= '<button aria-label="' . esc_attr( $aria_label ) . '" class="wp-block-navigation__submenu-icon wp-block-navigation-submenu__toggle" aria-expanded="false">'; |
200 $markup .= '<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg>'; |
214 $markup .= '<svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 12 12" fill="none" aria-hidden="true" focusable="false"><path d="M1.50002 4L6.00002 8L10.5 4" stroke-width="1.5"></path></svg>'; |
201 $markup .= '</button>'; |
215 $markup .= '</button>'; |
202 } |
216 } |
203 $markup .= '<ul class="submenu-container'; |
217 $markup .= '<ul class="wp-block-navigation__submenu-container">'; |
204 // Extra classname is added when the block is a child of Navigation. |
218 $markup .= block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $page['children'], $is_nested, $active_page_ancestor_ids, $colors, $depth + 1 ); |
205 if ( $is_navigation_child ) { |
219 $markup .= '</ul>'; |
206 $markup .= ' wp-block-navigation__submenu-container'; |
|
207 } |
|
208 $markup .= '">' . block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $page['children'], $active_page_ancestor_ids, $colors, $depth + 1 ) . '</ul>'; |
|
209 } |
220 } |
210 $markup .= '</li>'; |
221 $markup .= '</li>'; |
211 } |
222 } |
212 return $markup; |
223 return $markup; |
213 } |
224 } |
214 |
225 |
215 /** |
226 /** |
216 * Outputs nested array of pages |
227 * Outputs nested array of pages |
|
228 * |
|
229 * @since 5.8.0 |
217 * |
230 * |
218 * @param array $current_level The level being iterated through. |
231 * @param array $current_level The level being iterated through. |
219 * @param array $children The children grouped by parent post ID. |
232 * @param array $children The children grouped by parent post ID. |
220 * |
233 * |
221 * @return array The nested array of pages. |
234 * @return array The nested array of pages. |
233 } |
246 } |
234 |
247 |
235 /** |
248 /** |
236 * Renders the `core/page-list` block on server. |
249 * Renders the `core/page-list` block on server. |
237 * |
250 * |
|
251 * @since 5.8.0 |
|
252 * |
238 * @param array $attributes The block attributes. |
253 * @param array $attributes The block attributes. |
239 * @param string $content The saved content. |
254 * @param string $content The saved content. |
240 * @param WP_Block $block The parsed block. |
255 * @param WP_Block $block The parsed block. |
241 * |
256 * |
242 * @return string Returns the page list markup. |
257 * @return string Returns the page list markup. |
243 */ |
258 */ |
244 function render_block_core_page_list( $attributes, $content, $block ) { |
259 function render_block_core_page_list( $attributes, $content, $block ) { |
245 static $block_id = 0; |
260 static $block_id = 0; |
246 $block_id++; |
261 ++$block_id; |
|
262 |
|
263 $parent_page_id = $attributes['parentPageID']; |
|
264 $is_nested = $attributes['isNested']; |
247 |
265 |
248 $all_pages = get_pages( |
266 $all_pages = get_pages( |
249 array( |
267 array( |
250 'sort_column' => 'menu_order,post_title', |
268 'sort_column' => 'menu_order,post_title', |
251 'order' => 'asc', |
269 'order' => 'asc', |
262 $pages_with_children = array(); |
280 $pages_with_children = array(); |
263 |
281 |
264 $active_page_ancestor_ids = array(); |
282 $active_page_ancestor_ids = array(); |
265 |
283 |
266 foreach ( (array) $all_pages as $page ) { |
284 foreach ( (array) $all_pages as $page ) { |
267 $is_active = ! empty( $page->ID ) && ( get_the_ID() === $page->ID ); |
285 $is_active = ! empty( $page->ID ) && ( get_queried_object_id() === $page->ID ); |
268 |
286 |
269 if ( $is_active ) { |
287 if ( $is_active ) { |
270 $active_page_ancestor_ids = get_post_ancestors( $page->ID ); |
288 $active_page_ancestor_ids = get_post_ancestors( $page->ID ); |
271 } |
289 } |
272 |
290 |
273 if ( $page->post_parent ) { |
291 if ( $page->post_parent ) { |
274 $pages_with_children[ $page->post_parent ][ $page->ID ] = array( |
292 $pages_with_children[ $page->post_parent ][ $page->ID ] = array( |
275 'page_id' => $page->ID, |
293 'page_id' => $page->ID, |
276 'title' => $page->post_title, |
294 'title' => $page->post_title, |
277 'link' => get_permalink( $page->ID ), |
295 'link' => get_permalink( $page ), |
278 'is_active' => $is_active, |
296 'is_active' => $is_active, |
279 ); |
297 ); |
280 } else { |
298 } else { |
281 $top_level_pages[ $page->ID ] = array( |
299 $top_level_pages[ $page->ID ] = array( |
282 'page_id' => $page->ID, |
300 'page_id' => $page->ID, |
283 'title' => $page->post_title, |
301 'title' => $page->post_title, |
284 'link' => get_permalink( $page->ID ), |
302 'link' => get_permalink( $page ), |
285 'is_active' => $is_active, |
303 'is_active' => $is_active, |
286 ); |
304 ); |
287 |
305 |
288 } |
306 } |
289 } |
307 } |
297 $style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] ); |
315 $style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] ); |
298 $css_classes = trim( implode( ' ', $classes ) ); |
316 $css_classes = trim( implode( ' ', $classes ) ); |
299 |
317 |
300 $nested_pages = block_core_page_list_nest_pages( $top_level_pages, $pages_with_children ); |
318 $nested_pages = block_core_page_list_nest_pages( $top_level_pages, $pages_with_children ); |
301 |
319 |
302 // Limit the number of items to be visually displayed. |
320 if ( 0 !== $parent_page_id ) { |
303 if ( ! empty( $attributes['__unstableMaxPages'] ) ) { |
321 // If the parent page has no child pages, there is nothing to show. |
304 $nested_pages = array_slice( $nested_pages, 0, $attributes['__unstableMaxPages'] ); |
322 if ( ! array_key_exists( $parent_page_id, $pages_with_children ) ) { |
|
323 return; |
|
324 } |
|
325 |
|
326 $nested_pages = block_core_page_list_nest_pages( |
|
327 $pages_with_children[ $parent_page_id ], |
|
328 $pages_with_children |
|
329 ); |
305 } |
330 } |
306 |
331 |
307 $is_navigation_child = array_key_exists( 'showSubmenuIcon', $block->context ); |
332 $is_navigation_child = array_key_exists( 'showSubmenuIcon', $block->context ); |
308 |
333 |
309 $open_submenus_on_click = array_key_exists( 'openSubmenusOnClick', $block->context ) ? $block->context['openSubmenusOnClick'] : false; |
334 $open_submenus_on_click = array_key_exists( 'openSubmenusOnClick', $block->context ) ? $block->context['openSubmenusOnClick'] : false; |
310 |
335 |
311 $show_submenu_icons = array_key_exists( 'showSubmenuIcon', $block->context ) ? $block->context['showSubmenuIcon'] : false; |
336 $show_submenu_icons = array_key_exists( 'showSubmenuIcon', $block->context ) ? $block->context['showSubmenuIcon'] : false; |
312 |
337 |
313 $wrapper_markup = '<ul %1$s>%2$s</ul>'; |
338 $wrapper_markup = $is_nested ? '%2$s' : '<ul %1$s>%2$s</ul>'; |
314 |
339 |
315 $items_markup = block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $nested_pages, $active_page_ancestor_ids, $colors ); |
340 $items_markup = block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $nested_pages, $is_nested, $active_page_ancestor_ids, $colors ); |
316 |
341 |
317 $wrapper_attributes = get_block_wrapper_attributes( |
342 $wrapper_attributes = get_block_wrapper_attributes( |
318 array( |
343 array( |
319 'class' => $css_classes, |
344 'class' => $css_classes, |
320 'style' => $style_attribute, |
345 'style' => $style_attribute, |
326 $wrapper_attributes, |
351 $wrapper_attributes, |
327 $items_markup |
352 $items_markup |
328 ); |
353 ); |
329 } |
354 } |
330 |
355 |
331 /** |
356 /** |
332 * Registers the `core/pages` block on server. |
357 * Registers the `core/pages` block on server. |
333 */ |
358 * |
|
359 * @since 5.8.0 |
|
360 */ |
334 function register_block_core_page_list() { |
361 function register_block_core_page_list() { |
335 register_block_type_from_metadata( |
362 register_block_type_from_metadata( |
336 __DIR__ . '/page-list', |
363 __DIR__ . '/page-list', |
337 array( |
364 array( |
338 'render_callback' => 'render_block_core_page_list', |
365 'render_callback' => 'render_block_core_page_list', |
339 ) |
366 ) |
340 ); |
367 ); |
341 } |
368 } |
342 add_action( 'init', 'register_block_core_page_list' ); |
369 add_action( 'init', 'register_block_core_page_list' ); |