Exemplo n.º 1
0
/**
 * Find a list of pairs specifying the times the event occurs, for 20 years into the future, in user-time.
 *
 * @param  ID_TEXT		The timezone for the event (NULL: current user's timezone)
 * @param  BINARY			Whether the time should be converted to the viewer's own timezone
 * @param  integer		The year the event starts at. This and the below are in server time
 * @param  integer		The month the event starts at
 * @param  integer		The day the event starts at
 * @param  integer		The hour the event starts at
 * @param  integer		The minute the event starts at
 * @param  ?integer		The year the event ends at (NULL: not a multi day event)
 * @param  ?integer		The month the event ends at (NULL: not a multi day event)
 * @param  ?integer		The day the event ends at (NULL: not a multi day event)
 * @param  ?integer		The hour the event ends at (NULL: not a multi day event / all day event)
 * @param  ?integer		The minute the event ends at (NULL: not a multi day event / all day event)
 * @param  string			The event recurrence
 * @param  ?integer		The number of recurrences (NULL: none/infinite)
 * @param  ?TIME			The timestamp that found times must exceed. In user-time (NULL: now)
 * @param  ?TIME			The timestamp that found times must not exceed. In user-time (NULL: 20 years time)
 * @return array			A list of pairs for period times (timestamps, in user-time). Actually a series of pairs, 'window-bound timestamps' is first pair, then 'true coverage timestamps', then 'true coverage timestamps without timezone conversions'
 */
function find_periods_recurrence($timezone, $do_timezone_conv, $start_year, $start_month, $start_day, $start_hour, $start_minute, $end_year, $end_month, $end_day, $end_hour, $end_minute, $recurrence, $recurrences, $period_start = NULL, $period_end = NULL)
{
    if ($recurrences === 0) {
        return array();
    }
    if (is_null($period_start)) {
        $period_start = utctime_to_usertime(time());
    }
    if (is_null($period_end)) {
        $period_end = utctime_to_usertime(time() + 60 * 60 * 24 * 360 * 20);
    }
    $times = array();
    $i = 0;
    $parts = explode(' ', $recurrence);
    if (count($parts) != 1) {
        $recurrence = $parts[0];
        $mask = $parts[1];
        $mask_len = strlen($mask);
    } else {
        $mask = '1';
        $mask_len = 1;
    }
    $a = 0;
    $dif_day = 0;
    $dif_month = 0;
    $dif_year = 0;
    $dif = utctime_to_usertime() - utctime_to_usertime(mktime($start_hour, $start_minute, 0, $start_month, $start_day, $start_year));
    switch ($recurrence) {
        case 'daily':
            $dif_day = 1;
            if ($dif > 60 * 60 * 24 * 10 && $mask_len == 0) {
                $zoom = $dif_day * intval(floor(floatval($dif) / (60.0 * 60.0 * 24.0)));
                $start_day += $zoom;
                if (!is_null($end_day)) {
                    $end_day += $zoom;
                }
            }
            break;
        case 'weekly':
            $dif_day = 7;
            if ($dif > 60 * 60 * 24 * 70 && $mask_len == 0) {
                $zoom = $dif_day * intval(floor(floatval($dif) / (60.0 * 60.0 * 24.0))) - 70;
                $start_day += $zoom;
                if (!is_null($end_day)) {
                    $end_day += $zoom;
                }
            }
            break;
        case 'monthly':
            $dif_month = 1;
            if ($dif > 60 * 60 * 24 * 31 * 10 && $mask_len == 0) {
                $zoom = $dif_month * intval(floor(floatval($dif) / (60.0 * 60.0 * 24.0 * 31.0))) - 10;
                $start_month += $zoom;
                if (!is_null($end_day)) {
                    $end_day += $zoom;
                }
            }
            break;
        case 'yearly':
            $dif_year = 1;
            if ($dif > 60 * 60 * 24 * 365 * 10 && $mask_len == 0) {
                $zoom = $dif_year * intval(floor(floatval($dif) / (60.0 * 60.0 * 24.0 * 365.0))) - 1;
                $start_year += $zoom;
                if (!is_null($end_day)) {
                    $end_day += $zoom;
                }
            }
            break;
    }
    $_b = mixed();
    $b = mixed();
    do {
        /*
        Consider this scenario...
        
        An event ends at end of 1/1/2012 (23:59), which is 22:59 in UTC if they are in +1 timezone
        
        Therefore the event, which is stored in UTC, needs a server time of 22:59 before going through cal_utctime_to_usertime
        
        The server already has the day stored UTC which may be different to the day stored for the +1 timezone (in fact either the start or end day will be stored differently, assuming there is an end day)
        */
        $_a = cal_get_start_utctime_for_event($timezone, $start_year, $start_month, $start_day, $start_hour, $start_minute, $do_timezone_conv == 1);
        $a = cal_utctime_to_usertime($_a, $timezone, $do_timezone_conv == 1);
        if (is_null($start_hour) && (is_null($end_year) || is_null($end_month) || is_null($end_day))) {
            // Should not be needed, but normalise possible database error
            $start_minute = NULL;
            $start_hour = NULL;
            $end_minute = NULL;
            $end_hour = NULL;
            $end_day = $start_day;
            $end_month = $start_month;
            $end_year = $start_year;
        }
        if (is_null($end_year) || is_null($end_month) || is_null($end_day)) {
            $_b = NULL;
            $b = NULL;
        } else {
            $_b = cal_get_end_utctime_for_event($timezone, $end_year, $end_month, $end_day, $end_hour, $end_minute, $do_timezone_conv == 1);
            $b = cal_utctime_to_usertime($_b, $timezone, $do_timezone_conv == 1);
        }
        $starts_within = $a >= $period_start && $a < $period_end;
        $ends_within = $b > $period_start && $b <= $period_end;
        $spans = $a < $period_start && $b > $period_end;
        if (($starts_within || $ends_within || $spans) && in_array($mask[$i % $mask_len], array('1', 'y'))) {
            $times[] = array(max($period_start, $a), min($period_end, $b), $a, $b, $_a, $_b);
        }
        $i++;
        $start_day += $dif_day;
        $start_month += $dif_month;
        $start_year += $dif_year;
        if (!is_null($end_year) && !is_null($end_month) && !is_null($end_day)) {
            $end_day += $dif_day;
            $end_month += $dif_month;
            $end_year += $dif_year;
        }
        if ($i == 300) {
            break;
        }
        // Let's be reasonable
    } while ($recurrence != '' && $recurrence != 'none' && $a < $period_end && (is_null($recurrences) || $i < $recurrences));
    return $times;
}
Exemplo n.º 2
0
 /**
  * Subscribe for reminders to an event.
  *
  * @return tempcode		The UI
  */
 function _subscribe_event()
 {
     $title = get_page_title('SUBSCRIBE_EVENT');
     $seconds_before = intval(floatval(post_param('hours_before')) * 3600.0);
     $id = get_param_integer('id');
     // The event ID
     $events = $GLOBALS['SITE_DB']->query_select('calendar_events', array('*'), array('id' => get_param_integer('id')), '', 1);
     $event = $events[0];
     $rem_id = $GLOBALS['SITE_DB']->query_insert('calendar_reminders', array('e_id' => $id, 'n_member_id' => get_member(), 'n_seconds_before' => $seconds_before), true);
     if (has_actual_page_access($GLOBALS['FORUM_DRIVER']->get_guest_id(), 'calendar') && has_category_access($GLOBALS['FORUM_DRIVER']->get_guest_id(), 'calendar', strval($event['e_type']))) {
         $_from = cal_get_start_utctime_for_event($event['e_timezone'], $event['e_start_year'], $event['e_start_month'], $event['e_start_day'], $event['e_start_hour'], $event['e_start_minute'], $event['e_do_timezone_conv'] == 1);
         $from = cal_utctime_to_usertime($_from, $event['e_timezone'], $event['e_do_timezone_conv'] == 1);
         $to = mixed();
         if (!is_null($event['e_end_year']) && !is_null($event['e_end_month']) && !is_null($event['e_end_day'])) {
             $_to = cal_get_end_utctime_for_event($event['e_timezone'], $event['e_end_year'], $event['e_end_month'], $event['e_end_day'], $event['e_end_hour'], $event['e_end_minute'], $event['e_do_timezone_conv'] == 1);
             $to = cal_utctime_to_usertime($_to, $event['e_timezone'], $event['e_do_timezone_conv'] == 1);
         }
         syndicate_described_activity('calendar:ACTIVITY_SUBSCRIBED_EVENT', get_translated_text($event['e_title']), date_range($from, $to, !is_null($event['e_start_hour'])), '', '_SEARCH:calendar:view:' . strval($id), '', '', 'calendar', 1, NULL, true);
     }
     // Add next reminder to job system
     $recurrences = find_periods_recurrence($event['e_timezone'], 1, $event['e_start_year'], $event['e_start_month'], $event['e_start_day'], is_null($event['e_start_hour']) ? 0 : $event['e_start_hour'], is_null($event['e_start_minute']) ? 0 : $event['e_start_minute'], $event['e_end_year'], $event['e_end_month'], $event['e_end_day'], is_null($event['e_end_hour']) ? 0 : $event['e_end_hour'], is_null($event['e_end_minute']) ? 0 : $event['e_end_minute'], $event['e_recurrence'], min(1, $event['e_recurrences']));
     if (array_key_exists(0, $recurrences)) {
         $GLOBALS['SITE_DB']->query_insert('calendar_jobs', array('j_time' => usertime_to_utctime($recurrences[0][0]) - $seconds_before, 'j_reminder_id' => $rem_id, 'j_member_id' => get_member(), 'j_event_id' => get_param_integer('id')));
     }
     $url = build_url(array('page' => '_SELF', 'type' => 'view', 'id' => get_param_integer('id')), '_SELF');
     return redirect_screen($title, $url, do_lang_tempcode('SUCCESS'));
 }
Exemplo n.º 3
0
 /**
  * Standard aed_module edit actualiser.
  *
  * @param  ID_TEXT		The entry being edited
  * @return tempcode		Description shown after editing
  */
 function edit_actualisation($_id)
 {
     $id = intval($_id);
     $rows = $GLOBALS['SITE_DB']->query_select('calendar_events', array('*'), array('id' => $id), '', 1);
     if (!array_key_exists(0, $rows)) {
         warn_exit(do_lang_tempcode('MISSING_RESOURCE'));
     }
     $event = $rows[0];
     check_edit_permission($event['e_is_public'] == 1 ? 'mid' : 'low', $event['e_submitter']);
     $delete_status = post_param('delete', '0');
     list($type, $recurrence, $_recurrences, $title, $content, $priority, $is_public, $_start_year, $_start_month, $_start_day, $_start_hour, $_start_minute, $_end_year, $_end_month, $_end_day, $_end_hour, $_end_minute, $timezone, $do_timezone_conv) = $this->get_event_parameters();
     $allow_trackbacks = post_param_integer('allow_trackbacks', fractional_edit() ? INTEGER_MAGIC_NULL : 0);
     $allow_rating = post_param_integer('allow_rating', fractional_edit() ? INTEGER_MAGIC_NULL : 0);
     $allow_comments = post_param_integer('allow_comments', fractional_edit() ? INTEGER_MAGIC_NULL : 0);
     $notes = post_param('notes', STRING_MAGIC_NULL);
     $validated = post_param_integer('validated', fractional_edit() ? INTEGER_MAGIC_NULL : 0);
     $seg_recurrences = post_param_integer('seg_recurrences', fractional_edit() ? INTEGER_MAGIC_NULL : 0);
     $fixed_past = false;
     if ($delete_status == '3' && !fractional_edit()) {
         // Fix past occurences
         $past_times = find_periods_recurrence($event['e_timezone'], 1, $event['e_start_year'], $event['e_start_month'], $event['e_start_day'], $event['e_start_hour'], $event['e_start_minute'], $event['e_end_year'], $event['e_end_month'], $event['e_end_day'], $event['e_end_hour'], $event['e_end_minute'], $event['e_recurrence'], $event['e_recurrences'], utctime_to_usertime(mktime($event['e_start_hour'], $event['e_start_minute'], 0, $event['e_start_month'], $event['e_start_day'], $event['e_start_year'])), utctime_to_usertime(time()));
         if (count($past_times) > 0) {
             foreach ($past_times as $past_time) {
                 list($start_year, $start_month, $start_day, $start_hour, $start_minute) = explode('-', date('Y-m-d-h-i', usertime_to_utctime($past_time[0])));
                 if (is_null($past_time[1])) {
                     list($end_year, $end_month, $end_day, $end_hour, $end_minute) = array(NULL, NULL, NULL, NULL, NULL);
                 } else {
                     $explode = explode('-', date('Y-m-d-h-i', usertime_to_utctime($past_time[1])));
                     $end_year = intval($explode[0]);
                     $end_month = intval($explode[1]);
                     $end_day = intval($explode[2]);
                     $end_hour = intval($explode[3]);
                     $end_minute = intval($explode[4]);
                 }
                 add_calendar_event($event['e_type'], 'none', NULL, 0, get_translated_text($event['e_title']), get_translated_text($event['e_content']), $event['e_priority'], $event['e_is_public'], intval($start_year), intval($start_month), intval($start_day), intval($start_hour), intval($start_minute), $end_year, $end_month, $end_day, $end_hour, $end_minute, $timezone, $do_timezone_conv, $validated, $allow_rating, $allow_comments, $allow_trackbacks, $notes);
             }
             if (is_null($_recurrences)) {
                 $recurrences = NULL;
             } else {
                 $recurrences = max(0, $_recurrences - count($past_times));
             }
             // Find next occurence in future
             if (count($past_times) == 0) {
                 $start_year = $_start_year;
                 $start_month = $_start_month;
                 $start_day = $_start_day;
                 $start_hour = $_start_hour;
                 $start_minute = $_start_minute;
                 $end_year = $_end_year;
                 $end_month = $_end_month;
                 $end_day = $_end_day;
                 $end_hour = $_end_hour;
                 $end_minute = $_end_minute;
             }
             $past_times = find_periods_recurrence($event['e_timezone'], 1, $start_year, $start_month, $start_day, $start_hour, $start_minute, $end_year, $end_month, $end_day, $end_hour, $end_minute, $event['e_recurrence'], 1, time());
             if (array_key_exists(0, $past_times)) {
                 $past_time = $past_times[0];
                 $explode = explode('-', date('Y-m-d-h-i', $past_time[0]));
                 $start_year = intval($explode[0]);
                 $start_month = intval($explode[1]);
                 $start_day = intval($explode[2]);
                 $start_hour = intval($explode[3]);
                 $start_minute = intval($explode[4]);
                 if (is_null($past_time[1])) {
                     list($end_year, $end_month, $end_day, $end_hour, $end_minute) = array(NULL, NULL, NULL, NULL, NULL);
                 } else {
                     $explode = explode('-', date('Y-m-d-h-i', $past_time[1]));
                     $end_year = intval($explode[0]);
                     $end_month = intval($explode[1]);
                     $end_day = intval($explode[2]);
                     $end_hour = intval($explode[3]);
                     $end_minute = intval($explode[4]);
                 }
             } else {
                 $recurrences = 0;
             }
             $fixed_past = true;
         }
     }
     if (!$fixed_past) {
         $start_year = $_start_year;
         $start_month = $_start_month;
         $start_day = $_start_day;
         $start_hour = $_start_hour;
         $start_minute = $_start_minute;
         $end_year = $_end_year;
         $end_month = $_end_month;
         $end_day = $_end_day;
         $end_hour = $_end_hour;
         $end_minute = $_end_minute;
         $recurrences = $_recurrences;
     }
     if ($validated == 1 && $GLOBALS['SITE_DB']->query_value('calendar_events', 'validated', array('id' => $id)) == 0) {
         if (has_actual_page_access($GLOBALS['FORUM_DRIVER']->get_guest_id(), 'calendar') && has_category_access($GLOBALS['FORUM_DRIVER']->get_guest_id(), 'calendar', strval($type))) {
             $_from = cal_get_start_utctime_for_event($timezone, $start_year, $start_month, $start_day, $start_hour, $start_minute, true);
             $from = cal_utctime_to_usertime($_from, $timezone, false);
             $to = mixed();
             if (!is_null($end_year) && !is_null($end_month) && !is_null($end_day)) {
                 $_to = cal_get_end_utctime_for_event($timezone, $end_year, $end_month, $end_day, $end_hour, $end_minute, true);
                 $to = cal_utctime_to_usertime($_to, $timezone, false);
             }
             $submitter = $GLOBALS['SITE_DB']->query_value('calendar_events', 'e_submitter', array('id' => $id));
             syndicate_described_activity($submitter != get_member() ? 'calendar:ACTIVITY_VALIDATE_CALENDAR_EVENT' : 'calendar:ACTIVITY_CALENDAR_EVENT', $title, date_range($from, $to, !is_null($start_hour)), '', '_SEARCH:calendar:view:' . strval($id), '', '', 'calendar', 1, NULL, true);
         }
     }
     edit_calendar_event($id, $type, $recurrence, $recurrences, $seg_recurrences, $title, $content, $priority, $is_public, $start_year, $start_month, $start_day, $start_hour, $start_minute, $end_year, $end_month, $end_day, $end_hour, $end_minute, $timezone, $do_timezone_conv, post_param('meta_keywords', STRING_MAGIC_NULL), post_param('meta_description', STRING_MAGIC_NULL), $validated, $allow_rating, $allow_comments, $allow_trackbacks, $notes);
     if (!fractional_edit()) {
         $conflicts = detect_conflicts(get_member(), $id, $start_year, $start_month, $start_day, $start_hour, $start_minute, $end_year, $end_month, $end_day, $end_hour, $end_minute, $recurrence, $recurrences);
         $_description = is_null($conflicts) ? paragraph(do_lang_tempcode('SUCCESS')) : $conflicts;
         regenerate_event_reminder_jobs($id);
     } else {
         $_description = do_lang_tempcode('SUCCESS');
     }
     $this->donext_type = $type;
     $this->donext_date = strval($start_year) . '-' . strval($start_month) . '-' . strval($start_day);
     return $_description;
 }