Paged content using Movable Type!

This is a test with paged "more" text... implemented using a couple of PHP tricks. :)

Read on to see it in action and to see how it's done.

The implementation of paged content is pretty simple. I'll use this test entry to explain how I did it. First of all, you'll need PHP 4 installed on your server. You can use this same technique with other server-side tools like ASP, ColdFusion, etc., but this solution explains how to do it with PHP.

The end result of all this is that you can page your blog entry using a token like "<pb/>". (PB = page break, get it?)

On to page 2!

First, set your individual archive file extension to your PHP file extension ('php' usually, or whatever your server recognizes). Now, add the following PHP code to your individual archive template:

<?php
function bloggerPagedBody($b,$a = '') {
  // $b is the body of content to output
  // $a is a defined anchor
  global $HTTP_GET_VARS;
  global $PHP_SELF;
  $page = 1; // default page
  if ($HTTP_GET_VARS['page']) {
    // page # is specified
    $page = $HTTP_GET_VARS['page'];
  }
  // split content into an array of pages
  // note: preg_split requires the Perl-compatible regex
  // extension for PHP. If you don't have this installed,
  // you can do something similar with the PHP split function.
  // I chose preg_split because I wanted a case-insensitive
  // token to split pages.
  $paged_body = preg_split("/<pb *\/>/i", $b);
  $total_pages = count($paged_body);
  // if requested page is out of the bounds of our
  // paged content, default to displaying page 1
  if (($page > $total_pages) || ($page < 1)) {
    $page = 1;
  }
  // select the proper page of content
  $b = $paged_body[$page-1];
  // format the anchor if one was specified
  if ($a) {
    $a = "#$a";
  }
  // if more than 1 page was in the content,
  // format output to show which page we are looking
  // at (unless we're looking at page 1) and also
  // display a mini-navbar for the other available pages.
  if ($total_pages > 1) {
    if ($page > 1) {
      $b = "<div>(this"         ." is page $page of $total_pages)</div>\n" . $b;
    }
    $b .= "<div><font size=\"2\"><b>page:</b> ";
    for ($i = 1; $i <= $total_pages; $i++) {
      if ($i == $page) {
        $b .= "<b>$i</b>";
      } else {
        if ($i > 1) {
          $b .= "<a href=\"$PHP_SELF?page=$i$a\">$i</a>";
        } else {
          $b .= "<a href=\"$PHP_SELF$a\">$i</a>";
        }
      }
      if ($i < $total_pages) {
        $b .= ", ";
      }
    }
    $b .= "</font></div>\n";
  }
  return $b;
}
?>

Now lets look at what you have to do with your template and discuss the side-effects of using this technique. Page 3 is next.

Next, modify your Individual Archive template to output your "MORE" text using this function. Here's how my template handles the blog and more entries:

<?php
  // only display the main entry text if we're looking at the first page.
  if (!$HTTP_GET_VARS['page'] || $HTTP_GET_VARS['page'] == 1) { ?>
<$MTEntryBody$>
<?php
  }
?>

<a name="more"></a>
<?php echo bloggerPagedBody("<$MTEntryMore encode_php="qq"$>") ?>

And that's it!

In order to really pull this off, you'll also need to use MT 2.0 (which allows for escaping content properly for PHP), or use the patch I made, available here.

Finally, you can link to specific pages within your entry by using syntax like this: <a href="?page=2">page 2</a>

4 Comments

christina said:

HI!

I'm trying to make this work, and I'm gettin this error

Warning: Missing argument 2 for bloggerpagedbody() in /home/.delmanblender/cwodtke/boxesandarrows/beta/archives/002328.php on line 9

Also, you dont' say where to put the first code block. I put it in the head, with comments like javascript.

I'm not a php head, as you may have guessed.

Ben over at MT told me to check out your PHP for pagination.

From the looks of it, I'd have to insert a <pb/> in my blog entry wherever I want to paginate the text, right? Although your code would solve my issue, I'd prefer a solution that automatically paginates.

I'm working on a WAP (WML) version of my blog and would like to find a solution that will paginate based on the number of characters in the entry. Take a look at my post http://www.movabletype.org/support/ib3/ikonboard.cgi?s=3cd97ec3df2effff;act=ST;f=14;t=579;hl=new on MT for details. Could your PHP script be modified to automatically paginate every 1024 characters (including XHTML tags and all)? I know VERY little PHP, but I'm willing to learn it if this will solve my problem.

darren said:

Hey Brad... great mod... you can see it in action in a few days at http://nasty.cx

Stephen said:

If you want to keep things simple and let the main text body be page 1 and the extended text body be page 2 - the following modification of the script in the template will automatically paginate your post into 2 pages and insert urls to toggle between them

<?php
// only display the main entry text if we're looking at the first page.
if (!$HTTP_GET_VARS['page'] || $HTTP_GET_VARS['page'] == 1) { ?>
<MTEntryIfExtended>[ page 1 | <a href="?page=2">page 2</a> ]
</MTEntryIfExtended><$MTEntryBody$>
<?php
} else { ?>
<a name="more"></a>[ <a href="?page=1">page 1</a> | page 2 ]
<?php
echo bloggerPagedBody("<$MTEntryMore encode_php="qq"$>");
}
?>

About

This article was published on November 3, 2001 10:19 AM.

The article previously posted was free.aol.com.

The next article is Movable Type 1.2.

Many more can be found on the home page or by looking through the archives.

Powered by Movable Type