Complete and flexible blogging platform for ProcessWire

Render Posts

The method renderPosts() allows you to render Blog Posts anywhere on your website's frontend, even on non-Blog pages.

<?php
/**
 * Given a PageArray of blog entries generate and return the output.
 *
 * @access public
 * @param PageArray|Page $posts The entries to generate output for
 * @param bool $small Set to true if you want summarized versions of posts (default = false)
 * @return $out string The generated output
 *
 */
 public function renderPosts($posts, $small = false)

As you can see from the above code, the method renderPosts() takes two arguments, $posts and $small.

The first argument $posts can either be a ProcessWire Page|PageArray (read more here about Page and PageArray) or a string that the method will use in a selector to retrieve Blog Posts. The string must be formatted as a valid ProcessWire field=value selector. This argument is required (i.e. must be specified even if empty; see below).

The second argument $small has to be boolean and by default is set to false. This argument controls whether your Blog Posts will be rendered in full or summarised/truncated. You can set maximum length of text to show before truncation takes place from within the Blog manager screen once you've logged into your ProcessWire admin. If $small is set to true, the default length of text before truncation kicks in is 450, but as I said, you can set your own value. Let's look at some examples of how to use renderPosts() and its arguments.

Passing $posts as a string

When you call and pass the first parameter $posts as a string to renderPosts(),  it will find Blog Posts, sort them by date descending (i.e. newest post first) as well as applying your string in the selector (assuming it was a valid selector. More on this below). For instance, assuming you wanted to limit the number of results returned by renderPosts(), you could simply do the following in your Template File:

<?php
/**** RENDER 10 BLOG POSTS IN FULL ****/
//first we call MarkupBlog
$blog = $modules->get("MarkupBlog");
//we want to pass this as a string to the selector renderPosts() will use to find Blog Posts
$limit = 10;

//Having called MarkupBlog, all its methods are now available to us.
//We render a maximum of 10 Blog Posts in full. Note how we pass the first argument as a string
echo $blog->renderPosts("limit={$limit}");

You notice that we didn't specify the second argument of the method. This is because we were happy to let the default stand, i.e. $small=false. This means, we wanted our posts to be rendered in full. In case we wanted the Blog Posts to be truncated (e.g. as a summary on your home page), we would call the method like this.

<?php
/**** RENDER 5 SUMMARISED BLOG POSTS ****/
//first we call MarkupBlog
$blog = $modules->get("MarkupBlog");
//we will later pass this as a string to the selector renderPosts() to limit number of Blog Posts returned
$limit = 5;

//We render a maximum of 5 summarised Blog Posts
echo $blog->renderPosts("limit={$limit}", true);

Now let's pass renderPosts() a two-part selector string. Suppose we want to only show a limited number of Blog Posts by one Blog Author (or even group of authors). This is easy to do as follows.

<?php
$limit = 5;
//get this author by ID. we'll use this in our selector
$author = $users->get('authorname')->id;

//pass the variables $limit and $author as a string to our selector to find 5 Blog Posts by this author
echo $blog->renderPosts("limit={$limit}, created_users_id={$author}");

In some cases, you may wish not to pass any selector to renderPosts(). In this case, just indicate the first argument as an empty string as shown below. This is because if you don't specify this argument you will get an error.

<?php
echo $blog->renderPosts('');

//OR as below if you want to truncate posts as well
echo $blog->renderPosts('', true);

Passing $posts as a Page|PageArray

The beauty and strength of passing the first argument $posts to renderPosts() as a Page or PageArray is the many possibilities this offers. You can first retrieve (and save to a variable), mix and match, apply various filters, etc to Blog Posts using the powerful ProcessWire API before rendering the output. For instance, you can grab Blog Posts that meet a certain criteria - e.g. published within certain dates, that have a certain number of comments, by certain authors, etc. You then pass these to renderPosts() to output on the frontend. Let's look at some examples.

In the code below, we look for Blog Posts that have been commented on more than 3 times. We then pass the resulting PageArray to renderPosts().

<?php
//Find Blog Posts with more than 3 comments
$posts = $pages->find("template=blog-post, blog_comments.count>3");
$blog = $modules->get("MarkupBlog");
//if Blog Posts found, we render them out
if ($posts) {
echo $blog->renderPosts($posts);
}

else {
echo '<p>No posts found</p>';
}

In this second example, we look for Blog Posts published within a certain date range, limiting the find to 10 Posts.

<?php
//Find Posts published between two dates
$posts = $pages->find("blog_date>=15.5.2013, blog_date<=15.8.2014, template=blog-post, limit=10");
$blog = $modules->get("MarkupBlog");
//If Posts found, output them
if ($posts) {
echo $blog->renderPosts($posts);
}

else {
echo '<p>No posts found</p>';
}

OK, let's now turn our attention to the HTML output that renderPosts() produces and how we can target the CSS attributes in the output.

renderPosts() HTML output

Below are commented sample HTML outputs of renderPosts(). Note, the output will somewhat vary depending on whether the second argument $small is set to false or true. The HTML tags contain quite a number of Class attributes enabling you to target and style the output as you wish.

Notice the different bits of the output such as the pagination at the bottom, number of comments, post meta-line, etc. Additionally, if you are logged in and have the permision to edit a Blog Post, an edit link to the Blog Post is shown. Clicking on that will open that Post in a ProcessWire Admin edit page window. 

This code shows example HTML output of renderPosts($posts), i.e. with the default argument $small=false (full post).

<div class="posts">
 <div class="post" id="2550">
  <div class="post-head">
   <a class="num-comments-icon" href="/pwtests/blog/posts/yosemite-national-park/#comments" title="5 Comments">5</a>
   <h2 class="post-headline"><a href="/pwtests/blog/posts/yosemite-national-park/">Yosemite National Park</a></h2>

   <!-- Post meta-line showing Post Author and Post Date and Time -->
   <p class="post-byline"><span class="author">Posted by <a href="/pwtests/blog/authors/john/">John Smith</a></span>, <span class="date">15 April 2014 11:00 am</span></p>
  </div>
  <div class="post-body">
   <!-- This output is pulled in from blog_body [i.e. what you entered in the RTE] -->
   <p><strong>Yosemite National Park</strong> is a United States National Park spanning eastern portions of Tuolumne, Mariposa and Madera counties in the central eastern portion of the U.S. state of California.</p>
   <p>Yosemite is one of the largest and least fragmented habitat blocks in the Sierra Nevada, and the park supports a diversity of plants and animals. The park has an elevation range from 2,127 to 13,114 feet (648 to 3,997 m) and contains five majorvegetation zones.</p>
  </div>
  <!-- The Post's 'footer' showing Post Categories, Tags and Number of Comments -->
  <div class="post-foot">
   <!-- Post Categories -->
   <p class="categories"><span>Categories:</span><a href="/pwtests/blog/categories/amazing/">Amazing</a>, <a href="/pwtests/blog/categories/the-wild/">The Wild</a>, <a href="/pwtests/blog/categories/best-in-class/">Best in Class</a></p>
   <!-- Post Tags -->
   <p class="tags"><span>Tags:</span><a href="/pwtests/blog/tags/parks/">Parks</a>, <a href="/pwtests/blog/tags/great-outdoors/">Great Outdoors</a></p>
   <!-- Post Number of Comments -->
   <p class="num-comments"><span>Comments:</span> <a href="/pwtests/blog/posts/yosemite-national-park/#comments">5 Comments</a></p>
  </div>
 </div>
</div>
 
<!-- Posts' pagination. This is only output if number of Posts exceeds the set limit to retrieve at a time -->
<ul class="MarkupPagerNav">
 <li class="MarkupPagerNavOn MarkupPagerNavFirst MarkupPagerNavFirstNum"><a href="/pwtests/blog/"><span>1</span></a></li>
 <li><a href="/pwtests/blog/page2"><span>2</span></a></li>
 <li><a href="/pwtests/blog/page3"><span>3</span></a></li>
 <li><a href="/pwtests/blog/page4"><span>4</span></a></li>
 <li class="MarkupPagerNavSeparator">€¦</li>
 <li class="MarkupPagerNavLast MarkupPagerNavLastNum"><a href="/pwtests/blog/page7"><span>7</span></a></li>
 <li class="MarkupPagerNavNext MarkupPagerNavLast"><a href="/pwtests/blog/page2"><span>Next</span></a></li>
</ul>

In case you wanted to use a particular CSS Framework to structure the output, it is easy to wrap the output in your own HTML tags. Below is an example code using PocketGrid CSS.

<div id="wrapper" class="block-group">
 <div class="block">
 
 <?php 
 $limit = 10;
 $blog = $modules->get("MarkupBlog");
 echo $blog->renderPosts("limit={$limit}");
 ?>

 </div>
</div>

The code below shows example output HTML when $small=true, i.e. renderPosts($posts, true).

<!-- Number of visible Posts -->
<h3>Posts 1 to 1 of 17</h3>
<div class="posts posts-small">
 <div class="post" id="5095">
 <div class="post-head">
  <a class="num-comments-icon" href="/pwtests/blog/posts/a-story-about-a-man/#comments" title="No comments yet">0</a>
  <h4 class="post-headline"><a href="/pwtests/blog/posts/a-story-about-a-man/">A story about a man</a></h4>
  <p class="post-byline"><span class="author">Posted by <a href="/pwtests/blog/authors/peter/">Peter Samsonite</a></span>, <span class="date">13 August 2014 11:35 pm</span></p>
 </div>
 <div class="post-body">
  <!-- Summarised Post content from blog_body. Also notice the 'view more' link -->
  <p>This is one of the greatest stories every€¦ <a class="more" href="/pwtests/blog/posts/a-story-about-a-man/">View More</a></p>
 </div>
 </div>
</div>
<!-- Notice no Post footer info, i.e. no Post Categories, Tags and Number of Comments -->

<!-- Posts' pagination. This is only output if number of Posts exceeds the set limit to retrieve at a time -->
<ul class="MarkupPagerNav">
 <li class="MarkupPagerNavOn MarkupPagerNavFirst MarkupPagerNavFirstNum"><a href="/pwtests/blog/"><span>1</span></a></li>
 <li><a href="/pwtests/blog/page2"><span>2</span></a></li>
 <li><a href="/pwtests/blog/page3"><span>3</span></a></li>
 <li><a href="/pwtests/blog/page4"><span>4</span></a></li>
 <li><a href="/pwtests/blog/page5"><span>5</span></a></li>
 <li><a href="/pwtests/blog/page6"><span>6</span></a></li>
 <li><a href="/pwtests/blog/page7"><span>7</span></a></li>
 <li><a href="/pwtests/blog/page8"><span>8</span></a></li>
 <li><a href="/pwtests/blog/page9"><span>9</span></a></li>
 <li><a href="/pwtests/blog/page10"><span>10</span></a></li>
 <li class="MarkupPagerNavSeparator">€¦</li>
 <li class="MarkupPagerNavLast MarkupPagerNavLastNum"><a href="/pwtests/blog/page17"><span>17</span></a></li>
 <li class="MarkupPagerNavNext MarkupPagerNavLast"><a href="/pwtests/blog/page2"><span>Next</span></a></li>
</ul>

For your convenience, below are all the CSS Classes output by renderPosts() in the order in which the appear. Note that some tags have multiple classes.

renderPosts() CSS Classes

div.posts {} /*if $small=true => div.posts, div.posts-small*/
div.post {}
div.post-head {}
a.num-comments-icon {}
h2.post-headline {} /*if $small=true => h4.post-headline*/
p.post-byline {}
span.author {}
span.date {}
div.post-body {}
a.more {} /*only when $small=true*/
div.post-foot {}
p.categories {} /*only when $small=false*/
p.tags {} /*only when $small=false*/
p.num-comments {} /*only when $small=false*/
ul.MarkupPagerNav {}
li.MarkupPagerNavOn, li.MarkupPagerNavFirst, li.MarkupPagerNavFirstNum {}
li.MarkupPagerNavSeparator {}
li.MarkupPagerNavLast, li.MarkupPagerNavLastNum {}
li.MarkupPagerNavNext, li.MarkupPagerNavLast {}

Summary

In this lesson we looked at the MarkupBlog method for rendering posts - renderPosts($posts, $small = false). We've seen how versatile it is, enabling us to fine tune the Blog Post output to our needs. Next, we'll look at other methods in MarkupBlog.