Ok, so we all agree that Twenty Thirteen theme is perfect for nice clean start for your website, it’s responsive, simple and nice, all we need to do is to expand it a bit to fit our project requirements. By default this template does not have two column layout, which is a must have to avoid unnecessary scroll and to increase page views of our website. There is a lot of shortcode plugins that will do that, but than you will have a bunch of pages with shortcodes inside (which is by the way very confusing for the customers), and you will also depend on some plugin. Because all of this reasons (there are more I’m sure but that’s not the point here) I prefer good old fashioned way.
So let’s get our hand dirty and start with some coding 😉
Create the file page_of_posts_two_columns.php inside of our theme folder (Twenty Thirteen or Twenty Thirteen child in this case).
This first part inside of a comment “Template Name: Page Of Posts Two Columns” is important because it will be shown later as a template name in page administration.
<?php /* Template Name: Page Of Posts Two Columns */ /* This example is for a child theme of Twenty Thirteen: * You'll need to adapt it the HTML structure of your own theme. */ get_header(); /* in case of custom header */ // include (TEMPLATEPATH . '/custom-header.php'); ?> <div id="primary" class="content-area"> <div id="content" class="site-content" role="main"> |
First loop is default Twenty Thirteen Page source code (page.php) with some custom modification. I’ll use it to keep functionality of page as it was before.
<?php /* The loop */ while ( have_posts() ) : the_post(); ?> <header class="archive-header"> <h1 class="archive-title"><?php printf( __( '%s', 'twentythirteen' ), the_title( '', false ) ); ?></h1> </header><!-- .archive-header --> <header class="entry-header"> <?php if ( has_post_thumbnail() && ! post_password_required() ) : ?> <div class="entry-thumbnail"> <?php the_post_thumbnail(); ?> </div> <?php endif; ?> </header><!-- .entry-header --> <div class="entry-content"> <?php the_content(); ?> <?php wp_link_pages( array( 'before' => '<div class="page-links"><span class="page-links-title">' . __( 'Pages:', 'twentythirteen' ) . '</span>', 'after' => '</div>', 'link_before' => '<span>', 'link_after' => '</span>' ) ); ?> <?php edit_post_link( __( 'Edit', 'twentythirteen' ), '<span class="edit-link">', '</span>' ); ?> </div><!-- .entry-content --> <?php endwhile; ?> |
As you can see I have some modification in header section, this way I show Page title as a Archives title which I found very handy and usefull. Anyway, default page.php loop will also be fine if you don’t want it this way, so you can always copy it from page.php.
Than I’ll add some extra code which will give as an option to use number of posts inside of a chosen category (or categories). You must change category ‘plugins’ to your own category name you want to show on page (comma separated for multiple categories, empty or comment out for all categories), and than you can define number of posts shown per page (in this case 4). After that we will add second loop which will use our desired settings.
<?php $paged = ( get_query_var('paged') ) ? get_query_var('paged') : 1; /* $paged = ( get_query_var( 'page' ) ) ? get_query_var( 'page' ) : 1; // use this line instead of upper one for homepage */ $query_args = array( 'post_type' => 'post', 'category_name' => 'plugins', /*your category here, coma separated for multiple categories, empty or comment out for all categories*/ 'posts_per_page' => 4, /*number of posts to show per page*/ 'paged' => $paged ); // create a new instance of WP_Query $the_query = new WP_Query( $query_args ); ?> <?php $col = 1; ?> <article class="entry_content_medium"> <div class="entry-content"> <?php if ( $the_query->have_posts() ) : while ( $the_query->have_posts() ) : $the_query->the_post(); // run the loop ?> <?php if ($col == 1) echo '<div class="entry-content-two-columns-row">'; ?> <div class="post col<?php echo $col;?>" id="post-<?php the_ID(); ?>"> <h2 class="entry-title-medium"><a href="<?php echo get_permalink(); ?>" rel="bookmark"><?php echo the_title(); ?></a></h2> <div class="entry-thumbnail-medium"> <a href="<?php echo get_permalink(); ?>" rel="bookmark" title="<?php echo the_title(); ?>"> <?php the_post_thumbnail(); ?> </a> </div> <div class="excerpt"> <?php the_excerpt(); ?> </div> <div class="entry-meta"> <?php // twentythirteen_entry_meta(); ?> <?php // edit_post_link( __( 'Edit', 'twentythirteen' ), '<span class="edit-link">', '</span>' ); ?> <?php if ( comments_open() && ! is_single() ) : ?> <div class="comments-link"> <?php // comments_popup_link( '<span class="leave-reply">' . __( 'Leave a comment', 'twentythirteen' ) . '</span>', __( 'One comment so far', 'twentythirteen' ), __( 'View all % comments', 'twentythirteen' ) ); ?> </div><!-- .comments-link --> <?php endif; // comments_open() ?> </div><!-- .entry-meta --> </div><!-- .entry-content-two-columns-row --> <?php if ($col == 1) echo '</div>'; (($col==1) ? $col=2 : $col=1); endwhile; wp_reset_postdata();?> </div> <!-- entry_content --> </article> |
Ok, we are finished with the content here, but we need pagination also, in a case that our category have more than 4 posts…
<?php wp_link_pages( array( 'before' => '<div class="page-links"><span class="page-links-title">' . __( 'Pages:', 'twentythirteen' ) . '</span>', 'after' => '</div>', 'link_before' => '<span>', 'link_after' => '</span>' ) ); ?> <?php if ($the_query->max_num_pages > 1) { // check if the max number of pages is greater than 1 ?> <nav class="navigation paging-navigation" role="navigation"> <h1 class="screen-reader-text"><?php _e( 'Posts navigation', 'twentythirteen' ); ?></h1> <div class="nav-links"> <div class="nav-previous"> <?php echo get_next_posts_link( '<span class="meta-nav">←</span> Older posts', $the_query->max_num_pages ); // display older posts link ?> </div> <div class="nav-next"> <?php echo get_previous_posts_link( 'Newer posts <span class="meta-nav">→</span>' ); // display newer posts link ?> </div> </div> </nav> <?php } ?> <?php else: ?> <div class="entry-content"> <article> <p><?php _e('Sorry, no posts matched your criteria.'); ?></p> </article> </div> <?php endif; ?> |
And at the end we close the divs and add sidebars as usual.
</div><!-- #content --> </div><!-- #primary --> <?php get_sidebar(); ?> <?php get_footer(); ?> |
So now our page_of_posts_two_columns.php file is ready to use, save it and copy it (if not already) to your theme or child theme directory.
Now we need to add some custom css, you should add this code to your style.css, again from theme or child theme.
/* Template Name: Page Of Posts Two Columns */ .entry-content-two-columns-row { clear: both; } .col1 { max-width: 50%; float: left; padding: 0px 15px 0px 0px; } .col2 { max-width: 50%; float: right; padding: 0px 0px 0px 15px; } |
And for small screen sizes add this line to the end or integrate it inside existing @media width rule.
@media (max-width: 643px) { /* Template Name: Page Of Posts Two Columns */ .col1 { max-width: 100%!important; float: none; } .col2 { max-width: 100%!important; float: none; padding: 0px; } } |
So, now we are more or less finished, we need to add two more functions inside functions.php file, first one is to limit excerpt size. In this case 32 is a number of words that will be shown, so you can change it to fit your needs. Second one will show custom read more text instead of […]. In this case ‘Read More’. Change it to your own read more text.
// Add custom excerpt lenght if ( ! function_exists( 'mywp_custom_excerpt_length' ) ) { function mywp_custom_excerpt_length( $length ) { return 32; } add_filter( 'excerpt_length', 'mywp_custom_excerpt_length', 999 ); } // Add read more to custom pages if ( ! function_exists( 'mywp_new_excerpt_more' ) ) { function mywp_new_excerpt_more( $more ) { return ' <a class="read-more" href="'. get_permalink( get_the_ID() ) . '">' . __('Read More', 'twentythirteen') . '</a>'; } add_filter( 'excerpt_more', 'mywp_new_excerpt_more' ); } |
Also we can add function which will let us have multiple excerpt size lenghts for different content
if ( ! function_exists( 'excerpt' ) ) { function excerpt($limit) { $excerpt = explode(' ', get_the_excerpt(), $limit); if (count($excerpt)>=$limit) { array_pop($excerpt); $excerpt = implode(" ",$excerpt).'...'; } else { $excerpt = implode(" ",$excerpt); } $excerpt = preg_replace('`\[[^\]]*\]`','',$excerpt); return $excerpt; } } |
Than in your page template instead of “the_excerpt()”; use “echo excerpt(20);” or any number of words desired…
Same thing can be achieved for content as well:
if ( ! function_exists( 'content' ) ) { function content($limit) { $content = explode(' ', get_the_content(), $limit); if (count($content)>=$limit) { array_pop($content); $content = implode(" ",$content).'...'; } else { $content = implode(" ",$content); } $content = preg_replace('/\[.+\]/','', $content); $content = apply_filters('the_content', $content); $content = str_replace(']]>', ']]>', $content); return $content; } } |
To show it: “echo content(25);”
So now we are all done, there is one last thing to do, go to your dashboard and under Pages add a new page, call it as you want but I prefer to call it same as the category (to avoid confusion). So in my case I called this page Plugins. Than add some text if you want, if not nothing will be shown. From the right side under Page Attributes / Template Choose your new template – Page Of Posts Two Columns.
To avoid multiple content under default category view and page category view you should check out How to remove category base url from WordPress
That’s it, to check out this in action you can visit Plugins page on this very site. To create multiple pages you can rename this file like this – page_of_posts_two_columns_plugins.php and than change it’s name at the start of the file – “Template Name: Page Of Posts Two Columns” into “Template Name: Page Of Posts Two Columns Plugins”.
Related Posts
Page of child pages with two columns
How to remove category base url from WordPress
Hi, thanks for the tutorial, it has been so helpful to me. the issue is: with the content(20); the read more link does not display by default, so how to display the read more link?
thanks