Full-Site Editing (or FSE for short) is scheduled to be released with WordPress 5.6. In the meantime, the Gutenberg plugin includes a Navigation Block that theme-authors can use to experiment and preview what their navigation will look like once users are able to use FSE on their sites.
You can already start preparing for this shift by making the default WordPress navigation use an HTML structure similar to what the Navigation block is going to print.
To do that, you can paste the following code in your theme’s functions.php file:
/**
* Filters the CSS class(es) applied to a menu list element.
*
* @param array $classes Array of the CSS classes that are applied to the menu `<ul>` element.
* @return array
*/
add_filter( 'nav_menu_submenu_css_class', function( $classes ) {
return [ 'wp-block-navigation__container' ];
} );
/**
* Filters the CSS classes applied to a menu item's list item element.
*
* @param array $classes Array of the CSS classes that are applied to the menu item's `<li>` element.
* @return array
*/
add_filter( 'nav_menu_css_class', function( $classes ) {
$item_classes = [ 'wp-block-navigation-link' ];
if ( in_array( 'current-menu-item', $classes ) ) {
$item_classes[] = 'current-menu-item';
}
if ( in_array( 'menu-item-has-children', $classes ) ) {
$item_classes[] = 'has-child';
}
return $item_classes;
} );
/**
* Filters the HTML attributes applied to a menu item's anchor element.
*
* @param array $atts The HTML attributes applied to the menu item's `<a>` element, empty strings are ignored.
* @return array
*/
add_filter( 'nav_menu_link_attributes', function( $atts ) {
$atts['class'] = 'wp-block-navigation-link__content';
return $atts;
} );
/**
* Filters a menu item's title.
*
* @param string $title The menu item's title.
* @return string
*/
add_filter( 'nav_menu_item_title', function( $title ) {
return '<span class="wp-block-navigation-link__label">' . $title . '</span>';
} );
/**
* Filters a menu item's starting output.
*
* Append the dropdown arrow to links with submenus.
*
* @param string $item_output The menu item's starting HTML output.
* @param WP_Post $item Menu item data object.
* @return string
*/
add_filter( 'walker_nav_menu_start_el', function( $item_output, $item ) {
$has_children = in_array( 'menu-item-has-children', $item->classes );
if ( $has_children ) {
$item_output = str_replace(
'</a>',
'</a><span class="wp-block-navigation-link__submenu-icon"><svg xmlns="http://www.w3.org/2000/svg" width="12" height="12" viewBox="0 0 24 24" transform="rotate(90)"><path d="M8 5v14l11-7z"></path><path d="M0 0h24v24H0z" fill="none"></path></svg></span>',
$item_output
);
}
return $item_output;
}, 10, 2 );
Then to print the navigation you can use the following in your header.php file:
<nav class="wp-block-navigation" role="navigation">
<ul class="wp-block-navigation__container">
<?php
wp_nav_menu(
array(
'container' => '',
'items_wrap' => '%3$s',
'theme_location' => 'primary',
)
);
?>
</ul>
</nav>
This will allow you to see what the future structure of navigation will be in WordPress themes and you can start converting your styles & scripts accordingly to accommodate these changes and be ready for when they land in WordPress Core.