Modifying Values
Chronos objects provide modifier methods that let you modify the value in a granular way. Remember that all Chronos objects are immutable, so modifier methods return a new instance.
Setting Components
You can set individual components of the datetime value:
// Set components of the datetime value
$halloween = Chronos::create()
->year(2015)
->month(10)
->day(31)
->hour(20)
->minute(30);2
3
4
5
6
7
Relative Modifications
You can modify parts of the datetime relatively:
$future = Chronos::now()
->addYears(1)
->subMonths(2)
->addDays(15)
->addHours(20)
->subMinutes(2);2
3
4
5
6
Available add/sub methods:
addYears()/subYears()addMonths()/subMonths()addWeeks()/subWeeks()addDays()/subDays()addWeekdays()/subWeekdays()addHours()/subHours()addMinutes()/subMinutes()addSeconds()/subSeconds()
For DST-safe operations that add actual elapsed time (see DST Considerations):
addElapsedHours()/subElapsedHours()addElapsedMinutes()/subElapsedMinutes()addElapsedSeconds()/subElapsedSeconds()
Month Overflow Handling
By default, adding months will clamp the day if it would overflow:
// January 31 + 1 month = February 28 (clamped)
$date = Chronos::create(2015, 1, 31)->addMonths(1);2
If you want to allow overflow:
// January 31 + 1 month = March 3 (overflowed)
$date = Chronos::create(2015, 1, 31)->addMonthsWithOverflow(1);2
The same applies to years with addYearsWithOverflow() and subYearsWithOverflow().
Jump to Boundaries
You can jump to defined points in time:
$time = Chronos::now();
// Day boundaries
$time->startOfDay(); // 00:00:00
$time->endOfDay(); // 23:59:59
// Month boundaries
$time->startOfMonth(); // First day of month, 00:00:00
$time->endOfMonth(); // Last day of month, 23:59:59
// Year boundaries
$time->startOfYear(); // January 1st, 00:00:00
$time->endOfYear(); // December 31st, 23:59:59
// Week boundaries
$time->startOfWeek(); // Start of week (configurable)
$time->endOfWeek(); // End of week (configurable)
// Decade boundaries
$time->startOfDecade();
$time->endOfDecade();
// Century boundaries
$time->startOfCentury();
$time->endOfCentury();2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
Day of Week Navigation
Jump to specific days of the week:
$time = Chronos::now();
// Next/previous occurrence of a day
$time->next(Chronos::TUESDAY);
$time->previous(Chronos::MONDAY);
// First/last of month
$time->firstOfMonth(); // First day of month
$time->firstOfMonth(Chronos::FRIDAY); // First Friday of month
$time->lastOfMonth(Chronos::MONDAY); // Last Monday of month
// Nth occurrence in month
$time->nthOfMonth(2, Chronos::SATURDAY); // 2nd Saturday of month
// Quarter-based
$time->firstOfQuarter();
$time->lastOfQuarter(Chronos::FRIDAY);
$time->nthOfQuarter(3, Chronos::MONDAY);
// Year-based
$time->firstOfYear();
$time->lastOfYear(Chronos::SUNDAY);
$time->nthOfYear(10, Chronos::WEDNESDAY); // 10th Wednesday of the year2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
Finding Occurrences
Find the next or previous occurrence of a specific day at a specific time:
$now = Chronos::now();
// Find next Monday at 9:00 AM
$nextMeeting = $now->nextOccurrenceOf(Chronos::MONDAY, 9, 0, 0);
// Find previous Friday at 5:00 PM
$lastFriday = $now->previousOccurrenceOf(Chronos::FRIDAY, 17, 0, 0);2
3
4
5
6
7
If the current day matches and the time hasn't passed yet, nextOccurrenceOf() returns today. Similarly, previousOccurrenceOf() returns today if the time has already passed.
Timezone Modifications
Converting Timezone
setTimezone() converts the datetime to the new timezone, adjusting the time:
$time = new Chronos('2015-12-25 12:00:00', 'UTC');
$tokyo = $time->setTimezone('Asia/Tokyo');
// 2015-12-25 21:00:00 Asia/Tokyo (9 hours later)2
3
Shifting Timezone
shiftTimezone() keeps the same wall clock time but changes the timezone:
$time = new Chronos('2015-12-25 12:00:00', 'UTC');
$tokyo = $time->shiftTimezone('Asia/Tokyo');
// 2015-12-25 12:00:00 Asia/Tokyo (same time, different zone)2
3
This is useful when you have a datetime that was stored without timezone information and you need to assign the correct timezone.
DST Considerations
When modifying dates/times across DST (Daylight Saving Time) transitions, your operations may gain/lose an additional hour resulting in values that don't add up. Methods like addHours(), addMinutes(), and addSeconds() add "wall clock" time, which can produce unexpected results during DST transitions.
Elapsed Time Methods
For operations that need to add actual elapsed time (not wall clock time), use the elapsed time variants:
addElapsedHours()/subElapsedHours()addElapsedMinutes()/subElapsedMinutes()addElapsedSeconds()/subElapsedSeconds()
These methods manipulate the Unix timestamp directly, ensuring that adding 600 minutes always means exactly 36000 seconds of elapsed time:
// Australia/Melbourne DST ends April 5, 2026 at 3:00 AM
// Clocks go back from 3:00 AM AEDT (+11) to 2:00 AM AEST (+10)
$startOfDay = Chronos::parse('2026-04-05 00:00:00', 'Australia/Melbourne');
// Wall clock addition - adds 10 hours of "clock time"
$wallClock = $startOfDay->addMinutes(600);
// Result: 2026-04-05T10:00:00+10:00
// Elapsed time addition - adds 10 hours of elapsed time
$elapsed = $startOfDay->addElapsedMinutes(600);
// Result: 2026-04-05T09:00:00+10:002
3
4
5
6
7
8
9
10
11
The elapsed time methods ensure that diffInMinutes() and addElapsedMinutes() are true inverses of each other:
$time = Chronos::parse('2026-04-05 09:00:00', 'Australia/Melbourne');
$startOfDay = $time->startOfDay();
$diff = $time->diffInMinutes($startOfDay); // 600
// Reconstructing the original time works correctly
$reconstructed = $startOfDay->addElapsedMinutes($diff);
// $reconstructed equals $time2
3
4
5
6
7
8
Manual UTC Conversion
Alternatively, you can manually convert to UTC, modify, then convert back:
// Additional hour gained
$time = new Chronos('2014-03-30 00:00:00', 'Europe/London');
debug($time->modify('+24 hours')); // 2014-03-31 01:00:00
// First switch to UTC, modify, then convert back
$time = $time->setTimezone('UTC')
->modify('+24 hours')
->setTimezone('Europe/London');2
3
4
5
6
7
8