Pager with thumbnails

Last modified: August 26, 2009 - 22:46

Based on the original code in Add a << first < previous next > last >> Pager to Image Nodes Within a Gallery. I thought this might be useful as well. Following code shows the current, 2 previous and 2 next thumbnails, with a link to the corresponding pages:

<?php
function custom_pager($current_nid, $class = NULL) {
 
$tid = reset(array_keys(taxonomy_node_get_terms($current_nid)));
 
$result = db_query(db_rewrite_sql('SELECT n.nid, n.title, f.filepath FROM {node} n INNER JOIN {term_node} tn INNER JOIN {files} f ON n.nid = tn.nid AND n.nid = f.nid WHERE tn.tid = %s AND n.status = 1 AND f.filename = \'%s\' ORDER BY n.sticky DESC, n.created DESC, n.nid DESC'), $tid, 'thumbnail');
  while (
$node = db_fetch_object($result)) {
   
$nodes[++$i] = $node;
    if (
$node->nid == $current_nid) $x = $i;
  }

  if (
$i < 6) {
    while (++
$j <= $i) {
     
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$j]->filepath)) . ' />', 'node/'. $nodes[$j]->nid, array('title' => check_plain($nodes[$j]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
    }
  }
  else {
    switch (
$x) {
      case
1:
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$i-1]->filepath)) . ' />', 'node/'. $nodes[$i-1]->nid, array('title' => check_plain($nodes[$i-1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$i]->filepath)) . ' />', 'node/'. $nodes[$i]->nid, array('title' => check_plain($nodes[$i]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[1]->filepath)) . ' />', 'node/'. $nodes[1]->nid, array('title' => check_plain($nodes[1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[2]->filepath)) . ' />', 'node/'. $nodes[2]->nid, array('title' => check_plain($nodes[2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[3]->filepath)) . ' />', 'node/'. $nodes[3]->nid, array('title' => check_plain($nodes[3]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
        break;
      case
2:
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$i]->filepath)) . ' />', 'node/'. $nodes[$i]->nid, array('title' => check_plain($nodes[$i]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[1]->filepath)) . ' />', 'node/'. $nodes[1]->nid, array('title' => check_plain($nodes[1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[2]->filepath)) . ' />', 'node/'. $nodes[2]->nid, array('title' => check_plain($nodes[2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[3]->filepath)) . ' />', 'node/'. $nodes[3]->nid, array('title' => check_plain($nodes[3]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[4]->filepath)) . ' />', 'node/'. $nodes[4]->nid, array('title' => check_plain($nodes[4]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
        break;
      case
$i-1:
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-2]->filepath)) . ' />', 'node/'. $nodes[$x-2]->nid, array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-1]->filepath)) . ' />', 'node/'. $nodes[$x-1]->nid, array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x]->filepath)) . ' />', 'node/'. $nodes[$x]->nid, array('title' => check_plain($nodes[$x]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$i]->filepath)) . ' />', 'node/'. $nodes[$i]->nid, array('title' => check_plain($nodes[$i]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[1]->filepath)) . ' />', 'node/'. $nodes[1]->nid, array('title' => check_plain($nodes[1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
        break;
      case
$i:
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-2]->filepath)) . ' />', 'node/'. $nodes[$x-2]->nid, array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-1]->filepath)) . ' />', 'node/'. $nodes[$x-1]->nid, array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x]->filepath)) . ' />', 'node/'. $nodes[$x]->nid, array('title' => check_plain($nodes[$x]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[1]->filepath)) . ' />', 'node/'. $nodes[1]->nid, array('title' => check_plain($nodes[1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[2]->filepath)) . ' />', 'node/'. $nodes[2]->nid, array('title' => check_plain($nodes[2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
        break;
      default:
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-2]->filepath)) . ' />', 'node/'. $nodes[$x-2]->nid, array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x-1]->filepath)) . ' />', 'node/'. $nodes[$x-1]->nid, array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x]->filepath)) . ' />', 'node/'. $nodes[$x]->nid, array('title' => check_plain($nodes[$x]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x+1]->filepath)) . ' />', 'node/'. $nodes[$x+1]->nid, array('title' => check_plain($nodes[$x+1]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
       
$output .= l('<img src=' . check_url(url('system/files/' . $nodes[$x+2]->filepath)) . ' />', 'node/'. $nodes[$x+2]->nid, array('title' => check_plain($nodes[$x+2]->title), 'class' => $class), NULL, NULL, FALSE, TRUE);
    }
  }
  return
$output;
}
?>

For this code to work, copy the original node.tpl.php to node-image.tpl.php and add the following code where you want the thumbnails to appear:

<?php
if ($page != 0 && $terms) { print custom_pager($node->nid); }
?>

Any comment, especially security related, is highly appreciated.

drupal 6.x version

teagle - January 26, 2009 - 21:31

For Drupal 6.8 I had to change the sql, a few $node references and the l() function, so in case this is useful for anyone else...

function goes in template.php:

<?php

function custom_pager($current_nid, $class = NULL) {
 
$tid = reset(array_keys(taxonomy_node_get_terms($current_nid)));

 
// drupal 6.x: compared to the sql above, an extra inner join for the {image} table is added,
  // as {files} doesn't have an nid column.
 
$result = db_query(db_rewrite_sql('SELECT n.nid, n.title, f.filepath FROM {node} AS n INNER JOIN {term_node} AS tn INNER JOIN {image} AS i  INNER JOIN {files} AS f ON n.nid = tn.nid AND n.nid = i.nid AND f.fid = i.fid WHERE tn.tid = %s AND n.status = 1 AND f.filename = \'%s\' ORDER BY n.sticky DESC, n.created DESC, n.nid DESC'), $tid, 'thumbnail');
  while (
$node = db_fetch_object($result)) {
   
$nodes[++$i] = $node;
   
//  drupal 6.x: $current_nid spits out the whole node Object, so now it's $current_nid->nid
   
if ($node->nid == $current_nid->nid) $x = $i;
  }

  if (
$i < 6) {
    while (++
$j <= $i) {

     
//  drupal 6.x: all the l() functions from here onwards have been rewritten so that the <a> attributes show up
      // and so that the <img> code is properly interpreted as html rather than shown as text.
      // Also, the filepath in drupal 6 doesn't seem to need the hard-coded 'system/files/' part in the original version

     
$output .= l('<img src="' . check_url(url( $nodes[$j]->filepath)) . '" />', 'node/'. $nodes[$j]->nid, array('attributes' => array('title' => check_plain($nodes[$j]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
    }
  }
  else {
    switch (
$x) {

       
// in all cases below there are five links & thumbnails:
        // two to 'previous' nodes, one for the current node, then two to 'next' nodes.
        // If you don't want the current node showing a linked thumbnail,
        // change or remove the 3rd '$output .= ...' line from each switch case

       
case 1:
       
// if the current node is the first in the gallery, show the last two nodes in the gallery as 'previous' links
           
$output .= l('<img src="' . check_url(url( $nodes[$i-1]->filepath)) . '" />', 'node/'. $nodes[$i-1]->nid, array('attributes' => array('title' => check_plain($nodes[$i-1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$i]->filepath)) . '" />', 'node/'. $nodes[$i]->nid, array('attributes' => array('title' => check_plain($nodes[$i]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[1]->filepath)) . '" />', 'node/'. $nodes[1]->nid, array('attributes' => array('title' => check_plain($nodes[1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[2]->filepath)) . '" />', 'node/'. $nodes[2]->nid, array('attributes' => array('title' => check_plain($nodes[2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[3]->filepath)) . '" />', 'node/'. $nodes[3]->nid, array('attributes' => array('title' => check_plain($nodes[3]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
        break;

        case
2:
       
// if the current node is the second in the gallery, show the first and the last nodes in the gallery as 'previous' links
           
$output .= l('<img src="' . check_url(url( $nodes[$i]->filepath)) . '" />', 'node/'. $nodes[$i]->nid, array('attributes' => array('title' => check_plain($nodes[$i]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[1]->filepath)) . '" />', 'node/'. $nodes[1]->nid, array('attributes' => array('title' => check_plain($nodes[1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[2]->filepath)) . '" />', 'node/'. $nodes[2]->nid, array('attributes' => array('title' => check_plain($nodes[2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[3]->filepath)) . '" />', 'node/'. $nodes[3]->nid, array('attributes' => array('title' => check_plain($nodes[3]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[4]->filepath)) . '" />', 'node/'. $nodes[4]->nid, array('attributes' => array('title' => check_plain($nodes[4]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
        break;

        case
$i-1:
       
// if the current node is the penultimate in the gallery, show the last and the first nodes in the gallery as 'next' links
           
$output .= l('<img src="' . check_url(url( $nodes[$x-2]->filepath)) . '" />', 'node/'. $nodes[$x-2]->nid, array('attributes' => array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x-1]->filepath)) . '" />', 'node/'. $nodes[$x-1]->nid, array('attributes' => array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x]->filepath)) . '" />', 'node/'. $nodes[$x]->nid, array('attributes' => array('title' => check_plain($nodes[$x]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$i]->filepath)) . '" />', 'node/'. $nodes[$i]->nid, array('attributes' => array('title' => check_plain($nodes[$i]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[1]->filepath)) . '" />', 'node/'. $nodes[1]->nid, array('attributes' => array('title' => check_plain($nodes[1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
        break;

        case
$i:
       
// if the current node is the last in the gallery, show the first two nodes in the gallery as 'next' links
           
$output .= l('<img src="' . check_url(url( $nodes[$x-2]->filepath)) . '" />', 'node/'. $nodes[$x-2]->nid, array('attributes' => array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x-1]->filepath)) . '" />', 'node/'. $nodes[$x-1]->nid, array('attributes' => array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x]->filepath)) . '" />', 'node/'. $nodes[$x]->nid, array('attributes' => array('title' => check_plain($nodes[$x]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[1]->filepath)) . '" />', 'node/'. $nodes[1]->nid, array('attributes' => array('title' => check_plain($nodes[1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[2]->filepath)) . '" />', 'node/'. $nodes[2]->nid, array('attributes' => array('title' => check_plain($nodes[2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
        break;

        default:
       
// if the current node somewhere in the middle of the gallery, do the normal 'previous' 2 and 'next' 2 links
           
$output .= l('<img src="' . check_url(url( $nodes[$x-2]->filepath)) . '" />', 'node/'. $nodes[$x-2]->nid, array('attributes' => array('title' => check_plain($nodes[$x-2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x-1]->filepath)) . '" />', 'node/'. $nodes[$x-1]->nid, array('attributes' => array('title' => check_plain($nodes[$x-1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x]->filepath)) . '" />', 'node/'. $nodes[$x]->nid, array('attributes' => array('title' => check_plain($nodes[$x]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x+1]->filepath)) . '" />', 'node/'. $nodes[$x+1]->nid, array('attributes' => array('title' => check_plain($nodes[$x+1]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
           
$output .= l('<img src="' . check_url(url( $nodes[$x+2]->filepath)) . '" />', 'node/'. $nodes[$x+2]->nid, array('attributes' => array('title' => check_plain($nodes[$x+2]->title), 'class' => $class), 'query' => NULL, 'fragment' => NULL, 'absolute' => FALSE, 'html' => TRUE));
    }
  }
  return
$output;
}
?>

Then in node-image.tpl.php (or wherever you want it?), using $node instead of $node->nid put the call to the function in template.php:

    <?php
   
if ($page != 0 && $terms) { print custom_pager($node); }
   
?>

I'm no programmer, so I hope this doesn't lead anyone up the garden path...

 
 

Drupal is a registered trademark of Dries Buytaert.