diff --git a/calendar/inc/class.calendar_boupdate.inc.php b/calendar/inc/class.calendar_boupdate.inc.php index c43ad0bf38..193ad458ec 100644 --- a/calendar/inc/class.calendar_boupdate.inc.php +++ b/calendar/inc/class.calendar_boupdate.inc.php @@ -1812,6 +1812,40 @@ class calendar_boupdate extends calendar_bo return true; } + /** + * Check alarms and move them if needed + * + * Used when the start time has changed, and alarms need to be updated + * + * @param array $event + * @param array $old_event + * @param egw_time $instance_date For recurring events, this is the date we + * are dealing with + */ + function check_move_alarms(Array &$event, Array $old_event = null, egw_time $instance_date = null) + { + if ($old_event !== null && $event['start'] == $old_event['start']) return; + + $time = new egw_time($event['start']); + if(!is_array($event['alarm'])) + { + $event['alarm'] = $this->so->read_alarms($event['id']); + } + + foreach($event['alarm'] as $id => &$alarm) + { + if($event['recur_type'] != MCAL_RECUR_NONE) + { + calendar_so::shift_alarm($event, $alarm, $instance_date->format('ts')); + } + else if ($alarm['time'] !== $time->format('ts') - $alarm['offset']) + { + $alarm['time'] = $time->format('ts') - $alarm['offset']; + $this->save_alarm($event['id'], $alarm); + } + } + } + /** * saves a new or updated alarm * diff --git a/calendar/inc/class.calendar_so.inc.php b/calendar/inc/class.calendar_so.inc.php index 27fc3f10e0..e6d37ba01f 100644 --- a/calendar/inc/class.calendar_so.inc.php +++ b/calendar/inc/class.calendar_so.inc.php @@ -1688,15 +1688,17 @@ ORDER BY cal_user_type, cal_usre_id * * @param array $_event event with optional 'cal_' prefix in keys * @param array &$alarm + * @param int $timestamp For recurring events, this is the date we + * are dealing with, default is now. * @return boolean true if alarm could be shifted, false if not */ - public static function shift_alarm(array $_event, array &$alarm) + public static function shift_alarm(array $_event, array &$alarm, $timestamp) { if ($_event['recur_type'] == MCAL_RECUR_NONE) { return false; } - $start = (int)time() + $alarm['offset']; + $start = $timestamp ? $timestamp : (int)time() + $alarm['offset']; $event = egw_db::strip_array_keys($_event, 'cal_'); $rrule = calendar_rrule::event2rrule($event, false); foreach ($rrule as $time) diff --git a/calendar/inc/class.calendar_uiforms.inc.php b/calendar/inc/class.calendar_uiforms.inc.php index 8658c4a9ad..30019e5c44 100644 --- a/calendar/inc/class.calendar_uiforms.inc.php +++ b/calendar/inc/class.calendar_uiforms.inc.php @@ -788,6 +788,8 @@ class calendar_uiforms extends calendar_ui } } } + // check if we need to move the alarms, because they are relative + $this->bo->check_move_alarms($event, $old_event); } } } @@ -2764,22 +2766,7 @@ class calendar_uiforms extends calendar_ui $recur_event = $this->bo->read($event['reference']); $recur_event['recur_exception'][] = $d->format('ts'); // check if we need to move the alarms, because they are next on that exception - foreach($recur_event['alarm'] as $id => $alarm) - { - if ($alarm['time'] == $content['edit_single'] - $alarm['offset']) - { - $rrule = calendar_rrule::event2rrule($recur_event, true); - foreach ($rrule as $time) - { - if ($content['edit_single'] < $time->format('ts')) - { - $alarm['time'] = $time->format('ts') - $alarm['offset']; - $this->bo->save_alarm($event['reference'], $alarm); - break; - } - } - } - } + $this->bo->check_move_alarms($recur_event, null, $d); unset($recur_event['start']); unset($recur_event['end']); // no update necessary unset($recur_event['alarm']); // unsetting alarms too, as they cant be updated without start! $this->bo->update($recur_event,true); // no conflict check here @@ -2805,6 +2792,10 @@ class calendar_uiforms extends calendar_ui // stop it & create a new one. $this->_break_recurring($event, $old_event, $this->bo->date2ts($targetDateTime)); } + if(!$event['recur_type']) + { + $this->bo->check_move_alarms($event, $old_event); + } // Drag a whole day to a time if($durationT && $durationT != 'whole_day')