page = max(1, (int)$page); $this->perPage = in_array($perPage, $perPageOptions) ? (int)$perPage : 20; $this->perPageOptions = $perPageOptions; } public static function fromRequest() { $page = $_GET['page'] ?? $_POST['page'] ?? 1; $perPage = $_GET['per_page'] ?? $_POST['per_page'] ?? 20; return new self($page, $perPage); } public function getOffset() { return ($this->page - 1) * $this->perPage; } public function getLimit() { return $this->perPage; } public function getPage() { return $this->page; } public function getPerPage() { return $this->perPage; } public function setTotal($total) { $this->total = $total; } public function getTotal() { return $this->total; } public function getTotalPages() { return (int)ceil($this->total / $this->perPage); } public function hasNextPage() { return $this->page < $this->getTotalPages(); } public function hasPrevPage() { return $this->page > 1; } public function getNextPage() { return $this->page + 1; } public function getPrevPage() { return $this->page - 1; } public function toArray() { return [ 'page' => $this->page, 'per_page' => $this->perPage, 'total' => $this->total, 'total_pages' => $this->getTotalPages(), 'has_next' => $this->hasNextPage(), 'has_prev' => $this->hasPrevPage(), 'next_page' => $this->hasNextPage() ? $this->getNextPage() : null, 'prev_page' => $this->hasPrevPage() ? $this->getPrevPage() : null ]; } public function getLimitSql() { return "LIMIT {$this->perPage} OFFSET {$this->getOffset()}"; } }