一个巧妙的分页方法

PHP是一个Web脚本语言,在Web应用中最常见的莫过于列表显示。所以页码生成也就犹为常用。 最近我索性写了一个,在生成思想上, 有一些技巧拿与大家分享:

先说说需求: 显示的页码数是$size, 当前的页数是$page, 总数是$total, 每页显示的条数是$page_size

首先,要获取总页面数是多少:

  1.      $total_page = ceil($total/$page_size);
  2.  

这样的写法是不是更简单一些呢?
其次,我是这样想的, 这个需求最高的需求是要根据当前的页码,找出size个页码数来。
那么就可以转化为: 根据当前的信息, 填充一个size个元素的数组。
最终就可以简单的转化为:根据当前的信息,寻找出size个元素的数组的起始元素是什么?我们假设这个起始元素是:page_start;

  1.         $page_start = 1;
  2.         $half = intval($size/2);
  3.         $page_start = max(1, $page - $half);
  4.         $page_end = min($page_start + $size - 1, $total_page);
  5.         $page_start = max(1, $page_end - $size + 1);
  6.  

这样写,是不是也很有技巧呢?

最后就简单了, 根据起始页和结束页, 生成一个数组, 最后foreach这个数组,生成html代码:

  1.    $page_numbers = range($page_start, $page_end);
  2.    $nav_str = "";
  3.    foreach($page_numbers as $num){
  4.       //.......
  5.    }
  6.  

源码:

  1. /**
  2. *A pagination generation class
  3. *@class : Pagination
  4. *@version: 1.0.0
  5. *@author : huixinchen at baidu.com
  6. *@useage:
  7. * $pagi = new Pagination($url_prefix, $page_size, $mesgs_count, $pagination_size=10, array $conf);
  8. * $navigation_str = $pagi->generate($current_page_number);
  9. */
  10. class Pagination{
  11.         private $page, $total_page, $total, $page_size, $size;
  12.         private $prev_str = "&lt", $next_str = "&gt";
  13.         private $class, $selected_class = "selected", $prev_class="prev", $next_class="next",
  14.                 $de_prev_class="de_prev", $de_next_class="de_next";
  15.         private $url_prefix="", $split_char="?";
  16.         private $para_name = "page", $target = "";
  17.         public function Pagination($url_prefix, $page_size, $total, $size=10, $conf=array()){
  18.                 $this->page = 1;
  19.                 $this->page_size = $page_size;
  20.                 $this->total = $total;
  21.                 $this->total_page = intval(ceil($total/$page_size));
  22.                 $this->size = $size;
  23.                 if(!empty($conf)){
  24.                         $configure = array("prev_str", "next_str", "class", "selected_class");
  25.                         foreach($conf as $key => $val){
  26.                                 if(in_array($key, $configure)){
  27.                                         $this->$val = $val;
  28.                                 }
  29.                         }
  30.                 }
  31.                 $this->url_prefix = $url_prefix;
  32.                 if(strstr($url_prefix, '?') !== false){
  33.                         $this->url_prefix .= "&" . $this->para_name . "=";
  34.                 }else{
  35.                         $this->url_prefix .= "?" . $this->para_name . "=";
  36.                 }
  37.         }
  38.  
  39.         public function generate($page){
  40.                 $this->page = $page;
  41.                 if(isset($this->page[$page])){
  42.                         return $this->page_str[$page];
  43.                 }
  44.                 $page_start = 1;
  45.                 $half = intval($this->size/2);
  46.                 $page_start = max(1, $page - $half);
  47.                 $page_end = min($page_start + $this->size - 1, $this->total_page);
  48.                 $page_start = max(1, $page_end - $this->size + 1);
  49.  
  50.                 $this->page_str[$page] = $this->build_nav_str($page_start, $page_end);
  51.                 return $this->page_str[$page];
  52.         }
  53.  
  54.         private function build_nav_str($page_start, $page_end){
  55.                 $page_nums = range($page_start, $page_end);
  56.                 $target = $this->target? " target=\"{$this->target}\"" : "";
  57.                 if($this->page == 1){
  58.                         $page_str = <<<HTML
  59.                         <span class="{$this->de_prev_class}"> {$this->prev_str} </span>
  60. HTML;
  61.                 }else{
  62.                         $page = $this->page - 1;
  63.                         $page_str = <<<HTML
  64.                         <span class="{$this->prev_class}"> <a href="{$this->url_prefix}{$page}"{$this->target}>{$this->prev_str}</a></span>
  65. HTML;
  66.                 }
  67.                 foreach($page_nums as $p){
  68.                         $page_str .= ($p == $this->page) ? <<<HTML
  69.                         <span class="{$this->selected_class}">{$p}</span>
  70. HTML
  71.                         : <<<HTML
  72.                         <span class="{$this->class}"><a href="{$this->url_prefix}{$p}"{$this->target}>{$p}</a></span>
  73. HTML;
  74.  
  75.                 }
  76.                 if($this->page == $this->total_page){
  77.                         $page_str .= <<<HTML
  78.                         <span class="{$this->de_next_class}"> {$this->next_str} </span>
  79. HTML;
  80.                 }else{
  81.                         $page = $this->page + 1;
  82.                         $page_str .= <<<HTML
  83.                         <span class="{$this->next_class}"> <a href="{$this->url_prefix}{$page}"{$this->target}>{$this->next_str}</a></span>
  84. HTML;
  85.                 }
  86.                 return $page_str;
  87.         }
  88.  
  89.         public function tidy_str(){
  90.                 ;//void
  91.         }
  92.  
  93.         public function __call($func_name, $arguments){
  94.                 if(isset($this->$func_name)){
  95.                         return $this->$func_name;
  96.                 }
  97.         }
  98.  
  99.         public function __destruct(){
  100.                 unset($this->page_str);
  101.                 unset($this);
  102.         }
  103. }
Advertisements

发表评论

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / 更改 )

Twitter picture

You are commenting using your Twitter account. Log Out / 更改 )

Facebook photo

You are commenting using your Facebook account. Log Out / 更改 )

Google+ photo

You are commenting using your Google+ account. Log Out / 更改 )

Connecting to %s