In part 1 of this tutorial series I introduced the basic concept of dynamic page templates and created a standard page template as a foundation for future work. A WordPress child theme based on the Twenty Seventeen parent theme was used to implement the page template.
In this tutorial, you’ll learn more specific details about dynamic page templates and how you can use them in your own WordPress projects.
I’ll also show you step by step how to extend the page template from the first tutorial and turn it into your very first working dynamic page template!
Dynamic Page Templates: A More Flexible Approach
So how can we make page templates more flexible, and why would this be useful anyway?
Let’s say that you have a portfolio page template that outputs a gallery of individual portfolio items. Each item would be a fixed size, and only so many could fit onto each row.
We could, of course, add another page template to display portfolios at different sizes. But what if we wanted to show small, medium, or large portfolios? For this, we would need three separate page templates, with each one having different sizes for the portfolio items.
This could instantly be made more flexible by adding a drop-down control to select the portfolio size (i.e. Small, Medium, or Large). This is more convenient to the user as the page template box is less cluttered with unnecessary choices.
It makes more sense for the developer too, who only has one page template to maintain rather than three! This follows the Don’t Repeat Yourself (DRY) software development principle.
Should All Page Templates Be Dynamic?
It’s worth noting that not every page template would necessarily benefit from being dynamic. If you have a page template that does one thing, and one thing only, then that’s fine. It wouldn’t make sense to add custom controls, and extra logic, to a page template in this case.
But, as you’ll see by the end of this tutorial, many page templates would benefit greatly from being more flexible.
Another useful example for a dynamic page template would be a contact form. There are many custom controls that could be added to make this page template highly flexible.
For example, rather than output a fixed set of form fields, page template controls could be added to allow you to omit certain fields. Or maybe a Captcha field could be optionally displayed to prevent spam form submissions? There are so just many ways you could customize a contact form.
I’ll be creating a dynamic form page template in part 3 of this tutorial series. But first let’s get started with creating a general purpose dynamic page template.
Our First Dynamic Page Template
To begin with, we’ll be creating a basic dynamic page template to demonstrate how all the component parts fit together. Custom controls will be added to the page editor which will be used later on to control page template output.
The custom page template controls we’ll be adding shortly are:
- Text box
- Textarea
- Check box
- Radio buttons
- Drop-down select box
Ideally, the controls should be added directly below the page template drop-down box to make it obvious they’re related to a page template.
However, WordPress doesn’t provide any hooks for this, so you’ll have to make do (for now) with adding custom page template controls to a separate custom meta box. In part three of this tutorial series, I’ll show you how to get round this problem.
Hooks are fundamental to WordPress development. They allow developers to extend the code base without having to resort to editing core files, which is generally considered a bad idea. This is because any custom code would be wiped out whenever a WordPress update is performed (which can happen quite regularly).
To display our meta box on the page editor screen, add the load-post.php
and load-post-new.php
hooks to the child theme init()
method we created in part 1.
We use two WordPress hooks to ensure the meta box displays on the page editor, whether you're creating a new page or editing an existing one. There is also a
save_post
hook that handles saving of post meta data, which I'll cover a bit later on.Add the following four class methods to create, display, and save data for the meta box.
/* Add meta box hook. */ public function page_template_meta_box() { add_action( 'add_meta_boxes', array( $this, 'add_page_template_meta_box' ) ); }/* Register meta box. */ public function add_page_template_meta_box() { add_meta_box( 'page-template-meta-box', esc_html__( 'Page Template Meta Box', 'twenty-seventeen-child' ), array( $this, 'display_page_template_meta_box' ), 'page', 'side', 'default' ); }/* Render meta box on the page editor. */ public function display_page_template_meta_box($object) { wp_nonce_field( basename( __FILE__ ), 'page_template_meta_box_nonce' ); }I won't go into too much detail here about WordPress meta boxes, as that could be a whole tutorial on its own, but note the following points about the code I added above:
- The
page_template_meta_box()
andadd_page_template_meta_box()
class methods register the meta box with WordPress. - In
add_page_template_meta_box()
, the'page'
parameter specifies that this meta box will only be displayed on the 'page' post type editor in the WordPress admin. - The
display_page_template_meta_box()
class method renders the meta box and sets up a nonce to make the form controls more secure.
If all is well, you should now have a meta box displayed on the page editor, as shown below.
It's a bit empty at the moment, though, so let's add some controls.
Adding Custom Controls
If you'll recall from above, we're going to add a text box, text area, checkbox, radio button, and select box controls to the meta box. Start by adding the following code to the display_page_template_meta_box()
method underneath the nonce function.
ID, 'page_template_text', true ); $textarea = get_post_meta( $object->ID, 'page_template_textarea', true ); $checkbox = get_post_meta( $object->ID, 'page_template_chk', true ); $radio = get_post_meta( $object->ID, 'page_template_radio', true ); $select = get_post_meta( $object->ID, 'page_template_select', true );
This retrieves the current values of our meta box controls and stores them in local variables. Now add the following HTML directly after, to render the meta box controls.
?>
/>
>
>
>
Each control is contained inside a paragraph tag, and its current value is updated via the local variable we created earlier. This ensures that the meta box controls always display the correct settings.
However, this won't happen unless we save the current meta box control data to the WordPress database.
A little earlier, I registered a hook to execute a class method every time the page editor was updated. Let's add that method to our child theme class now.
post_type ) { return $post_id; } $page_template_text_value = isset( $_POST[ 'page-template-text' ] ) ? $_POST[ 'page-template-text' ] : ''; update_post_meta( $post_id, 'page_template_text', $page_template_text_value ); $page_template_textarea_value = isset( $_POST[ 'page-template-textarea' ] ) ? $_POST[ 'page-template-textarea' ] : ''; update_post_meta( $post_id, 'page_template_textarea', $page_template_textarea_value ); $page_template_chk_value = isset( $_POST[ 'page-template-chk' ] ) ? $_POST[ 'page-template-chk' ] : ''; update_post_meta( $post_id, 'page_template_chk', $page_template_chk_value ); $page_template_radio_value = isset( $_POST[ 'page-template-align' ] ) ? $_POST[ 'page-template-align' ] : ''; update_post_meta( $post_id, 'page_template_radio', $page_template_radio_value ); $page_template_select_value = isset( $_POST[ 'page-template-select' ]) ? $_POST[ 'page-template-select' ] : ''; update_post_meta( $post_id, 'page_template_select', $page_template_select_value ); }The
save_page_template_meta()
class method handles saving the meta box control data. It only saves the meta box data if the nonce is verified, the current users can edit posts, and we are on the page editor admin screen.If those conditions are satisfied, then we extract the data for each control which is stored in the global
$_POST
variable. This variable is set every time a form is submitted.Finally, the meta box control data is saved to the WordPress database as meta data for the current page.
With the custom page template controls added, our meta box should look like this.
Enter some text for the text box and textarea, and make selections for the check box, radio button, and select box. Hit update to save your changes, and when the page editor reloads, your meta box controls should show the data you just entered.
The full source code for the child theme functions.php file is shown below.
ID, 'page_template_text', true ); $textarea = get_post_meta( $object->ID, 'page_template_textarea', true ); $checkbox = get_post_meta( $object->ID, 'page_template_chk', true ); $radio = get_post_meta( $object->ID, 'page_template_radio', true ); $select = get_post_meta( $object->ID, 'page_template_select', true ); ?>post_type ) { return $post_id; } $page_template_text_value = isset( $_POST[ 'page-template-text' ] ) ? $_POST[ 'page-template-text' ] : ''; update_post_meta( $post_id, 'page_template_text', $page_template_text_value ); $page_template_textarea_value = isset( $_POST[ 'page-template-textarea' ] ) ? $_POST[ 'page-template-textarea' ] : ''; update_post_meta( $post_id, 'page_template_textarea', $page_template_textarea_value ); $page_template_chk_value = isset( $_POST[ 'page-template-chk' ] ) ? $_POST[ 'page-template-chk' ] : ''; update_post_meta( $post_id, 'page_template_chk', $page_template_chk_value ); $page_template_radio_value = isset( $_POST[ 'page-template-align' ] ) ? $_POST[ 'page-template-align' ] : ''; update_post_meta( $post_id, 'page_template_radio', $page_template_radio_value ); $page_template_select_value = isset( $_POST[ 'page-template-select' ]) ? $_POST[ 'page-template-select' ] : ''; update_post_meta( $post_id, 'page_template_select', $page_template_select_value ); } } $ts_child_theme = new DPT_Twenty_Seventeen_Child(); $ts_child_theme->init();
/>
>
>
>
The final piece of the puzzle is to use the meta box control data in our page template on the front end. Open up the
test-page-template.php
file we created in part 1 and replace the contents with this updated code.Text Box: " . $text . ""; echo " Text Area: " . $textarea . "
"; echo "Checkbox: " . $checkbox . "
"; echo "Radio Buttons: " . $radio . "
"; echo "Dropdown: " . $select . "
"; echo "Sitemap
"; echo "" . wp_list_pages( array( 'title_li' => '' ) ) . "
"; endwhile; // End of the loop. ?>Make sure the 'Test Page Template' is the currently selected page template and view the page on the front end.
As you can see, the page template now includes the values just set for the meta box controls on the page editor. This is core to the rest of the tutorial as we'll build on this basic example and create various examples of fully working dynamic page templates that you can use in your own WordPress projects.
Conclusion
In this tutorial, we covered how to build a functioning dynamic page template. At the moment, even though it's functional, our basic page template isn't terribly useful.
In the third and final part of this tutorial series, I'll show you how to build various dynamic page templates, from start to finish, that you can use (and expand upon) in your own WordPress projects.
If you have any questions, please leave me a message in the comments below. I'd love to hear your thoughts on the tutorial.