Completed
Pull Request — master (#77)
by ignace nyamagana
03:12
created

Datepoint::isEnding()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 1
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * League.Period (https://period.thephpleague.com)
5
 *
6
 * (c) Ignace Nyamagana Butera <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
declare(strict_types=1);
13
14
namespace League\Period;
15
16
use DateInterval;
17
use DateTime;
18
use DateTimeImmutable;
19
use DateTimeInterface;
20
use DateTimeZone;
21
use function filter_var;
22
use function intdiv;
23
use const FILTER_VALIDATE_INT;
24
25
/**
26
 * League Period Datepoint.
27
 *
28
 * @package League.period
29
 * @author  Ignace Nyamagana Butera <[email protected]>
30
 * @since   4.2.0
31
 */
32
final class Datepoint extends DateTimeImmutable
33
{
34
    /**
35
     * Returns a position in time expressed as a DateTimeImmutable object.
36
     *
37
     * A datepoint can be
38
     * <ul>
39
     * <li>a DateTimeInterface object
40
     * <li>a integer interpreted as a timestamp
41
     * <li>a string parsable by DateTime::__construct
42
     * </ul>
43
     *
44
     * @param mixed $datepoint a position in time
45
     */
46 876
    public static function create($datepoint): self
47
    {
48 876
        if ($datepoint instanceof DateTimeInterface) {
49 453
            return new self($datepoint->format('Y-m-d H:i:s.u'), $datepoint->getTimezone());
50
        }
51
52 447
        if (false !== ($timestamp = filter_var($datepoint, FILTER_VALIDATE_INT))) {
53 3
            return new self('@'.$timestamp);
54
        }
55
56 444
        return new self($datepoint);
57
    }
58
59
    /**
60
     * @inheritdoc
61
     *
62
     * @param string       $format
63
     * @param string       $datetime
64
     * @param DateTimeZone $timezone
65
     *
66
     * @return self|false
67
     */
68 3
    public static function createFromFormat($format, $datetime, $timezone = null)
69
    {
70 3
        $datepoint = parent::createFromFormat($format, $datetime, $timezone);
71 3
        if (false !== $datepoint) {
72 3
            return self::create($datepoint);
73
        }
74
75 3
        return $datepoint;
76
    }
77
78
    /**
79
     * @inheritdoc
80
     *
81
     * @param DateTime $datetime
82
     */
83 3
    public static function createFromMutable($datetime): self
84
    {
85 3
        return self::create(parent::createFromMutable($datetime));
86
    }
87
88
    /**************************************************
89
     * interval constructors
90
     **************************************************/
91
92
    /**
93
     * Returns a Period instance.
94
     *
95
     *  - the starting datepoint represents the beginning of the current datepoint second
96
     *  - the duration is equal to 1 second
97
     */
98 6
    public function getSecond(): Period
99
    {
100 6
        $datepoint = $this->setTime(
101 6
            (int) $this->format('H'),
102 6
            (int) $this->format('i'),
103 6
            (int) $this->format('s')
104
        );
105
106 6
        return new Period($datepoint, $datepoint->add(new DateInterval('PT1S')));
107
    }
108
109
    /**
110
     * Returns a Period instance.
111
     *
112
     *  - the starting datepoint represents the beginning of the current datepoint minute
113
     *  - the duration is equal to 1 minute
114
     */
115 6
    public function getMinute(): Period
116
    {
117 6
        $datepoint = $this->setTime((int) $this->format('H'), (int) $this->format('i'), 0);
118
119 6
        return new Period($datepoint, $datepoint->add(new DateInterval('PT1M')));
120
    }
121
122
    /**
123
     * Returns a Period instance.
124
     *
125
     *  - the starting datepoint represents the beginning of the current datepoint hour
126
     *  - the duration is equal to 1 hour
127
     */
128 9
    public function getHour(): Period
129
    {
130 9
        $datepoint = $this->setTime((int) $this->format('H'), 0);
131
132 9
        return new Period($datepoint, $datepoint->add(new DateInterval('PT1H')));
133
    }
134
135
    /**
136
     * Returns a Period instance.
137
     *
138
     *  - the starting datepoint represents the beginning of the current datepoint day
139
     *  - the duration is equal to 1 day
140
     */
141 48
    public function getDay(): Period
142
    {
143 48
        $datepoint = $this->setTime(0, 0);
144
145 48
        return new Period($datepoint, $datepoint->add(new DateInterval('P1D')));
146
    }
147
148
    /**
149
     * Returns a Period instance.
150
     *
151
     *  - the starting datepoint represents the beginning of the current datepoint iso week
152
     *  - the duration is equal to 7 days
153
     */
154 6
    public function getIsoWeek(): Period
155
    {
156
        $startDate = $this
157 6
            ->setTime(0, 0)
158 6
            ->setISODate((int) $this->format('o'), (int) $this->format('W'), 1);
159
160 6
        return new Period($startDate, $startDate->add(new DateInterval('P7D')));
161
    }
162
163
    /**
164
     * Returns a Period instance.
165
     *
166
     *  - the starting datepoint represents the beginning of the current datepoint month
167
     *  - the duration is equal to 1 month
168
     */
169 15
    public function getMonth(): Period
170
    {
171
        $startDate = $this
172 15
            ->setTime(0, 0)
173 15
            ->setDate((int) $this->format('Y'), (int) $this->format('n'), 1);
174
175 15
        return new Period($startDate, $startDate->add(new DateInterval('P1M')));
176
    }
177
178
    /**
179
     * Returns a Period instance.
180
     *
181
     *  - the starting datepoint represents the beginning of the current datepoint quarter
182
     *  - the duration is equal to 3 months
183
     */
184 6
    public function getQuarter(): Period
185
    {
186
        $startDate = $this
187 6
            ->setTime(0, 0)
188 6
            ->setDate((int) $this->format('Y'), (intdiv((int) $this->format('n'), 3) * 3) + 1, 1);
189
190 6
        return new Period($startDate, $startDate->add(new DateInterval('P3M')));
191
    }
192
193
    /**
194
     * Returns a Period instance.
195
     *
196
     *  - the starting datepoint represents the beginning of the current datepoint semester
197
     *  - the duration is equal to 6 months
198
     */
199 6
    public function getSemester(): Period
200
    {
201
        $startDate = $this
202 6
            ->setTime(0, 0)
203 6
            ->setDate((int) $this->format('Y'), (intdiv((int) $this->format('n'), 6) * 6) + 1, 1);
204
205 6
        return new Period($startDate, $startDate->add(new DateInterval('P6M')));
206
    }
207
208
    /**
209
     * Returns a Period instance.
210
     *
211
     *  - the starting datepoint represents the beginning of the current datepoint year
212
     *  - the duration is equal to 1 year
213
     */
214 15
    public function getYear(): Period
215
    {
216 15
        $year = (int) $this->format('Y');
217 15
        $datepoint = $this->setTime(0, 0);
218
219 15
        return new Period($datepoint->setDate($year, 1, 1), $datepoint->setDate(++$year, 1, 1));
220
    }
221
222
    /**
223
     * Returns a Period instance.
224
     *
225
     *  - the starting datepoint represents the beginning of the current datepoint iso year
226
     *  - the duration is equal to 1 iso year
227
     */
228 6
    public function getIsoYear(): Period
229
    {
230 6
        $year = (int) $this->format('o');
231 6
        $datepoint = $this->setTime(0, 0);
232
233 6
        return new Period($datepoint->setISODate($year, 1, 1), $datepoint->setISODate(++$year, 1, 1));
234
    }
235
236
    /**************************************************
237
     * relation methods
238
     **************************************************/
239
240
    /**
241
     * Tells whether the datepoint is before the interval.
242
     */
243 12
    public function isBefore(Period $interval): bool
244
    {
245 12
        return $interval->isAfter($this);
246
    }
247
248
    /**
249
     * Tell whether the datepoint borders on start the interval.
250
     */
251 3
    public function bordersOnStart(Period $interval): bool
252
    {
253 3
        return $this == $interval->getStartDate() && $interval->isStartExcluded();
254
    }
255
256
    /**
257
     * Tells whether the datepoint starts the interval.
258
     */
259 12
    public function isStarting(Period $interval): bool
260
    {
261 12
        return $interval->isStartedBy($this);
262
    }
263
264
    /**
265
     * Tells whether the datepoint is contained within the interval.
266
     */
267 27
    public function isDuring(Period $interval): bool
268
    {
269 27
        return $interval->contains($this);
270
    }
271
272
    /**
273
     * Tells whether the datepoint ends the interval.
274
     */
275 6
    public function isEnding(Period $interval): bool
276
    {
277 6
        return $interval->isEndedBy($this);
278
    }
279
280
    /**
281
     * Tells whether the datepoint borders on end the interval.
282
     */
283 3
    public function bordersOnEnd(Period $interval): bool
284
    {
285 3
        return $this == $interval->getEndDate() && $interval->isEndExcluded();
286
    }
287
288
    /**
289
     * Tells whether the datepoint abuts the interval.
290
     */
291 3
    public function abuts(Period $interval): bool
292
    {
293 3
        return $this->bordersOnEnd($interval) || $this->bordersOnStart($interval);
294
    }
295
296
    /**
297
     * Tells whether the datepoint is after the interval.
298
     */
299 18
    public function isAfter(Period $interval): bool
300
    {
301 18
        return $interval->isBefore($this);
302
    }
303
}
304