Passed
Push — master ( c5ffd7...a01ea1 )
by Robson
02:38
created

Paginator::pager()   A

Complexity

Conditions 5
Paths 8

Size

Total Lines 13
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 5
eloc 9
nc 8
nop 5
dl 0
loc 13
rs 9.6111
c 0
b 0
f 0
1
<?php
2
3
namespace CoffeeCode\Paginator;
4
5
/**
6
 * Class CoffeeCode Paginator
7
 *
8
 * @author Robson V. Leite <https://github.com/robsonvleite>
9
 * @package CoffeeCode\Paginator
10
 */
11
class Paginator
12
{
13
    /** @var int */
14
    private $page;
15
16
    /** @var int */
17
    private $pages;
18
19
    /** @var int */
20
    private $rows;
21
22
    /** @var int */
23
    private $limit;
24
25
    /** @var int */
26
    private $offset;
27
28
    /** @var int */
29
    private $range;
30
31
    /** @var string */
32
    private $link;
33
34
    /** @var string */
35
    private $title;
36
37
    /** @var string */
38
    private $class;
39
40
    /** @var string */
41
    private $hash;
42
43
    /** @var array */
44
    private $first;
45
46
    /** @var array */
47
    private $last;
48
49
    /**
50
     * Paginator constructor.
51
     * @param string|null $link
52
     * @param string|null $title
53
     * @param array|null $first
54
     * @param array|null $last
55
     */
56
    public function __construct(string $link = null, string $title = null, array $first = null, array $last = null)
57
    {
58
        $this->link = ($link ?? "?page=");
59
        $this->title = ($title ?? "Página");
60
        $this->first = ($first ?? ["Primeira página", "<<"]);
61
        $this->last = ($last ?? ["Última página", ">>"]);
62
    }
63
64
    /**
65
     * @param int $rows
66
     * @param int $limit
67
     * @param int|null $page
68
     * @param int $range
69
     * @param string|null $hash
70
     */
71
    public function pager(int $rows, int $limit = 10, int $page = null, int $range = 3, string $hash = null): void
72
    {
73
        $this->page = $this->toPositive($page);
74
        $this->rows = $this->toPositive($rows);
75
        $this->limit = $this->toPositive($limit);
76
        $this->range = $this->toPositive($range);
77
78
        $this->offset = (($page * $limit) - $limit >= 0 ? ($page * $limit) - $limit : 0);
79
        $this->hash = ($hash ? "#{$hash}" : null);
80
81
        if ($this->rows && $this->offset >= $this->rows) {
82
            header("Location: {$this->link}" . ceil($this->rows / $this->limit));
83
            exit;
84
        }
85
    }
86
87
    /**
88
     * @return int
89
     */
90
    public function limit(): int
91
    {
92
        return $this->limit;
93
    }
94
95
    /**
96
     * @return int
97
     */
98
    public function offset(): int
99
    {
100
        return $this->offset;
101
    }
102
103
    /**
104
     * @param string $cssClass
105
     * @return null|string
106
     */
107
    public function render(string $cssClass = "paginator"): ?string
108
    {
109
        $this->class = $cssClass;
110
        $this->pages = (int)ceil($this->rows / $this->limit);
111
112
        if ($this->rows > $this->limit):
113
            $paginator = "<nav class=\"{$this->class}\">";
114
            $paginator .= "<a class='{$this->class}_item' title=\"{$this->first[0]}\" href=\"{$this->link}1{$this->hash}\">{$this->first[1]}</a>";
115
            $paginator .= $this->beforePages();
116
            $paginator .= "<span class=\"{$this->class}_item {$this->class}_active\">{$this->page}</span>";
117
            $paginator .= $this->afterPages();
118
            $paginator .= "<a class='{$this->class}_item' title=\"{$this->last[0]}\" href=\"{$this->link}{$this->pages}{$this->hash}\">{$this->last[1]}</a>";
119
            $paginator .= "</nav>";
120
            return $paginator;
121
        endif;
122
123
        return null;
124
    }
125
126
    /**
127
     * @return null|string
128
     */
129
    private function beforePages(): ?string
130
    {
131
        $before = null;
132
        for ($iPag = $this->page - $this->range; $iPag <= $this->page - 1; $iPag++):
133
            if ($iPag >= 1):
134
                $before .= "<a class='{$this->class}_item' title=\"{$this->title} {$iPag}\" href=\"{$this->link}{$iPag}{$this->hash}\">{$iPag}</a>";
135
            endif;
136
        endfor;
137
138
        return $before;
139
    }
140
141
    /**
142
     * @return string|null
143
     */
144
    private function afterPages(): ?string
145
    {
146
        $after = null;
147
        for ($dPag = $this->page + 1; $dPag <= $this->page + $this->range; $dPag++):
148
            if ($dPag <= $this->pages):
149
                $after .= "<a class='{$this->class}_item' title=\"{$this->title} {$dPag}\" href=\"{$this->link}{$dPag}{$this->hash}\">{$dPag}</a>";
150
            endif;
151
        endfor;
152
153
        return $after;
154
    }
155
156
    /**
157
     * @param $number
158
     * @return int
159
     */
160
    private function toPositive($number): int
161
    {
162
        return ($number >= 1 ? $number : 1);
163
    }
164
}