Passed
Branch master (7fe1ca)
by compolom
01:42
created

Pagination::getTotalPages()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 1
eloc 1
c 1
b 0
f 0
nc 1
nop 0
dl 0
loc 3
ccs 0
cts 2
cp 0
crap 2
rs 10
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Compolomus\Pagination;
6
7
class Pagination
8
{
9
    private int $total;
10
11
    private int $page;
12
13
    private int $limit;
14
15
    private int $totalPages;
16
17
    private int $length;
18
19
    private string $pos;
20
21
    private bool $uiKeys;
22
23
    /**
24
     * @param int $page
25
     * @param int $limit
26
     * @param int $total
27
     * @param int $length
28
     * @param bool $uiKeys
29
     */
30 5
    public function __construct(int $page, int $limit, int $total, int $length = 3, bool $uiKeys = false)
31
    {
32 5
        $this->totalPages = (int) ceil($total / $limit);
33 5
        $this->page = $page > 1 ? ($page > $this->totalPages ? 1 : $page) : 1;
34 5
        $this->limit = $limit > 0 ? $limit : 10;
35 5
        $this->total = $total;
36 5
        $this->length = $length >= 0 ? $length : 3;
37 5
        $this->pos = $this->init();
38 5
        $this->uiKeys = $uiKeys;
39
    }
40
41 5
    private function init(): string
42
    {
43 5
        switch ($this->page) {
44 5
            case ($this->totalPages < 7):
45
            default:
46 4
                $pos = 'full';
47 4
                break;
48 1
            case (($this->page - $this->length) < 3):
49 1
                $pos = 'noLeftDots';
50 1
                break;
51 1
            case (($this->page - $this->length) >= 3 && ($this->totalPages - $this->page - $this->length) > 1):
52 1
                $pos = 'center';
53 1
                break;
54 1
            case (abs($this->totalPages - $this->page - $this->length) >= 0):
55 1
                $pos = 'noRightDots';
56 1
                break;
57
        }
58
59 5
        return $pos;
60
    }
61
62
    /**
63
     * @return int
64
     */
65 1
    public function getLimit(): int
66
    {
67 1
        return $this->limit;
68
    }
69
70
    /**
71
     * @return int
72
     */
73 1
    public function getEnd(): int
74
    {
75 1
        return $this->page === $this->totalPages ? $this->total : $this->page * $this->limit;
76
    }
77
78
    /**
79
     * @return int
80
     */
81 1
    public function getOffset(): int
82
    {
83 1
        return $this->page === 1 ? 0 : ($this->page - 1) * $this->limit;
84
    }
85
86
    /**
87
     * @return array
88
     */
89
    private function uiStart(): array
90
    {
91
        $result = [];
92
93
        if ($this->page > 1) {
94
            $result['prev'] = $this->page - 1;
95
        }
96
        if ($this->page !== 1) {
97
            $result['first'] = 1;
98
        }
99
        if ($this->page > 3) {
100
            $result['second'] = 2;
101
        }
102
103
        return $result;
104
    }
105
106
    /**
107
     * @return array
108
     */
109 1
    private function start(): array
110
    {
111 1
        $result = $this->uiKeys ? $this->uiStart() : [];
112
113 1
        return $this->pos !== 'full' ? $result : [];
114
    }
115
116
    /**
117
     * @return array
118
     */
119
    private function uiEnd(): array
120
    {
121
        $result = [];
122
123
        if ($this->page !== $this->totalPages) {
124
            $result['last'] = $this->totalPages;
125
        }
126
        if ($this->totalPages - $this->page > 0) {
127
            $result['next'] = $this->page + 1;
128
        }
129
        if ($this->totalPages - $this->page + $this->length > 3) {
130
            $result['preLast'] = $this->totalPages - 1;
131
        }
132
133
        return $result;
134
    }
135
136
    /**
137
     * @return array
138
     */
139 1
    private function end(): array
140
    {
141 1
        $result = $this->uiKeys ? $this->uiEnd() : [];
142
143 1
        return $this->pos !== 'full' ? $result : [];
144
    }
145
146
    /**
147
     * @return array
148
     */
149 1
    private function leftDots(): array
150
    {
151 1
        $result = [];
152
153 1
        if ($this->pos !== 'noLeftDots') {
154 1
            if ($this->uiKeys) {
155
                $result['leftDots'] = '...';
156
            } else {
157 1
                $result[] = '...';
158
            }
159
        }
160
161 1
        return $result;
162
    }
163
164
    /**
165
     * @return array
166
     */
167 1
    private function leftPad(): array
168
    {
169 1
        $result = [];
170 1
        $for = [];
171
172 1
        if ($this->page - $this->length > 1) {
173 1
            $result[] = 1;
174
        }
175 1
        foreach (range($this->page - 1, $this->page - $this->length) as $value) {
176 1
            if ($value > 0) {
177 1
                $for[] = $value;
178
            }
179
        }
180
181 1
        return $this->pos === 'full' ? [] : array_merge($result, $this->leftDots(), array_reverse($for));
182
    }
183
184
    /**
185
     * @return array
186
     */
187 1
    private function rightDots(): array
188
    {
189 1
        $result = [];
190
191 1
        if ($this->pos !== 'noRightDots') {
192 1
            if ($this->uiKeys) {
193
                $result['rightDots'] = '...';
194
            } else {
195 1
                $result[] = '...';
196
            }
197
        }
198
199 1
        return $result;
200
    }
201
202
    /**
203
     * @return array
204
     */
205 1
    private function rightPad(): array
206
    {
207 1
        $result = [];
208
209 1
        foreach (range($this->page + 1, $this->page + $this->length) as $value) {
210 1
            if ($value <= $this->totalPages) {
211 1
                $result[] = $value;
212
            }
213
        }
214
215 1
        $last = ($this->totalPages - $this->page - $this->length > 0) ? [$this->totalPages] : [];
216
217 1
        return $this->pos === 'full' ? [] : array_merge($result, $this->rightDots(), $last);
218
    }
219
220
    /**
221
     * @return array
222
     */
223
    private function full(): array
224
    {
225
        $result = [];
226
227
        foreach (range(1, $this->totalPages) as $value) {
228
            if ($this->uiKeys && $value === $this->page) {
229
                $result['current'] = $value;
230
            } else {
231
                $result[] = $value;
232
            }
233
        }
234
235
        return $result;
236
    }
237
238
    /**
239
     * @return array
240
     */
241 1
    private function getCurrent(): array
242
    {
243 1
        if ($this->uiKeys) {
244
            $result['current'] = $this->page;
0 ignored issues
show
Comprehensibility Best Practice introduced by
$result was never initialized. Although not strictly required by PHP, it is generally a good practice to add $result = array(); before regardless.
Loading history...
245
        } else {
246 1
            $result[] = $this->page;
247
        }
248
249 1
        if ($this->pos === 'full') {
250
            $result = $this->full();
251
        }
252
253 1
        return $result;
254
    }
255
256
    /**
257
     * @return array
258
     */
259 1
    public function get(): array
260
    {
261 1
        return array_merge($this->start(), $this->leftPad(), $this->getCurrent(), $this->rightPad(), $this->end());
262
    }
263
264
    /**
265
     * @return int
266
     */
267
    public function getTotalPages(): int
268
    {
269
        return $this->totalPages;
270
    }
271
}
272