mirror of
https://github.com/EGroupware/egroupware.git
synced 2024-11-07 08:34:42 +01:00
show changes in participants, new and old start-date
for exceptions only sending the concerned recurrence, instead of the whole series, so user understands what has changed
This commit is contained in:
parent
42178c432e
commit
1509f30971
@ -570,10 +570,10 @@ class calendar_boupdate extends calendar_bo
|
||||
*
|
||||
* @param array $new_event the updated event
|
||||
* @param array $old_event the event before the update
|
||||
* @param int $notify_max_recurrences notify only about this number of single recurrences at maximum
|
||||
*/
|
||||
function check4update($new_event,$old_event)
|
||||
function check4update($new_event, $old_event, int $notify_max_recurrences=3)
|
||||
{
|
||||
//error_log(__METHOD__."($new_event[title])");
|
||||
$modified = $added = $deleted = array();
|
||||
|
||||
//echo "<p>calendar_boupdate::check4update() new participants = ".print_r($new_event['participants'],true).", old participants =".print_r($old_event['participants'],true)."</p>\n";
|
||||
@ -582,6 +582,63 @@ class calendar_boupdate extends calendar_bo
|
||||
{
|
||||
if($new_event[$field] !== $old_event[$field])
|
||||
{
|
||||
$n = 0;
|
||||
switch($field)
|
||||
{
|
||||
case 'recur_exception':
|
||||
foreach ($added_exceptions=array_diff($new_event[$field]??[],$old_event[$field]??[]) as $key => $recurrence)
|
||||
{
|
||||
if ($this->read($new_event['uid'], $recurrence))
|
||||
{
|
||||
unset($added_exceptions[$key]);
|
||||
continue; // explicit exception --> no need to notify, already done for the exception itself
|
||||
}
|
||||
// send a cancel for each RECURRENCE-ID
|
||||
$this->send_update(MSG_DELETED, $new_event['participants'], [
|
||||
'recurrence' => $recurrence,
|
||||
'start' => $recurrence,
|
||||
'end' => $recurrence + $new_event['end'] - $new_event['start'],
|
||||
]+$new_event);
|
||||
// limit number of notifications to the first N recurrences
|
||||
if (++$n >= $notify_max_recurrences) break;
|
||||
}
|
||||
$n = 0;
|
||||
foreach($removed_exceptions=array_diff($old_event[$field]??[],$new_event[$field]??[]) as $key => $recurrence)
|
||||
{
|
||||
if ($this->read($new_event['uid'], $recurrence))
|
||||
{
|
||||
unset($removed_exceptions[$key]);
|
||||
continue; // explicit exception --> no need to notify, already done for the exception itself
|
||||
}
|
||||
// send an add for each RECURRENCE-ID
|
||||
$this->send_update(MSG_ADDED, $new_event['participants'], null, [
|
||||
'recurrence' => $recurrence,
|
||||
'start' => $recurrence,
|
||||
'end' => $recurrence + $new_event['end'] - $new_event['start'],
|
||||
]+$new_event);
|
||||
// limit number of notifications to the first N recurrences
|
||||
if (++$n >= $notify_max_recurrences) break;
|
||||
}
|
||||
continue 2;
|
||||
|
||||
case 'recur_rdates':
|
||||
foreach(array_diff($new_event[$field]??[],$old_event[$field]??[]) as $recurrence)
|
||||
{
|
||||
// send an add for each RECURRENCE-ID
|
||||
$this->send_update(MSG_ADDED, $new_event['participants'], null, [
|
||||
'recurrence' => $recurrence,
|
||||
'start' => $recurrence,
|
||||
'end' => $recurrence + $new_event['end'] - $new_event['start'],
|
||||
]+$new_event);
|
||||
// limit number of notifications to the first N recurrences
|
||||
if (++$n >= $notify_max_recurrences) break;
|
||||
}
|
||||
continue 2;
|
||||
|
||||
case 'recur_enddate':
|
||||
if ($new_event['recur_type'] == MCAL_RECUR_RDATE) continue 2; // already handled above
|
||||
break;
|
||||
}
|
||||
$modified = $new_event['participants'];
|
||||
break;
|
||||
}
|
||||
@ -1288,7 +1345,7 @@ class calendar_boupdate extends calendar_bo
|
||||
'videoconference' => $details['videoconference'],
|
||||
), $event['id']);
|
||||
}
|
||||
if ($m_type === MSG_ALARM)
|
||||
elseif ($m_type === MSG_ALARM)
|
||||
{
|
||||
$notification->set_popupdata('calendar',
|
||||
array('egw_pr_notify' => 1,
|
||||
@ -1299,6 +1356,10 @@ class calendar_boupdate extends calendar_bo
|
||||
)
|
||||
+ ($alarm ? ['alarm-offset' => (int)$alarm['offset']] : []), $event['id']);
|
||||
}
|
||||
else
|
||||
{
|
||||
$notification->set_popupdata('calendar', null, $event['id']);
|
||||
}
|
||||
$notification->set_popupmessage($subject . "\n\n" . $notify_body . "\n\n" . $details['description'] . "\n\n" . $details_body . "\n\n");
|
||||
$notification->set_popuplinks(array($details['link_arr'] + array('app' => 'calendar')));
|
||||
|
||||
|
@ -2225,14 +2225,6 @@ class calendar_uiforms extends calendar_ui
|
||||
// convert event from servertime returned by calendar_ical to user-time
|
||||
$this->bo->server2usertime($event);
|
||||
|
||||
// Check if this is an exception
|
||||
if($event['recur_type'] && count($event['recur_exception']) && !$event['recurrence'])
|
||||
{
|
||||
$diff = $event['recur_exception'][0] - $event['start'];
|
||||
$event['start'] += $diff;
|
||||
$event['end'] += $diff;
|
||||
}
|
||||
|
||||
if (($existing_event = $this->bo->read($event['uid'], $event['recurrence'], false, 'ts', null, true))) // true = read the exception
|
||||
{
|
||||
// check if mail is from extern organizer
|
||||
@ -2251,6 +2243,20 @@ class calendar_uiforms extends calendar_ui
|
||||
{
|
||||
$master = $this->bo->read($event['uid']);
|
||||
}
|
||||
$all_participants = ($event['participants'] ?? []) + ($existing_event['participants'] ?? []);
|
||||
$event['participantChanges'] = array_map(function($uid, $status) use ($existing_event, $event) {
|
||||
return [
|
||||
'changed' => !isset($event['participants'][$uid]) ? 'meetingRequestParticipantDeleted' :
|
||||
(!isset($existing_event['participants'][$uid]) ? 'meetingRequestChanged' :
|
||||
($status !== $existing_event['participants'][$uid] ? 'meetingRequestChangedStatus' : '')),
|
||||
'label' => $this->bo->participant_name($uid),
|
||||
'status' => lang($this->bo->verbose_status[calendar_so::split_status($status, $quantity, $role)]),
|
||||
'role' => $role === 'REQ-PARTICIPANT' ? '' : lang($this->bo->roles[$role] ??
|
||||
(substr($role,0,6) === 'X-CAT-' && ($cat_id = (int)substr($role,6)) > 0 ?
|
||||
$GLOBALS['egw']->categories->id2name($cat_id) : str_replace('X-','',$role))),
|
||||
];
|
||||
}, array_keys($all_participants), $all_participants);
|
||||
|
||||
switch(strtolower($ical_method))
|
||||
{
|
||||
case 'reply':
|
||||
@ -2338,22 +2344,14 @@ class calendar_uiforms extends calendar_ui
|
||||
$readonlys['button[reject]'] = $readonlys['button[cancel]'] = true;
|
||||
}
|
||||
}
|
||||
$all_participants = ($event['participants'] ?? []) + ($existing_event['participants'] ?? []);
|
||||
$event['participantChanges'] = array_map(function($uid, $status) use ($existing_event, $event) {
|
||||
return [
|
||||
'changed' => !isset($event['participants'][$uid]) ? 'meetingRequestParticipantDeleted' :
|
||||
(!isset($existing_event['participants'][$uid]) ? 'meetingRequestChanged' :
|
||||
($status !== $existing_event['participants'][$uid] ? 'meetingRequestChangedStatus' : '')),
|
||||
'label' => $this->bo->participant_name($uid),
|
||||
'status' => lang($this->bo->verbose_status[calendar_so::split_status($status, $quantity, $role)]),
|
||||
'role' => $role === 'REQ-PARTICIPANT' ? '' : lang($this->bo->roles[$role] ??
|
||||
(substr($role,0,6) === 'X-CAT-' && ($cat_id = (int)substr($role,6)) > 0 ?
|
||||
$GLOBALS['egw']->categories->id2name($cat_id) : str_replace('X-','',$role))),
|
||||
];
|
||||
}, array_keys($all_participants), $all_participants);
|
||||
break;
|
||||
case 'cancel':
|
||||
// first participant is the (external) organizer (our iCal parser adds owner first!)
|
||||
$event['changed'] = [
|
||||
'start' => 'meetingRequestChangedValue',
|
||||
'end' => 'meetingRequestChangedValue',
|
||||
'participants' => 'meetingRequestParticipantDeleted',
|
||||
];
|
||||
$parts = $event['participants'] ?? [];
|
||||
unset($parts[$existing_event['owner']]);
|
||||
$event['ical_sender_uid'] = key($parts);
|
||||
@ -2600,6 +2598,18 @@ class calendar_uiforms extends calendar_ui
|
||||
unset($changes['recure']);
|
||||
}
|
||||
|
||||
// if start changed, make old start-time available to template
|
||||
if (isset($changes['start']) && $_event['start'] != $changes['start'])
|
||||
{
|
||||
$_event['old_start'] = $changes['start'];
|
||||
}
|
||||
// if we have an explicit exception, always report that as a change from the regular recurrence
|
||||
elseif (!empty($_event['recurrence']) && empty($_event['recur_type']) && $_event['recurrence'] != $_event['start'])
|
||||
{
|
||||
$_event['old_start'] = $changes['start'] = $_event['recurrence'];
|
||||
$changes['end'] = $_event['recurrence'] + $_event['end']-$_event['start'];
|
||||
}
|
||||
|
||||
return $changes;
|
||||
}
|
||||
|
||||
|
@ -78,7 +78,7 @@
|
||||
<et2-description value="Title"></et2-description>
|
||||
<et2-description id="title" noLang="1" class="@changed[title]"></et2-description>
|
||||
</row>
|
||||
<row class="row" disabled="!$cont[location]$cont[##videoconference]">
|
||||
<row class="row" disabled="!$cont[location]{$cont['##videoconference']}"> <!-- '##videoconference' must be in quotes because of #! -->
|
||||
<et2-description value="Location"></et2-description>
|
||||
<et2-hbox>
|
||||
<et2-description id="location" noLang="1" class="@changed[location]"></et2-description>
|
||||
@ -90,6 +90,7 @@
|
||||
<et2-description value="Date"></et2-description>
|
||||
<et2-hbox class="dates">
|
||||
<et2-date-time id="start" readonly="true" class="@changed[start]"></et2-date-time>
|
||||
<et2-date-time id="old_start" readonly="true" class="meetingRequestChangedValue" disabled="!@old_start"></et2-date-time>
|
||||
<et2-date-time label="-" id="end" readonly="true" class="@changed[end]"></et2-date-time>
|
||||
</et2-hbox>
|
||||
</row>
|
||||
@ -111,7 +112,7 @@
|
||||
</row>
|
||||
<row class="row" valign="top">
|
||||
<et2-description value="Participants"></et2-description>
|
||||
<grid id="participantChanges" class="meetingRequestParticipants">
|
||||
<grid id="participantChanges" class="meetingRequestParticipants $cont[changed][participants]">
|
||||
<columns>
|
||||
<column/>
|
||||
</columns>
|
||||
@ -169,6 +170,7 @@
|
||||
}
|
||||
et2-hbox.dates {
|
||||
padding-left: 5px;
|
||||
width: fit-content;
|
||||
}
|
||||
.meetingWarning tr.th {
|
||||
background-color: #dc2625;
|
||||
@ -176,7 +178,7 @@
|
||||
.meetingWarning tr.row td {
|
||||
font-size: 120% !important;
|
||||
}
|
||||
.meetingRequestError, .meetingRequestChanged, .meetingRequestChangedStatus et2-description[id$=status\]], .meetingRequestParticipantDeleted {
|
||||
.meetingRequestError, .meetingRequestChanged, .meetingRequestChangedStatus et2-description[id$=status\]] {
|
||||
font-style: italic;
|
||||
color: red;
|
||||
}
|
||||
@ -184,7 +186,8 @@
|
||||
padding: 0 !important;
|
||||
padding-left: 0 !important;
|
||||
}
|
||||
.meetingRequestParticipantDeleted {
|
||||
.meetingRequestParticipantDeleted, .meetingRequestChangedValue {
|
||||
font-style: italic;
|
||||
text-decoration: line-through;
|
||||
}
|
||||
</styles>
|
||||
|
Loading…
Reference in New Issue
Block a user