PageRenderTime 48ms CodeModel.GetById 23ms RepoModel.GetById 0ms app.codeStats 0ms

/classes/view/generic/pagination.php

https://github.com/anqh/core
PHP | 328 lines | 151 code | 73 blank | 104 comment | 37 complexity | 2b4d0c7cda16067832bb752667068cdc MD5 | raw file
  1. <?php defined('SYSPATH') or die('No direct access allowed.');
  2. /**
  3. * Pagination view.
  4. *
  5. * @package Anqh
  6. * @author Antti Qvickström
  7. * @copyright (c) 2012 Antti Qvickström
  8. * @license http://www.opensource.org/licenses/mit-license.php MIT license
  9. */
  10. class View_Generic_Pagination extends View_Base {
  11. /**
  12. * @var boolean Hide pagination if only 1 page
  13. */
  14. public $auto_hide = true;
  15. /**
  16. * @var string Base URL
  17. */
  18. public $base_url;
  19. /**
  20. * @var integer Current page number
  21. */
  22. public $current_page;
  23. /**
  24. * @var string Text for first page
  25. */
  26. public $first_text = '&laquo;';
  27. /**
  28. * @var string First page URL
  29. */
  30. public $first_url;
  31. /**
  32. * @var integer How many items to show per page
  33. */
  34. public $items_per_page;
  35. /**
  36. * @var string Text for last page
  37. */
  38. public $last_text = '&raquo;';
  39. /**
  40. * @var string Last page URL
  41. */
  42. public $last_url;
  43. /**
  44. * @var string Text for next page
  45. */
  46. public $next_text = '&rsaquo;';
  47. /**
  48. * @var string Next page URL
  49. */
  50. public $next_url;
  51. /**
  52. * @var integer Pagination offset for SQL
  53. */
  54. public $offset;
  55. /**
  56. * @var string Query string parameter
  57. */
  58. public $parameter = 'page';
  59. /**
  60. * @var string Text for previous page
  61. */
  62. public $previous_text = '&lsaquo;';
  63. /**
  64. * @var string Previous page URL
  65. */
  66. public $previous_url;
  67. /**
  68. * @var integer Total item count
  69. */
  70. public $total_items;
  71. /**
  72. * @var integer Total page count
  73. */
  74. public $total_pages;
  75. /**
  76. * Create new pagination.
  77. *
  78. * @param array $setup
  79. */
  80. public function __construct(array $setup = null) {
  81. parent::__construct();
  82. if ($setup) {
  83. foreach ($setup as $key => $value) {
  84. $this->{$key} = $value;
  85. }
  86. }
  87. $this->setup();
  88. }
  89. /**
  90. * Go to page with item.
  91. *
  92. * @param integer $item
  93. * @return View_Generic_Pagination
  94. */
  95. public function item($item) {
  96. // Calculate new page
  97. $this->current_page = ceil((int)$item / $this->items_per_page);
  98. $this->previous_url = null;
  99. $this->next_url = null;
  100. $this->offset = null;
  101. return $this->setup();
  102. }
  103. /**
  104. * Go to last page.
  105. *
  106. * @return View_Generic_Pagination
  107. */
  108. public function last() {
  109. $this->current_page = $this->total_pages;
  110. return $this->setup();
  111. }
  112. /**
  113. * Pager style pagination.
  114. *
  115. * @return string
  116. */
  117. private function _pager() {
  118. ob_start();
  119. ?>
  120. <ul class="pager">
  121. <?php if ($this->first_url): ?>
  122. <li class="previous"><?= HTML::anchor($this->first_url, $this->first_text) ?></li>
  123. <?php endif; ?>
  124. <?php if ($this->previous_url): ?>
  125. <li class="previous"><?= HTML::anchor($this->previous_url, $this->previous_text) ?></li>
  126. <?php endif; ?>
  127. <?php if ($this->current_page): ?>
  128. <li class="disabled"><a><?= $this->current_page ?></a></li>
  129. <?php endif; ?>
  130. <?php if ($this->last_url): ?>
  131. <li class="next"><?= HTML::anchor($this->last_url, $this->last_text) ?></li>
  132. <?php endif; ?>
  133. <?php if ($this->next_url): ?>
  134. <li class="next"><?= HTML::anchor($this->next_url, $this->next_text) ?></li>
  135. <?php endif; ?>
  136. </ul>
  137. <?php
  138. return ob_get_clean();
  139. }
  140. /**
  141. * Pagination style pagination.
  142. *
  143. * @return string
  144. */
  145. private function _pagination() {
  146. // Build range
  147. if ($this->total_pages > 15) {
  148. $first = max($this->current_page - 2, 1);
  149. $last = min($this->current_page + 2, $this->total_pages);
  150. } else {
  151. $first = 1;
  152. $last = $this->total_pages;
  153. }
  154. $range = range($first, $last);
  155. // Add gaps
  156. if ($first > 1) {
  157. if ($first > 10) {
  158. array_unshift($range, floor($first / 2));
  159. }
  160. array_unshift($range, 1);
  161. }
  162. if ($last < $this->total_pages) {
  163. if ($this->total_pages - $last > 10) {
  164. $range[] = ceil(($this->total_pages - $last) / 2) + $last;
  165. }
  166. $range[] = $this->total_pages;
  167. }
  168. ob_start();
  169. $previous = 1;
  170. ?>
  171. <div class="pagination pagination-centered">
  172. <ul>
  173. <?php if ($this->previous_url): ?>
  174. <li class="previous"><?= HTML::anchor($this->previous_url, $this->previous_text) ?></li>
  175. <?php else: ?>
  176. <li class="previous disabled"><span><?= $this->previous_text ?></span></li>
  177. <?php endif; ?>
  178. <?php foreach ($range as $page): ?>
  179. <?php if ($page - $previous > 1): ?>
  180. <li class="disabled"><span>&hellip;</span></li>
  181. <?php endif; ?>
  182. <li<?= $page == $this->current_page ? ' class="active"' : '' ?>><?= HTML::anchor($this->url($page), $page) ?></li>
  183. <?php $previous = $page; endforeach; ?>
  184. <?php if ($this->next_url): ?>
  185. <li class="next"><?= HTML::anchor($this->next_url, $this->next_text) ?></li>
  186. <?php else: ?>
  187. <li class="next disabled"><span><?= $this->next_text ?></span></li>
  188. <?php endif; ?>
  189. </ul>
  190. </div>
  191. <?php
  192. return ob_get_clean();
  193. }
  194. /**
  195. * Render view.
  196. *
  197. * @return string
  198. */
  199. public function render() {
  200. $this->setup();
  201. return $this->total_pages ? $this->_pagination() : $this->_pager();
  202. }
  203. /**
  204. * Setup pagination.
  205. *
  206. * @return View_Generic_Pagination
  207. */
  208. public function setup() {
  209. if ($this->total_pages === null && $this->total_items && $this->items_per_page) {
  210. $this->total_pages = (int)ceil($this->total_items / $this->items_per_page);
  211. }
  212. if ($this->current_page === null && $this->total_pages) {
  213. $page = Arr::get($_GET, $this->parameter, 1);
  214. $this->current_page = $page == 'last' ? $this->total_pages : (int)$page;
  215. }
  216. if ($this->previous_url === null && $this->current_page > 1) {
  217. $this->previous_url = $this->url($this->current_page - 1);
  218. }
  219. if ($this->next_url === null && $this->current_page < $this->total_pages) {
  220. $this->next_url = $this->url($this->current_page + 1);
  221. }
  222. if ($this->first_url === null && $this->total_pages && $this->current_page > 1) {
  223. $this->first_url = $this->url(1);
  224. }
  225. if ($this->last_url === null && $this->total_pages && $this->current_page < $this->total_pages) {
  226. $this->last_url = $this->url(-1);
  227. }
  228. if ($this->offset === null && $this->items_per_page) {
  229. $this->offset = max(0, $this->current_page - 1) * $this->items_per_page;
  230. }
  231. return $this;
  232. }
  233. /**
  234. * Generates the full URL for a certain page.
  235. *
  236. * @param integer $page
  237. * @return string
  238. */
  239. public function url($page = 1) {
  240. // Last page
  241. if ($page === -1 && $this->total_pages) {
  242. $page = $this->total_pages;
  243. }
  244. // Clean the page number
  245. $page = max(1, (int)$page);
  246. // No page number in URLs to first page
  247. if ($page === 1) {
  248. $page = null;
  249. }
  250. list($uri) = $this->base_url ? array($this->base_url) : explode('?', Request::current()->current_uri());
  251. $query = $_GET;
  252. $query[$this->parameter] = $page;
  253. return URL::site($uri) . URL::query($query);
  254. }
  255. }