Paginator::renderForward()   A
last analyzed

Complexity

Conditions 4
Paths 8

Size

Total Lines 12
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 8
CRAP Score 4

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 4
eloc 8
c 1
b 0
f 0
nc 8
nop 2
dl 0
loc 12
ccs 8
cts 8
cp 1
crap 4
rs 10
1
<?php
2
3
namespace Bone\View\Helper;
4
5
use Bone\View\Helper\Exception\PaginatorException;
6
use Del\Icon;
7
8
class Paginator
9
{
10
    private $currentPage = 1;
11
    private $pageCount;
12
    private $pagerSize = 5;
13
    private $url;
14
    private $urlPart = ':page';
15
16
    /**
17
     * @param int $pageNum
18
     * @return string
19
     */
20 7
    private function url(int $pageNum): string
21
    {
22 7
        return str_replace($this->urlPart, $pageNum, $this->url);
23
    }
24
25
    /**
26
     * @param $pageCount
27
     */
28 5
    public function setPageCount(int $pageCount): void
29
    {
30 5
        $this->pageCount = $pageCount;
31 5
    }
32
33
    /**
34
     * @param $pageCount
35
     */
36 3
    public function setPageCountByTotalRecords(int $rowCount, int $numPerPage): void
37
    {
38 3
        $this->pageCount = (int)ceil($rowCount / $numPerPage) ?: 1;
39 3
    }
40
41
    /**
42
     * @param $url
43
     */
44 7
    public function setUrl(string $url): void
45
    {
46 7
        $this->url = $url;
47 7
    }
48
49
    /**
50
     * @param $replace
51
     */
52 2
    public function setUrlPart(string $replace): void
53
    {
54 2
        $this->urlPart = $replace;
55 2
    }
56
57
    /**
58
     * @param int $page_no
59
     */
60 7
    public function setCurrentPage(int $page_no): void
61
    {
62 7
        $this->currentPage = $page_no;
63 7
    }
64
65
    /**
66
     * @param int $numBoxes an ODD number!
67
     */
68 4
    public function setPagerSize(int $numBoxes): void
69
    {
70 4
        if ($numBoxes % 2 === 0) {
71 1
            $numBoxes--;
72
        }
73 4
        $this->pagerSize = $numBoxes;
74 4
    }
75
76
    /**
77
     * @return int
78
     */
79 7
    public function getPagerSize(): int
80
    {
81 7
        return $this->pagerSize;
82
    }
83
84
    /**
85
     * @throws PaginatorException
86
     */
87 9
    private function ensurePageCount()
88
    {
89 9
        if (null === $this->pageCount) {
90 1
            throw new PaginatorException(PaginatorException::NO_PAGE_COUNT);
91
        }
92 8
    }
93
94
    /**
95
     * @throws PaginatorException
96
     */
97 8
    private function ensureUrl()
98
    {
99 8
        if (null === $this->url) {
100 1
            throw new PaginatorException(PaginatorException::NO_URL);
101
        }
102 7
    }
103
104
    /**
105
     * @return int
106
     */
107 5
    private function calculateStart(int $pages): int
108
    {
109 5
        $half = ($pages - 1) / 2;
110
111 5
        if ($this->currentPage < 3) {
112 1
            $start = 1;
113 4
        } elseif ($this->currentPage >= ($this->pageCount - $half)) {
114 2
            $start = $this->pageCount - ($this->getPagerSize() - 1);
115
        } else {
116 2
            $start = $this->currentPage - $half;
117
118 2
            if ($start < 1) {
119 1
                $start = 1;
120
            }
121
        }
122
123 5
        return $start;
124
    }
125
126
    /**
127
     * @return string
128
     * @throws PaginatorException
129
     */
130 9
    public function render(): string
131
    {
132 9
        $this->ensurePageCount();
133 8
        $this->ensureUrl();
134
135 7
        $html = '<nav><ul class="pagination">';
136
137 7
        if ($this->pageCount > ($this->getPagerSize() - 1)) {
138 5
            $pages = $this->getPagerSize();
139 5
            $start = $this->calculateStart($pages);
140
        } else {
141 2
            $pages = $this->pageCount;
142 2
            $start = 1;
143
        }
144
145 7
        $html .= $this->renderRewind(Icon::FAST_BACKWARD, true);
146 7
        $html .= $this->renderRewind();
147
148 7
        for ($x = $start; $x <= ($start + ($pages - 1)); $x++) {
149 7
            $html .= $this->renderBox($x);
150
        }
151
152 7
        $html .= $this->renderForward();
153 7
        $html .= $this->renderForward(Icon::FAST_FORWARD, true);
154 7
        $html .= '</ul></nav>';
155
156 7
        return $html;
157
    }
158
159
    /**
160
     * @param string $icon
161
     * @param bool $fastBackward
162
     * @return string
163
     */
164 7
    private function renderRewind($icon = Icon::BACKWARD, bool $fastBackward = false): string
165
    {
166 7
        $urlPageNo = $fastBackward ? 1 : $this->currentPage - 1;
167 7
        $html = ($this->currentPage === 1) ? '<li class="page-item disabled">' : '<li class="page-item">';
168 7
        if ($this->currentPage === 1) {
169 1
            $html .= '<a class="page-link"  href ="#">' . Icon::custom($icon, 'disabled') . '</a>';
170
        } else {
171 6
            $html .= '<a class="page-link"  href ="' . $this->url($urlPageNo) . '">' . $icon . '</a>';
172
        }
173 7
        $html .= '</li>';
174
175 7
        return $html;
176
    }
177
178
    /**
179
     * @param string $icon
180
     * @param bool $fastForward
181
     * @return string
182
     */
183 7
    private function renderForward($icon = Icon::FORWARD, bool $fastForward = false): string
184
    {
185 7
        $urlPageNo = $fastForward ? $this->pageCount : $this->currentPage + 1;
186 7
        $html = ($this->currentPage >= $this->pageCount) ? '<li class="page-item disabled">' : '<li class="page-item">';
187 7
        if ($this->currentPage >= $this->pageCount) {
188 1
            $html .= '<a class="page-link" href="#">' . Icon::custom($icon, 'disabled') . '</a>';
189
        } else {
190 6
            $html .= '<a class="page-link"  href ="' . $this->url($urlPageNo) . '">' . $icon . '</i></a>';
191
        }
192 7
        $html .= '</li>';
193
194 7
        return $html;
195
    }
196
197
    /**
198
     * @param int $pageNo
199
     * @return string
200
     */
201 7
    private function renderBox(int $pageNo): string
202
    {
203 7
        $html = '<li class="page-item ';
204 7
        if ($this->currentPage === $pageNo) {
205 7
            $html .= ' active" aria-current="page';
206
        }
207 7
        $html .= '">';
208 7
        if ($this->currentPage === $pageNo) {
209 7
            $html .= '<a class="page-link" href="#">' . $pageNo . '</a>';
210
        } else {
211 7
            $html .= '<a class="page-link" href="' . $this->url($pageNo) . '">' . $pageNo . '</a>';
212
        }
213 7
        $html .= '</li>';
214
215 7
        return $html;
216
    }
217
}
218