For my portfolio site I wanted each image node (CCK + imagefield) to have a thumbnail strip of 10 or so images from the same category. Very simple stuff I thought. A quick search and I came across fantastic module called Custom Pagers by Eaton. This highly flexible module provides you a Next and Previous custom pager that you can display in your node pages. This was perfect for blog nodes but I wanted more control over the pager and I only wanted nodes to be pulled out from the same taxonomy term as the node being displayed.. fairly simple idea:
- hook_nodeapi - so we can intercept the current node
- Identify the term we want to target (you will need to adapt this for your own taxonomy)
- Pass the NID and TID to our custom pager function
- Select nodes from the db and process them
- return results to hook_nodeapi and add to node object
- print your custom pager in the node template
Example

Here is what the code looks like:
Step 1
Setup the hook_nodeapi
<?php
function mymodule_nodeapi(&$node, $op, $a3 = NULL, $a4 = NULL){
switch($op){
case 'view':
//only apply to "mynode" node type
if($node->type == "mynode" and $a3 == null and $a4 != null){
//loop through taxonomy if you need to
foreach ($node->taxonomy as $term_obj){
//if its the right term vocab..
// do your custom code here
if($term_obj->vid == 1){
//thumbnail custom pager
$node->node_thumbnail_nav = mymodule_node_thumbnail_nav($node->nid, $term_obj->tid);
}
}
}
break;
}
}
?>Step 2
Function to return the custom pager nodes
<?php
function mymodule_node_thumbnail_nav($nid, $tid){
// current one will be added to the total later,
// make sure number is always 1 less than the TOTAL displayed
$total_thumbnails_to_display = 10;
$left = ceil(($total_thumbnails_to_display) / 2);
$right = floor(($total_thumbnails_to_display) / 2);
$next_nids_array = mymodule_node_thumbnail_nav_db($nid, $tid, 'more', $total_thumbnails_to_display);
$previous_nids_array = mymodule_node_thumbnail_nav_db($nid, $tid, 'less', $total_thumbnails_to_display);
// if we dont have enough next (newer) items, pad with previous
if(count($next_nids_array) < $right){
$previous_nids_array = array_splice($previous_nids_array, 0, $total_thumbnails_to_display - count($next_nids_array));
}
// if we dont have enough previous (older) items, pad with next
elseif(count($previous_nids_array) < $left){
$next_nids_array = array_splice($next_nids_array, 0, $total_thumbnails_to_display - count($previous_nids_array));
}
// all good, splice in the center to get both left (older) and right (newer) nodes
else{
$previous_nids_array = array_splice($previous_nids_array, 0, $left);
$next_nids_array = array_splice($next_nids_array, 0, $right);
}
//merge left and right and add current node
$all_nids_array = array_merge($next_nids_array, array($nid), $previous_nids_array);
// sort the list
sort($all_nids_array);
//check if there is something to work with
if(count($all_nids_array) != 0){
//we have our list, lets work though it
foreach($all_nids_array as $available_nid){
$node_obj = node_load($available_nid);
$current_nid_class = "";
//for the current nid we need a custom class to identify it
if($available_nid == $nid){
$current_nid_class=' current_nid';
}
$image = $node_obj->field_image_attach[0]['filepath'];
$linked_image = l(theme('imagecache', 'photo_mini', $image, $node_obj->title, $node_obj->title), 'node/' . $node_obj->nid, array('html'=>true));
$thumbs .= "<div class=\"thumbnail_item{$current_nid_class}\">{$linked_image}</div>";
}
return "<div class=\"thumbnail_container\">{$thumbs}</div>";
}
}
?>Step 3
MySql DB query stuff
<?php
function mymodule_node_thumbnail_nav_db($nid, $tid, $op='more', $limit=10){
if($op == 'more'){ $op = '>'; $order = "ASC";}
else{ $op = '<'; $order = "DESC";}
$sql = "
SELECT
node.nid
FROM
node
Inner Join term_node ON node.nid = term_node.nid
WHERE
node.type = 'mynode' AND
node.status = 1 AND
node.moderate = 0 AND
node.nid %s %d AND
term_node.tid = %d
ORDER BY node.nid %s
LIMIT %d
";
$nids_array = array();
$result = db_query($sql, $op, $nid, $tid, $order, $limit);
while($row = db_fetch_object($result)){
$nids_array[] = $row->nid;
}
return $nids_array;
}
?>Step 4
Edit your node template and add
<?php
if($node->node_thumbnail_nav){ $print $node->node_thumbnail_nav;}
?>Step 5
Customise the output with your own CSS
For a working demo, check any of the nodes from portfolio section of my site.
Your thoughts and comments are most welcome.

















2 comments
22nd Oct, 09
That's a pretty cool way to paginate. Excellent tutorial.
23rd Oct, 09
Good stuff, I'll be using this in a website I'm working on.
Post new comment