Before we get to the technical stuff, I highly recommend creating a Child theme first prior to any changes.
Step 1. Open up your theme’s folder and copy single.php file to something different like awesome-custom-template.php
That’s it! Congrats, you’ve just created your very first custom WordPress single post template, now it’s time to modify it as you wish.
NOTE: Since WordPress 4.7 Post-Type-Templates are enabled in the WordPress core.
Create New Single Post Template
If you wish to create a new WordPress single post template from scratch, you can do so by creating a new file and put the following code inside it:
<?php
/* * Template Name: Featured Article
* Template Post Type: post, page, product
*/
get_header(); ?>
Now when editing posts you can switch templates to the newly created: Featured Article template.
Author based Single Post Template
Different templates for different authors? No problem, just add this code snippet to the beginning of your active theme’s functions.php file:
define(SINGLE_PATH, TEMPLATEPATH . '/single');
add_filter('single_template', 'my_single_author_template');
function my_single_author_template($single) {
global $wp_query, $post; $curauth = get_userdata($wp_query->post->post_author);
if(file_exists(SINGLE_PATH . '/single-author-' . $curauth->user_nicename . '.php')) return SINGLE_PATH . '/single-author-' . $curauth->user_nicename . '.php'; elseif(file_exists(SINGLE_PATH . '/single-author-' . $curauth->ID . '.php')) return SINGLE_PATH . '/single-author-' . $curauth->ID . '.php'; }
Category based Single Post Template
Different templates for posts in different categories? Again, no problem, just add this code snippet to the beginning of your active theme’s functions.php file:
define(SINGLE_PATH, TEMPLATEPATH . '/single');
add_filter('single_template', 'my_single_template');
function my_single_template($single) {
global $wp_query, $post;
foreach((array)get_the_category() as $cat) :
if(file_exists(SINGLE_PATH . '/single-cat-' . $cat->slug . '.php'))
return SINGLE_PATH . '/single-cat-' . $cat->slug . '.php';
elseif(file_exists(SINGLE_PATH . '/single-cat-' . $cat->term_id . '.php'))
return SINGLE_PATH . '/single-cat-' . $cat->term_id . '.php';
endforeach;
}