Project Set-up. You can continue working with an existing project, such as the one you just created in The CHILD, or you can start a new site. If you start a new site, I recommend naming it n413_header. The instructions will assume you are using a new project. Set up a new database and do a fresh install of the Wordpress files, as explained in The INSTALL.
If you need the files for the twentytwenty theme, you can find them on the Resources page.
The Theme. Once you have a WordPress project ready to go, put some thought into which theme you want to use. There are a few considerations:
Themes vary greatly in the customizable features available in the header and footer. If your aim is to simply make changes to the header or footer, you may find that you need to look no farther than the Dashboard's Appearance > Customize menu. However, these same features make the code in the header.php and footer.php files much more complex, with several theme-specific functions for incorporating the user input. If your aim is to do something with customized code in the header or footer, it is best to work with a theme with minimal customization options.
The concepts presented here will apply to many themes you might work with, but the specific examples will be for Twenty Twenty and Twenty Twenty-One. However, the new "block" themes, such as Twenty Twenty-Two/Twenty Twenty-Three, will not work with the instructions here. Block themes have a very different structure than the classic PHP template-based themes.
It is possible to have a couple of themes going at once as you try things. You will need a child theme for each theme you want to use. However, you can activate and de-activate the child themes as you make changes to view your results.
header.php and footer.php. With your child theme set up, move header.php and footer.php into your child theme. Also move one of the page template files, such as single.php or singular.php. (The Twenty Twenty theme uses singular.php.)
Compare. Now, have a look at how the page markup is distributed among the template files. The page will be structured so the the main page content is enclosed in a "container", or <div> tag. Some themes use multiple nested tags for supporting structures like sidebars or post navigation. It might look like this:
<header> ... </header> <div id="content" class="site-content"> <main id="main" class="site-main" role="main"> ... <!-- Main page content --> </main><!-- #main --> </div><!-- /#content --> <footer> ... </footer>
The theme designer will need to decide which template files the opening and closing container tags will be in. Some themes place the opening tags in the header.php file, with the closing tags in the footer.php file. Other themes will place both the opening and closing container tags in the main page template.
Let's look at Twenty Twenty-One first. The last few lines of header.php contain the following container markup tags:
twentytwentyone/header.php ... <div id="content" class="site-content"> <div id="primary" class="content-area"> <main id="main" class="site-main" role="main">
The first few lines of footer.php contain the corresponding closing tags for the container markup:
twentytwentyone/footer.php </main><!-- #main --> </div><!-- #primary --> </div><!-- #content --> ...
This information tells you a few things:
Now consider Twenty Twenty. You will not find the container markup in either header.php or footer.php. However, if you have a look at singular.php (the PHP template for rendering single post pages), you will find this:
twentytwenty/singular.php <?php /** * The template for displaying single posts and pages. * * @link https://developer.wordpress.org/themes/basics/template-hierarchy/ * * @package WordPress * @subpackage Twenty_Twenty * @since Twenty Twenty 1.0 */ get_header(); ?> <main id="site-content"> <?php if ( have_posts() ) { while ( have_posts() ) { the_post(); get_template_part( 'template-parts/content', get_post_type() ); } } ?> </main><!-- #site-content --> <?php get_template_part( 'template-parts/footer-menus-widgets' ); ?> <?php get_footer(); ?>
The only container markup used for Twenty Twenty is in the page templates, and it consists of only a simple "main" container, which encloses "The Loop". Again, we learn some good information here:
Other themes may have variations of this pattern. For example, the popular theme "Neve" uses the <main> tag in the header/footer templates, but employs a system of "wrappers" that are used to create containers for various purposes.
Modifying header.php The header works to accomplish a few different things:
twentytwenty/header.php ... <head> <meta charset="<?php bloginfo( 'charset' ); ?>"> <meta name="viewport" content="width=device-width, initial-scale=1.0" > <link rel="profile" href="https://gmpg.org/xfn/11"> <?php wp_head(); ?> </head> ...
It's a mix of markup (with a couple of PHP functions to grab key items from WordPress) and a WordPress function, wp_head() that does the heavy lifting of getting all the "wp_enqueue_style" items from functions.php.
Opening the body tag is also quite simple in both Twenty Twenty and Twenty Twenty-One:
twentytwenty/header.php ... <body <?php body_class(); ?>> <?php wp_body_open(); ?> ...
It's a standard <body> tag that grabs some classes that WordPress knows about, then it runs the wp_body_open() function. This is one of the "hooks" that are discussed elswhere in the exercises. A developer can place an "action", or "hook" that listens for the "body_open" event, and runs any code that should happen at this point.
Twenty Twenty Header Section. Now it gets interesting -- drawing the site header itself. Keep in mind, the header performs only a few (but important!) functions for the page:
If you read through the code in the Twenty Twenty <header> tag, it is quite complex. One simple way to handle the problem would be to remove all the <header> code and replace it with your own markup. However, WordPress is very good at drawing menus and handling the responsive part, so you probably want to leave that code untouched. But if you working with the Twenty Twenty header at all, it is very likely that you will need to customize a logo that has an unusual shape/size, or do some custom work with your client's identity graphics. So let's examine how this happens.
At this point, it's helpful to open the web inspector panel in your browser and examine how the tags in the code are rendered in the browser itself. Here's the first part of the Twenty Twenty header:
twentytwenty/header.php ... <header id="site-header" class="header-footer-group"> <div class="header-inner section-inner"> <div class="header-titles-wrapper"> ...
The <header> tag and the inner container provide good CSS targets for customizing the background color. Possibly text color, also. Remember these when it is time to do styling. The third container, header-titles-wrapper, holds the left-side half of the header, which includes the site identity graphics and text. It also contains toggles for the responsive version of the header UI. Small screen sizes will only show the header-titles-wrapper, so it must contain versions of the search UI and the navigation menu, which only become visible when the screen is small. The first passage of code is the toggle button for a search interface when the screen size is small:
twentytwenty/header.php ... <?php // Check whether the header search is activated in the customizer. $enable_header_search = get_theme_mod( 'enable_header_search', true ); if ( true === $enable_header_search ) { ?> <button class="toggle search-toggle mobile-search-toggle" data-toggle-target=".search-modal" data-toggle-body-class="showing-search-modal" data-set-focus=".search-modal .search-field" aria-expanded="false"> <span class="toggle-inner"> <span class="toggle-icon"><?php twentytwenty_the_theme_svg( 'search' ); ?></span> <span class="toggle-text"><?php _ex( 'Search', 'toggle text', 'twentytwenty' ); ?></span> </span> </button><!-- .search-toggle --> <?php } ?> ...
It isn't critical to understand what this code does, as you should probably just leave it alone, but it does check the dashboard interface data to see whether or not to show a header search. The list of button classes and attributes is daunting, but basically, they set up the button to display a modal for the search. Finally, there are theme-specific functions (twentytwenty) to get the .svg file for the search icon, and there is a translation function (_ex()) to show the search icon label. Notice, you won't see this at all, unless the screen size is small (it is a "mobile" class). It's a little unusual, in that it appears on the left side of the header and therefore appears first in the <header> code.
Now comes the section we are most interested in:
twentytwenty/header.php ... <div class="header-titles"> <?php // Site title or logo. twentytwenty_site_logo(); // Site description. twentytwenty_site_description(); ?> </div><!-- .header-titles --> ...
These theme-specific functions will retrieve the logo and "tag-line" from the dashboard interface. If you want to do your own thing here, just replace the content of <div class="header-titles"> with your own markup. An <img> tag and some formatted text will give the site your look.
The next passage of code is the equivalent of the "hamburger" menu for the responsive version of the header. However, the symbol used is the "ellipsis". Watch for where it occurs:
twentytwenty/header.php ... <button class="toggle nav-toggle mobile-nav-toggle" data-toggle-target=".menu-modal" data-toggle-body-class="showing-menu-modal" aria-expanded="false" data-set-focus=".close-nav-toggle"> <span class="toggle-inner"> <span class="toggle-icon"> <?php twentytwenty_the_theme_svg( 'ellipsis' ); ?> </span> <span class="toggle-text"><?php _e( 'Menu', 'twentytwenty' ); ?></span> </span> </button><!-- .nav-toggle --> </div><!-- .header-titles-wrapper --> ...
Following the ellipsis, a translation function processes the "Menu" label using the twentytwenty text domain. That finishes the leftside part of the header-titles-wrapper div.
Now, for the header-navigation-wrapper, which will contain the main site menu and a few variations of the "ellispis" and search toggles. Let's focus on the navigation menu:
twentytwenty/header.php ... <div class="header-navigation-wrapper"> <?php if ( has_nav_menu( 'primary' ) || ! has_nav_menu( 'expanded' ) ) { ?> <nav class="primary-menu-wrapper" aria-label="<?php echo esc_attr_x( 'Horizontal', 'menu', 'twentytwenty' ); ?>"> <ul class="primary-menu reset-list-style"> <?php if ( has_nav_menu( 'primary' ) ) { wp_nav_menu( array( 'container' => '', 'items_wrap' => '%3$s', 'theme_location' => 'primary', ) ); } elseif ( ! has_nav_menu( 'expanded' ) ) { wp_list_pages( array( 'match_menu_classes' => true, 'show_sub_menu_icons' => true, 'title_li' => false, 'walker' => new TwentyTwenty_Walker_Page(), ) ); } ?> </ul> </nav><!-- .primary-menu-wrapper --> <?php }
Your head may want to explode here. Understandable. But let's break down the logic a bit... We first want to know if there is a primary menu -and- whether the menu is expanded. If it's not expanded, we have the responsive header, and nothing will be showing here at all. But if we are showing the menu, is it the primary menu or the list of pages? WordPress can show the list of pages, based on the pages you've set up for the site (or the default pages during the install). If you haven't set up a primary menu, the pages are what you get. But if you have defined a primary menu, wp_nav_menu() will fetch it for you. The three arguments provided here are only a fraction of the options, so if you want to style the menu, this is where to make your changes. You can learn more here: Wordpress.Org. Also, that '%3$s' item is kind of nasty, too. This StackExchange article sheds some light on what's going on there. A hint: '%3$s' is the list of menu items. Wow.
The page list is the last item to consider here. wp_list_pages() will generate that for you. Again, it has a long list of customizable options, which can be seen at WordPress.Org. The most curious thing to see here is the 'walker' item. This is a reference to a WordPress Walker Class, which will draw hierarchical lists. You can read more about that at WordPress.Org. In this case, it looks like the theme has it's own version of a walker to get the menu pages.
The rest of the code in the Twenty Twenty header supports the larger screen versions of the search modal and the ellipsis(hamburger) menu toggle. So let's look at the Twenty Twenty-One header code.
Twenty Twenty-One Header Section. Let's start just past the opening <body> tag:twentytwentyone/header.php ... <div id="page" class="site"> <a class="skip-link screen-reader-text" href="#content"><?php esc_html_e( 'Skip to content', 'twentytwentyone' ); ?></a> <?php get_template_part( 'template-parts/header/site-header' ); ?> <div id="content" class="site-content"> <div id="primary" class="content-area"> <main id="main" class="site-main">
The first thing to notice is a container for the entire page. It contains a link for a screen reader to skip through all the header information. Good accessibility feature! --Then the last few lines are the markup for the content containers discussed earlier.
So where is all the header code?? There's only one line, and it calls get_template_part(). The get_template_part() function is usually seen in "The Loop", fetching the HTML markup code to render posts, but Twenty Twenty-One uses this method to call in fragments of code for rendering headers, footers, and other pieces of content. We will find the code we seek in the template-parts/header/site-header.php file.
After setting some variables to hold classes, the code for site-header.php is this:
twentytwentyone/template-parts/header/site-header.php ... <header id="masthead" class="<?php echo esc_attr( $wrapper_classes ); ?>"> <?php get_template_part( 'template-parts/header/site-branding' ); ?> <?php get_template_part( 'template-parts/header/site-nav' ); ?> </header><!-- #masthead -->