<pedrocorreia.net ⁄>
corner
<mySearch ⁄> <mySearch ⁄>

corner
 
corner
<mySnippets order="rand" ⁄> <mySnippets order="rand" ⁄>

corner
 
corner
<myContacts ⁄> <myContacts ⁄>

<email ⁄>


pc@pedrocorreia.net

<windows live messenger ⁄>


pedrojacorreia@hotmail.com

<myCurriculum type="pdf" ⁄>


Download
corner
 
corner
<myBlog show="last" ⁄> <myBlog show="last" ⁄>

corner
 
corner
<myNews show="rand" ⁄> <myNews show="rand" ⁄>

corner
 
corner
<myNews type="cat" ⁄> <myNews type="cat" ⁄>

corner
 
corner
<myQuote order="random" ⁄> <myQuote order="random" ⁄>

corner
 
corner
<myPhoto order="random" ⁄> <myPhoto order="random" ⁄>

<pedrocorreia.net ⁄>
corner
 
corner
<myAdSense ⁄> <myAdSense ⁄>

corner
 
corner
<myVisitorsMap ⁄> <myVisitorsMap ⁄>

corner
 
 

<Yet Another Pagination Bar ⁄ >




clicks: 8145 8145 2008-01-20 2008-01-20 goto mySnippets mySnippets php  Download  Bookmark This Bookmark This



Bem, primeiro de tudo não quero que fiquem a pensar que eu tenho uma queda para paginação ^_^''

Mas pronto, vou dar mais um exemplo de paginação de registos. Já tinha dedicado um snippet a falar sobre este tema, a principal diferença para este, é que vão existir n links consoante o número de páginas, isto faz com que, se por exemplo, estivermos a paginar um conjunto de 1000 registos, tendo 10 por página, vamos ter 100 páginas, o que se poderá tornar um pouco grande a paginação.


Neste snippet, vamos optar por outra forma de apresentação, a barra de paginação vai-se adaptando à página que estamos a visitar, ou seja, podemos definir um range de páginas que queiramos que apareça na listagem.


Para diversificar um pouco mais do outro snippet, vamos recorrer ao PHP5, para programar este snippet.

nota importante: vou re-aproveitar o código que já tinha utilizado no snippet Construir Toolbar vista-style, por isso se quiserem podem dar uma vista de olhos pelo snippet (caso ainda não o tenham visto) para ficar +/- como uma ideia. Basicamente, o que vamos fazer é adicionar mais funcionalidades à nossa tiny-mini-micro-piccolo-small, dai a principal importância da modulação do código, uma das grandes vantagens da OOP, mas isso já são outras conversas. Como tal não vou novamente colocar o código das Classes usadas no snippet da toolbar, para não tornar este snippet ainda maior.



style.css - vamos ter um ficheiro de estilos, que é praticamente igual ao outro, só fiz uma pequena alteração

  1. /****** <layout> ******/
  2. body{font-family: Tahoma, Verdana, Arial, sans-serif;font-size: 8pt;color: #000;}
  3. /****** <layout /> ******/
  4.  
  5. /****** <paginacao> ******/
  6. .pages{padding: 0;margin: auto auto auto 12px;text-align: center;}
  7. .pages a, .pages span{
  8. display: block;margin: 1px; width:16px auto; height: 13px; float: left;
  9. padding: 0.2em 0.5em;border: 1px solid #666;background: #fff;
  10. }
  11. .pages span.current{background: #FF7F55;color: #fff;}
  12. .pages a{text-decoration: none;}
  13. .pages a:hover{background: #FF6600;color: #fff;}
  14. .pages a.current{background: #FF7F55;color: #fff;}
  15. .pages a.current:hover{color: #FFFF99;}
  16. /****** <paginacao /> ******/
  17.  
  18. /****** <misc> ******/
  19. a{color: #FF5500;text-decoration: underline;}
  20. a:hover{color: #0080D5;text-decoration: none;}
  21. /****** <misc /> ******/


- AutoLoad.inc - para evitar andar a fazer sempre includes (neste caso não seriam muitos, mas num projecto seria mais demorado), vamos implementar uma magic function do php - __autoload, assim que fôr necessário usar uma class, automaticamente esta função é chamada e irá fazer o include a esse ficheiro.

  1. <?php
  2. //class para automaticamente fazer o load das classes
  3. if(function_exists("__autoload")) return;{
  4. function __autoload($class){
  5. include_once("class.$class.php");
  6. }
  7. }
  8. ?>




- settings.inc - ficheiro que contém algumas definições da nossa paginação
  1. <?php
  2. define("LNG_PAGINACAO_PAGINA","Página");
  3. define("LNG_PAGINACAO_DE","de");
  4. define("LNG_PAGINACAO_SELECIONADA","(selecionada)");
  5.  
  6. define("LNG_BAR_FIRST","First");
  7. define("LNG_BAR_PREVIOUS","Previous");
  8. define("LNG_BAR_NEXT","Next");
  9. define("LNG_BAR_LAST","Last");
  10.  
  11. define("BAR_PER_PAGE",10);
  12. define("BAR_PAGES_INTERVAL",11);
  13.  
  14. define("LNG_WEBPAGE_TITLE","My Custom Pagination");
  15. define("CHARSET","iso-8859-1");
  16.  
  17. define("DIV_ID","pages");
  18. ?>





Até aqui nada de novo a apontar.

Vamos então criar a nossa classe propriamente dita. Optei por recorrer a uma interface, talvez neste caso não fosse necessário, mas fica também para verem uma breve introdução às interfaces.

Basicamente o que a interface vai fazer é definir conjunto de funções que terão de ser implementadas por quem (class) fôr usá-la, ou seja, é definido um conjunto de requisitos necessários (métodos) para que um determinado "problema" seja resolvido, depois a maneira como esses métodos são implementados é totalmente alheio à interface, serve também para padronizar, mas deiam uma vista de olhos pelo link que explica bem melhor :D


- class.IMyPagination.php
  1. <?php
  2. /**
  3. * Interface MyPagination
  4. *
  5. * Especifica métodos a serem implementados
  6. *
  7. * @author pedrocorreia.net
  8. *
  9. */
  10. interface IMyPagination{
  11.  
  12. /**
  13. * Método Construtor
  14. *
  15. * @param String $id Nome do Div
  16. * @param Int $cur_page Página corrent
  17. * @param Int $num_records Número de registos
  18. * @param Int $per_page Itens por página
  19. * @param Int $interval Intervalo de páginas que aparecem visiveis
  20. * @param String $class Class href
  21. * @param String $class_selected Class da página selecionada
  22. * @param Array $arr_page_indicators Indicadores de inicio de fim da paginação
  23. * @param String $webpage Página para onde será feito o pedido
  24. */
  25. function __construct($id,$cur_page,$num_records,$per_page,$interval,$class="",$class_selected="",$arr_page_indicators="",$webpage="");
  26.  
  27. /**
  28. * Atribuir a página corrent
  29. *
  30. * @param Int $cur_page
  31. */
  32. function SetCurPage($page);
  33.  
  34. /**
  35. * Obter página corrente
  36. *
  37. * @return Int
  38. */
  39. function GetCurPage();
  40.  
  41. /**
  42. * Atribuir a próxima página
  43. *
  44. */
  45. function SetNextPage();
  46.  
  47. /**
  48. * Obter a página seguinte
  49. *
  50. * @return Int
  51. */
  52. function GetNextPage();
  53.  
  54. /**
  55. * Atribuir a página anterior
  56. *
  57. */
  58. function SetPrevPage();
  59.  
  60. /**
  61. * Obter a página anterior
  62. *
  63. * @return Int
  64. */
  65. function GetPrevPage();
  66.  
  67. /**
  68. * Atribuir o intervalo de páginas
  69. * Se não forem especificados intervalos (recomendado)
  70. * o cálculo é feito automaticamente
  71. *
  72. * @param Int $start_pos Onde começa a paginação
  73. * @param Int $end_pos Onde termina a paginação
  74. */
  75. function SetIntervalPageDelimiters($start="",$end="");
  76.  
  77. /**
  78. * Obter paginação
  79. *
  80. * @return String
  81. */
  82. function Parse();
  83.  
  84. }
  85. ?>




Agora vamos então implementar a nossa interface, atenção que temos de respeitar a interface, ou seja temos de programar todos os seus métodos, mas podemos adicionar métodos que não estejam na interface, tanto métodos públicos como privados, neste caso apenas adicionei métodos privados; bem como podemos adicionar as propriedades/ atributos à classe, atributos esses que não poderão ser/estar definidos na interface.






- class.MyPagination.php
  1. <?php
  2. include_once("settings.inc");
  3.  
  4. /**
  5. * Class MyPagination
  6. * Constrói paginação
  7. *
  8. * @author pedrocorreia.net
  9. *
  10. */
  11. class MyPagination implements IMyPagination {
  12. private $_id;
  13.  
  14. private $_class;
  15. private $_class_selected="current";
  16.  
  17. private $_cur_page=1;
  18. private $_next_page=2;
  19. private $_prev_page=0;
  20.  
  21. private $_num_pages;
  22. private $_per_page;
  23.  
  24. private $_interval;
  25.  
  26. private $_page_delimiter_start_at;
  27. private $_page_delimiter_end_at;
  28.  
  29. private $_web_page;
  30. private $_arr_page_indicators;
  31.  
  32. function __construct($id,$cur_page,$num_records,$per_page,$interval,$class="",$class_selected="",$arr_page_indicators="",$webpage=""){
  33. $this->_id=$id;
  34. $this->_per_page=$per_page;
  35. if($class) $this->_class=$class;
  36. if($class_selected) $this->_class_selected=$class_selected;
  37. $this->_interval=$interval;
  38.  
  39. if($arr_page_indicators) {
  40. $this->_arr_page_indicators=$arr_page_indicators;
  41. }
  42. else{ //valores por omissão
  43. $this->_arr_page_indicators=array(LNG_BAR_FIRST,LNG_BAR_PREVIOUS,LNG_BAR_NEXT,LNG_BAR_LAST);
  44. }
  45.  
  46. $this->_web_page=($webpage)?$webpage:$_SERVER['PHP_SELF'];
  47. $this->_num_pages=ceil($num_records/$this->_per_page);
  48. $this->SetCurPage($cur_page);
  49. }
  50.  
  51. public function SetCurPage($cur_page){
  52. if(!$cur_page || !is_numeric($cur_page)) $cur_page=1;
  53.  
  54. $this->_cur_page=$cur_page;
  55. $this->SetNextPage();
  56. $this->SetPrevPage();
  57. }
  58.  
  59. public function GetCurPage(){return $this->_cur_page;}
  60.  
  61. public function SetNextPage(){
  62. if($this->GetCurPage()<$this->_num_pages){$this->_next_page=$this->GetCurPage()+1;}
  63. else{$this->_next_page=1;}
  64. }
  65.  
  66. public function GetNextPage(){return $this->_next_page;}
  67.  
  68. public function SetPrevPage(){
  69. if($this->GetCurPage()-1>0){$this->_prev_page=$this->GetCurPage()-1;}
  70. else{$this->_prev_page=$this->_num_pages;}
  71. }
  72.  
  73. public function GetPrevPage(){return $this->_prev_page;}
  74.  
  75. public function SetIntervalPageDelimiters($start_pos="",$end_pos=""){
  76. if($start_pos>0 && $end_pos>0){
  77. $this->_page_delimiter_start_at=$start_pos;
  78. $this->_page_delimiter_end_at=$end_pos;
  79. return ;
  80. }
  81.  
  82. //definir intervalos superior e inferior
  83. //relativamente à página actual
  84. $interval=intval($this->_interval/2);
  85. if($this->_interval % 2==0) {
  86. $start_at=$this->_cur_page-$interval;
  87. }
  88. else{
  89. $interval++;
  90. $start_at=$this->_cur_page-$interval+1;
  91. }
  92. $end_at=$this->_cur_page+$interval-1;
  93.  
  94. //isto acontece quando nos encontramos
  95. //no inicio ou no fim da listagem,
  96. //faz com que o intervalo de páginas
  97. //se mantenha sempre igual
  98. $aux_diff=$this->GetCurPage()+$interval;
  99. if($aux_diff>$this->_num_pages+1){
  100. $start_at-=$aux_diff-$this->_num_pages-1;
  101. }
  102. //
  103.  
  104. //verificar limites superiores e inferiores
  105. if($end_at>$this->_num_pages){$end_at=$this->_num_pages;}
  106. if($start_at<1){
  107. $start_at=1;
  108. $end_at=$this->_interval;
  109. }
  110. //
  111.  
  112. $this->_page_delimiter_start_at=$start_at;
  113. $this->_page_delimiter_end_at=$end_at;
  114. }
  115.  
  116. public function Parse(){
  117. //senão existirem registos suficientes a paginação não é construída
  118. if($this->_num_pages<$this->_per_page) return ;
  119.  
  120. $const=get_defined_constants();
  121. $this->SetIntervalPageDelimiters();
  122.  
  123. //construir paginação no invervalo pretendido
  124. for ($i=$this->_page_delimiter_start_at;$i<=$this->_page_delimiter_end_at;$i++){
  125. $title="{$const['LNG_PAGINACAO_PAGINA']} $i {$const['LNG_PAGINACAO_DE']} {$this->_num_pages}";
  126.  
  127. if ($i==$this->_cur_page){
  128. $title.=$const['LNG_PAGINACAO_SELECIONADA'];
  129. $href=new HRef("href_$i","{$this->_web_page}?page=$i",$i,$title,$this->_class_selected);
  130. $middle_pagination_bar.=$href->ParseObject();
  131. }
  132. else{
  133. $href=new HRef("href_$i","{$this->_web_page}?page=$i",$i,$title);
  134. $middle_pagination_bar.=$href->ParseObject();
  135. }
  136. }
  137. //
  138.  
  139. $complete_pagination_bar=$this->_BuildLeftMostItens().$middle_pagination_bar.$this->_BuildRightMostItens();
  140.  
  141. $div=new Div($this->_id,$complete_pagination_bar,"pages");
  142. $result=$div->ParseObject();
  143.  
  144. return $result;
  145. }
  146.  
  147. /**
  148. * Método privado
  149. * Obter os itens mais à esquerda da paginação
  150. *
  151. * @return String
  152. */
  153. private function _BuildLeftMostItens(){
  154. if(!$this->_arr_page_indicators[0] || !$this->_arr_page_indicators[1]) return ;
  155. //primeiras páginas
  156. $txt=$this->_arr_page_indicators[0];
  157. $href=new HRef("left_href_1","{$this->_web_page}?page=1",$txt,$txt);
  158. $left_pagination_bar=$href->ParseObject();
  159.  
  160. $txt=$this->_arr_page_indicators[1];
  161. $href=new HRef("left_href_2","{$this->_web_page}?page={$this->GetPrevPage()}",$txt,$txt);
  162. $left_pagination_bar.=$href->ParseObject();
  163.  
  164. return $left_pagination_bar;
  165. }
  166.  
  167. /**
  168. * Método privado
  169. * Obter os itens mais à direita da paginação
  170. *
  171. * @return String
  172. */
  173. private function _BuildRightMostItens(){
  174. if(!$this->_arr_page_indicators[2] || !$this->_arr_page_indicators[3]) return ;
  175. //últimas páginas
  176. $txt=$this->_arr_page_indicators[2];
  177. $href=new HRef("left_href_3","{$this->_web_page}?page={$this->GetNextPage()}",$txt,$txt);
  178. $right_pagination_bar=$href->ParseObject();
  179.  
  180. $txt=$this->_arr_page_indicators[3];
  181. $href=new HRef("left_href_4","{$this->_web_page}?page={$this->_num_pages}",$txt,$txt);
  182. $right_pagination_bar.=$href->ParseObject();
  183.  
  184. return $right_pagination_bar;
  185. }
  186. }
  187. ?>





Também aqui não vamos utilizar uma única linha de html para gerar a nossa barra de paginação:

- index.php
  1. <?php
  2. include_once("Classes/AutoLoad.inc");
  3. include_once("Classes/settings.inc");
  4.  
  5. //valor de exemplo
  6. //normalmente este número vai ser obtido
  7. //através de um "select count ..." à tabela
  8. $num_records=200;
  9.  
  10. $my_pagination=new MyPagination(DIV_ID,$_GET["page"],$num_records,BAR_PER_PAGE,BAR_PAGES_INTERVAL);
  11. $html=new Html(LNG_WEBPAGE_TITLE,$my_pagination->Parse(),"css/style.css",CHARSET);
  12.  
  13. $output = new Output();
  14. $output->AddElement($html->Parse());
  15. $output->Parse();
  16. ?>






Em baixo podemos ver uma breve animação em flash que mostra a barra de paginação:










Qualquer erro/ dúvida é só dizer.









clicks: 8145 8145 2008-01-20 2008-01-20 goto mySnippets mySnippets php  Download  Bookmark This Bookmark This