From 72253380e60222238592f5449c7c29051d6a092b Mon Sep 17 00:00:00 2001 From: murilohp Date: Sat, 4 Jan 2025 01:53:14 -0300 Subject: [PATCH 1/8] Add some methods to the page renderer to make easier to get the first item, the last item and the total of items. --- system/Pager/PagerRenderer.php | 77 ++++++++++++++++++++++++ tests/system/Pager/PagerRendererTest.php | 52 ++++++++++++++++ 2 files changed, 129 insertions(+) diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index 64c4c40c531d..7db834833417 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -82,6 +82,27 @@ class PagerRenderer */ protected $pageSelector; + /** + * The number of items a page. + * + * @var int|null + */ + protected $perPage; + + /** + * The total items the current has started. + * + * @var int|null + */ + protected $perPageStart; + + /** + * The total items of the current page; + * + * @var int|null + */ + protected $perPageEnd; + /** * Constructor. */ @@ -98,6 +119,8 @@ public function __construct(array $details) $this->pageCount = $details['pageCount']; $this->segment = $details['segment'] ?? 0; $this->pageSelector = $details['pageSelector'] ?? 'page'; + $this->perPage = $details['perPage'] ?? null; + $this->updatePerPages(); } /** @@ -307,6 +330,28 @@ protected function updatePages(?int $count = null) $this->last = $this->current + $count <= $this->pageCount ? $this->current + $count : (int) $this->pageCount; } + /** + * Updates the start and end items per pages, which is + * the number of items displayed on the active page. + */ + protected function updatePerPages(): void + { + if ($this->total === null || $this->perPage === null) { + return; + } + + // When the page is the last, performs a different calculation. + if ($this->last === $this->current) { + $this->perPageStart = $this->perPage * ($this->current - 1) + 1; + $this->perPageEnd = $this->total; + + return; + } + + $this->perPageStart = $this->current === 1 ? 1 : ($this->perPage * $this->current) - $this->perPage + 1; + $this->perPageEnd = $this->perPage * $this->current; + } + /** * Checks to see if there is a "previous" page before our "first" page. */ @@ -430,4 +475,36 @@ public function getNextPageNumber(): ?int { return ($this->current === $this->pageCount) ? null : $this->current + 1; } + + /** + * Returns the total items of the page. + */ + public function getTotal(): ?int + { + return $this->total; + } + + /** + * Returns the number of items to be displayed on the page. + */ + public function getPerPage(): ?int + { + return $this->perPage; + } + + /** + * Returns the number of items the page starts with. + */ + public function getPerPageStart(): ?int + { + return $this->perPageStart; + } + + /** + * Returns the number of items the page ends with. + */ + public function getPerPageEnd(): ?int + { + return $this->perPageEnd; + } } diff --git a/tests/system/Pager/PagerRendererTest.php b/tests/system/Pager/PagerRendererTest.php index 8ac8683a4327..8d0095854374 100644 --- a/tests/system/Pager/PagerRendererTest.php +++ b/tests/system/Pager/PagerRendererTest.php @@ -15,6 +15,7 @@ use CodeIgniter\HTTP\URI; use CodeIgniter\Test\CIUnitTestCase; +use PHPUnit\Framework\Attributes\DataProvider; use PHPUnit\Framework\Attributes\Group; /** @@ -619,4 +620,55 @@ public function testGetNextPageNumberNull(): void $this->assertNull($pager->getNextPageNumber()); } + + #[DataProvider('providePageStartEnd')] + public function testPageStartEnd(array $details, int $pageStart, int $pageEnd): void + { + $pager = new PagerRenderer($details); + $pager->setSurroundCount(2); + + $this->assertSame($pager->getPerPageStart(), $pageStart); + $this->assertSame($pager->getPerPageEnd(), $pageEnd); + } + + public static function providePageStartEnd(): iterable + { + $uri = new URI('http://example.com/foo'); + + return [ + 'first page' => [ + 'details' => [ + 'uri' => $uri, + 'pageCount' => 3, + 'total' => 25, + 'currentPage' => 1, + 'perPage' => 10, + ], + 'pageStart' => 1, + 'pageEnd' => 10, + ], + 'second page' => [ + 'details' => [ + 'uri' => $uri, + 'pageCount' => 3, + 'total' => 25, + 'currentPage' => 2, + 'perPage' => 10, + ], + 'pageStart' => 11, + 'pageEnd' => 20, + ], + 'last page' => [ + 'details' => [ + 'uri' => $uri, + 'pageCount' => 3, + 'total' => 25, + 'currentPage' => 3, + 'perPage' => 10, + ], + 'pageStart' => 21, + 'pageEnd' => 25, + ], + ]; + } } From fa9bf84a697794ae1c5ecc32e58c868638d7de84 Mon Sep 17 00:00:00 2001 From: murilohp Date: Sat, 4 Jan 2025 13:20:28 -0300 Subject: [PATCH 2/8] Add type hint to the new per page variable on the page renderer. --- system/Pager/PagerRenderer.php | 12 +++--------- 1 file changed, 3 insertions(+), 9 deletions(-) diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index 7db834833417..9076fed28dc0 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -84,24 +84,18 @@ class PagerRenderer /** * The number of items a page. - * - * @var int|null */ - protected $perPage; + protected ?int $perPage; /** * The total items the current has started. - * - * @var int|null */ - protected $perPageStart; + protected ?int $perPageStart; /** * The total items of the current page; - * - * @var int|null */ - protected $perPageEnd; + protected ?int $perPageEnd; /** * Constructor. From f369cb9e1b772886bc56f09ce91770b4c386cfa5 Mon Sep 17 00:00:00 2001 From: murilohp Date: Sat, 4 Jan 2025 16:43:51 -0300 Subject: [PATCH 3/8] Create more tests for the page start and end, and improve the comment of the variables from the PagerRenderer class. --- system/Pager/PagerRenderer.php | 6 ++--- tests/system/Pager/PagerRendererTest.php | 28 ++++++++++++++++++++++++ 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index 9076fed28dc0..173f2c4b79f1 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -83,17 +83,17 @@ class PagerRenderer protected $pageSelector; /** - * The number of items a page. + * The maximum number of items displayed per page. */ protected ?int $perPage; /** - * The total items the current has started. + * The index of the first item on the current page. */ protected ?int $perPageStart; /** - * The total items of the current page; + * The index of the last item on the current page.s */ protected ?int $perPageEnd; diff --git a/tests/system/Pager/PagerRendererTest.php b/tests/system/Pager/PagerRendererTest.php index 8d0095854374..7f97c9c10a9f 100644 --- a/tests/system/Pager/PagerRendererTest.php +++ b/tests/system/Pager/PagerRendererTest.php @@ -621,6 +621,9 @@ public function testGetNextPageNumberNull(): void $this->assertNull($pager->getNextPageNumber()); } + /** + * @param array> $details + */ #[DataProvider('providePageStartEnd')] public function testPageStartEnd(array $details, int $pageStart, int $pageEnd): void { @@ -631,6 +634,9 @@ public function testPageStartEnd(array $details, int $pageStart, int $pageEnd): $this->assertSame($pager->getPerPageEnd(), $pageEnd); } + /** + * @return array> $details + */ public static function providePageStartEnd(): iterable { $uri = new URI('http://example.com/foo'); @@ -669,6 +675,28 @@ public static function providePageStartEnd(): iterable 'pageStart' => 21, 'pageEnd' => 25, ], + 'current greater last page' => [ + 'details' => [ + 'uri' => $uri, + 'pageCount' => 3, + 'total' => 25, + 'currentPage' => 5, + 'perPage' => 10, + ], + 'pageStart' => 41, + 'pageEnd' => 50, + ], + 'current equal last page' => [ + 'details' => [ + 'uri' => $uri, + 'pageCount' => 1, + 'total' => 10, + 'currentPage' => 1, + 'perPage' => 10, + ], + 'pageStart' => 1, + 'pageEnd' => 10, + ], ]; } } From 9878718e7a497d9b533daea38d5974412cd20124 Mon Sep 17 00:00:00 2001 From: murilohp Date: Sat, 4 Jan 2025 19:22:06 -0300 Subject: [PATCH 4/8] Add a documentation and also improve some comments. --- system/Pager/PagerRenderer.php | 6 ++--- .../source/libraries/pagination.rst | 25 +++++++++++++++++++ .../source/libraries/pagination/019.php | 7 ++++++ 3 files changed, 35 insertions(+), 3 deletions(-) create mode 100644 user_guide_src/source/libraries/pagination/019.php diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index 173f2c4b79f1..e54df4af2804 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -83,17 +83,17 @@ class PagerRenderer protected $pageSelector; /** - * The maximum number of items displayed per page. + * Returns the number of results per page that should be shown. */ protected ?int $perPage; /** - * The index of the first item on the current page. + * The number of items the page starts with. */ protected ?int $perPageStart; /** - * The index of the last item on the current page.s + * The number of items the page ends with. */ protected ?int $perPageEnd; diff --git a/user_guide_src/source/libraries/pagination.rst b/user_guide_src/source/libraries/pagination.rst index ed5567372324..4f037ba44ba1 100644 --- a/user_guide_src/source/libraries/pagination.rst +++ b/user_guide_src/source/libraries/pagination.rst @@ -340,3 +340,28 @@ getPageCount() -------------- This method returns total number of pages. + +Displaying the Number of Items on the Page +========================================== + +.. warning:: The methods `getTotal()`, `getPerPage()`, `getPerPageStart()`, and `getPerPageEnd()` were introduced in v4.6.0. + +When paginating items, it’s often helpful to display the total number of items and the range of items shown on the current page. To simplify this task, new methods have been added. These methods make it easier to manage and display pagination details. Here's an example: + +.. literalinclude:: pagination/019.php + +getTotal() +---------- +Returns the total items of the page. + +getPerPage() +------------ +Returns the number of items to be displayed on the page. + +getPerPageStart() +----------------- +Returns the number of items the page starts with. + +getPerPageEnd() +--------------- +Returns the number of items the page ends with. diff --git a/user_guide_src/source/libraries/pagination/019.php b/user_guide_src/source/libraries/pagination/019.php new file mode 100644 index 000000000000..91c514948111 --- /dev/null +++ b/user_guide_src/source/libraries/pagination/019.php @@ -0,0 +1,7 @@ +setSurroundCount(1) ?> + +

+ Showing getPerPageStart() ?> + to getPerPageEnd() ?> + of getTotal() ?> results +

From ce162e24afb6bb7f1f4e5ea30636e3b3fba77f56 Mon Sep 17 00:00:00 2001 From: murilohp Date: Sun, 5 Jan 2025 14:16:14 -0300 Subject: [PATCH 5/8] Use version added instead of warning on the documentation --- user_guide_src/source/libraries/pagination.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/user_guide_src/source/libraries/pagination.rst b/user_guide_src/source/libraries/pagination.rst index 4f037ba44ba1..27abfa7a1604 100644 --- a/user_guide_src/source/libraries/pagination.rst +++ b/user_guide_src/source/libraries/pagination.rst @@ -344,7 +344,7 @@ This method returns total number of pages. Displaying the Number of Items on the Page ========================================== -.. warning:: The methods `getTotal()`, `getPerPage()`, `getPerPageStart()`, and `getPerPageEnd()` were introduced in v4.6.0. +.. versionadded:: 4.6.0 When paginating items, it’s often helpful to display the total number of items and the range of items shown on the current page. To simplify this task, new methods have been added. These methods make it easier to manage and display pagination details. Here's an example: From 224719184fbd239da501b73dad2450fcbcabc10c Mon Sep 17 00:00:00 2001 From: murilohp Date: Mon, 6 Jan 2025 09:26:03 -0300 Subject: [PATCH 6/8] Add changelog. --- user_guide_src/source/changelogs/v4.6.0.rst | 6 ++++++ user_guide_src/source/libraries/pagination.rst | 2 ++ 2 files changed, 8 insertions(+) diff --git a/user_guide_src/source/changelogs/v4.6.0.rst b/user_guide_src/source/changelogs/v4.6.0.rst index db4e8abaa07b..e2632007c4bc 100644 --- a/user_guide_src/source/changelogs/v4.6.0.rst +++ b/user_guide_src/source/changelogs/v4.6.0.rst @@ -246,6 +246,12 @@ Negotiator Previously, response with language headers ``Accept-language: en-US,en-GB;q=0.9`` returned the first allowed language ``en`` could instead of the exact language ``en-US`` or ``en-GB``. Set the value to ``true`` to enable comparison not only by language code ('en' - ISO 639-1) but also by regional code ('en-US' - ISO 639-1 plus ISO 3166-1 alpha). +Pagination +========== + +- Added a new feature to get the total and the range number of items of the current page. + See the section ``Displaying the Number of Items on the Page`` of the :ref:`displaying-the-number-of-items-on-the-page` for more details. + Testing ======= diff --git a/user_guide_src/source/libraries/pagination.rst b/user_guide_src/source/libraries/pagination.rst index 27abfa7a1604..f718bab28fc6 100644 --- a/user_guide_src/source/libraries/pagination.rst +++ b/user_guide_src/source/libraries/pagination.rst @@ -341,6 +341,8 @@ getPageCount() This method returns total number of pages. +.. _displaying-the-number-of-items-on-the-page: + Displaying the Number of Items on the Page ========================================== From 5b8459444643001763e952dfa8fda1a4ecf704c6 Mon Sep 17 00:00:00 2001 From: murilohp Date: Mon, 6 Jan 2025 18:25:53 -0300 Subject: [PATCH 7/8] Fix CR issues. --- system/Pager/PagerRenderer.php | 2 +- tests/system/Pager/PagerRendererTest.php | 4 ++-- user_guide_src/source/changelogs/v4.6.0.rst | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index e54df4af2804..3e83d02fbcdd 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -334,7 +334,7 @@ protected function updatePerPages(): void return; } - // When the page is the last, performs a different calculation. + // When the page is the last, perform a different calculation. if ($this->last === $this->current) { $this->perPageStart = $this->perPage * ($this->current - 1) + 1; $this->perPageEnd = $this->total; diff --git a/tests/system/Pager/PagerRendererTest.php b/tests/system/Pager/PagerRendererTest.php index 7f97c9c10a9f..d06a040a7925 100644 --- a/tests/system/Pager/PagerRendererTest.php +++ b/tests/system/Pager/PagerRendererTest.php @@ -630,8 +630,8 @@ public function testPageStartEnd(array $details, int $pageStart, int $pageEnd): $pager = new PagerRenderer($details); $pager->setSurroundCount(2); - $this->assertSame($pager->getPerPageStart(), $pageStart); - $this->assertSame($pager->getPerPageEnd(), $pageEnd); + $this->assertSame($pageStart, $pager->getPerPageStart()); + $this->assertSame($pageEnd, $pager->getPerPageEnd()); } /** diff --git a/user_guide_src/source/changelogs/v4.6.0.rst b/user_guide_src/source/changelogs/v4.6.0.rst index e2632007c4bc..fdc831dcbaca 100644 --- a/user_guide_src/source/changelogs/v4.6.0.rst +++ b/user_guide_src/source/changelogs/v4.6.0.rst @@ -250,7 +250,7 @@ Pagination ========== - Added a new feature to get the total and the range number of items of the current page. - See the section ``Displaying the Number of Items on the Page`` of the :ref:`displaying-the-number-of-items-on-the-page` for more details. + See :ref:`Displaying the Number of Items on the Page ` for more details. Testing ======= From ae13ba54a9e24158d2689802b86edee91858fff5 Mon Sep 17 00:00:00 2001 From: murilohp Date: Tue, 7 Jan 2025 10:28:36 -0300 Subject: [PATCH 8/8] Add null as the default value for perPageStart and End --- system/Pager/PagerRenderer.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/system/Pager/PagerRenderer.php b/system/Pager/PagerRenderer.php index 3e83d02fbcdd..f71cb665aab6 100644 --- a/system/Pager/PagerRenderer.php +++ b/system/Pager/PagerRenderer.php @@ -90,12 +90,12 @@ class PagerRenderer /** * The number of items the page starts with. */ - protected ?int $perPageStart; + protected ?int $perPageStart = null; /** * The number of items the page ends with. */ - protected ?int $perPageEnd; + protected ?int $perPageEnd = null; /** * Constructor.