post_status == 'auto-draft' ) throw new Ai1ec_Event_Not_Found( "Post with ID '$data' could not be retrieved from the database." ); // ============================= // = Fetch event from database = // ============================= $query = $wpdb->prepare( "SELECT e.post_id, UNIX_TIMESTAMP( e.start ) as start, UNIX_TIMESTAMP( e.end ) as end, e.allday, e.recurrence_rules, e.exception_rules, e.recurrence_dates, e.exception_dates, e.venue, e.country, e.address, e.city, e.province, e.postal_code, e.show_map, e.contact_name, e.contact_phone, e.contact_email, e.cost, e.ical_feed_url, e.ical_source_url, e.ical_organizer, e.ical_contact, e.ical_uid, " . "GROUP_CONCAT( ttc.term_id ) AS categories, " . "GROUP_CONCAT( ttt.term_id ) AS tags " . "FROM {$wpdb->prefix}ai1ec_events e " . "LEFT JOIN $wpdb->term_relationships tr ON post_id = tr.object_id " . "LEFT JOIN $wpdb->term_taxonomy ttc ON tr.term_taxonomy_id = ttc.term_taxonomy_id AND ttc.taxonomy = 'events_categories' " . "LEFT JOIN $wpdb->term_taxonomy ttt ON tr.term_taxonomy_id = ttt.term_taxonomy_id AND ttt.taxonomy = 'events_tags' " . "WHERE post_id = %d " . "GROUP BY post_id", $data ); $event = $wpdb->get_row( $query ); if( $event === null || $event->post_id === null ) throw new Ai1ec_Event_Not_Found( "Event with ID '$data' could not be retrieved from the database." ); // =========================== // = Assign post to property = // =========================== $this->post = $post; // ========================== // = Assign values to $this = // ========================== foreach( $this as $property => $value ) { if( $property != 'post' ) $this->{$property} = $event->{$property}; } } // =================== // = Post/event data = // =================== elseif( is_array( $data ) ) { // ======================================================= // = Assign each event field the value from the database = // ======================================================= foreach( $this as $property => $value ) { if( $property != 'post' && array_key_exists( $property, $data ) ) { $this->{$property} = $data[$property]; unset( $data[$property] ); } } if( isset( $data['post'] ) ) { $this->post = (object) $data['post']; } else { // ======================================== // = Remaining fields are the post fields = // ======================================== $this->post = (object) $data; } } else { throw new Ai1ec_Invalid_Argument( "Argument to constructor must be integer, array or null, not '$data'." ); } } /** * __set function * * Magic set function * * @param string $name Property name * @param mixed $value Property value * * @return void **/ public function __set( $name, $value ) { // Not currently used... switch( $name ) { default: $this->{$name} = $value; break; } } /** * __get function * * Magic get function * Shortcuts for common formatted versions of event data. * * @param string $name Property name * * @return mixed Property value **/ public function __get( $name ) { global $post, $more, $ai1ec_events_helper; switch( $name ) { case 'uid': return $this->post_id . '@' . bloginfo( 'url' ); // ======================== // = Get short-form dates = // ======================== case 'short_start_time': return $ai1ec_events_helper->get_short_time( $this->start ); case 'short_end_time': return $ai1ec_events_helper->get_short_time( $this->end ); case 'short_start_date': return $ai1ec_events_helper->get_short_date( $this->start ); case 'short_end_date': // Subtract 1 second so that all-day events' end date still // falls within the logical duration of days (since the end date // is always midnight of the following day) return $ai1ec_events_helper->get_short_date( $this->end - 1 ); // ========================= // = Get medium-form dates = // ========================= case 'start_time': return $ai1ec_events_helper->get_medium_time( $this->start ); case 'end_time': return $ai1ec_events_helper->get_medium_time( $this->end ); // ======================= // = Get long-form times = // ======================= case 'long_start_time': return $ai1ec_events_helper->get_long_time( $this->start ); case 'long_end_time': return $ai1ec_events_helper->get_long_time( $this->end ); // ======================= // = Get long-form dates = // ======================= case 'long_start_date': return $ai1ec_events_helper->get_long_date( $this->start ); case 'long_end_date': // Subtract 1 second so that all-day events' end date still // falls within the logical duration of days (since the end date // is always midnight of the following day) return $ai1ec_events_helper->get_long_date( $this->end - 1 ); case 'timespan_html': $timespan = ''; $long_start_date = $this->long_start_date; $long_end_date = $this->long_end_date; if( $this->allday ) { $timespan .= $long_start_date; if( $long_end_date != $long_start_date ) $timespan .= " – $long_end_date"; $timespan = esc_html( $timespan ); $timespan .= ''; $timespan .= __( ' (all-day)', AI1EC_PLUGIN_NAME ); $timespan .= ''; } else { if( $long_end_date != $long_start_date ) $timespan .= esc_html( $this->long_start_time . ' – ' . $this->long_end_time ); elseif( $this->start != $this->end ) $timespan .= esc_html( $this->long_start_time . ' - ' . $this->end_time ); else $timespan .= esc_html( $this->long_start_time ); } return $timespan; // ===================================================== // = Get the post's excerpt for display in popup view. = // ===================================================== case 'post_excerpt': if( ! $this->post->post_excerpt ) { $content = strip_tags( strip_shortcodes( $this->post->post_content ) ); $content = preg_replace( '/\s+/', ' ', $content ); $words = explode( ' ', $content ); if( count( $words ) > 25 ) $this->post->post_excerpt = implode( ' ', array_slice( $words, 0, 25 ) ) . ' [...]'; else $this->post->post_excerpt = $content; } return $this->post->post_excerpt; // =============================================================== // = Return any available location details separated by newlines = // =============================================================== case 'location': $location = ''; if( $this->venue ) $location .= "$this->venue\n"; if( $this->address ) { $bits = explode( ',', $this->address ); $bits = array_map( 'trim', $bits ); // If more than three comma-separated values, treat first value as // the street address, last value as the country, and everything // in the middle as the city, state, etc. if( count( $bits ) >= 3 ) { // Append the street address $street_address = array_shift( $bits ) . "\n"; if( $street_address ) $location .= $street_address; // Save the country for the last line $country = array_pop( $bits ); // Append the middle bit(s) (filtering out any zero-length strings) $bits = array_filter( $bits, 'strval' ); if( $bits ) $location .= join( ',', $bits ) . "\n"; if( $country ) $location .= $country . "\n"; } else { // There are two or less comma-separated values, so just append // them each on their own line (filtering out any zero-length strings) $bits = array_filter( $bits, 'strval' ); $location .= join( "\n", $bits ); } } return $location; // ====================== // = Categories as HTML = // ====================== case 'categories_html': if( $this->categories_html === null ) { $categories = wp_get_post_terms( $this->post_id, 'events_categories' ); foreach( $categories as &$category ) { $category = 'description ? 'title="' . esc_attr( $category->description ) . '" ' : '' ) . 'href="' . get_term_link( $category ) . '">' . $ai1ec_events_helper->get_category_color_square( $category->term_id ) . ' ' . esc_html( $category->name ) . ''; } $this->categories_html = join( ' ', $categories ); } return $this->categories_html; // ================ // = Tags as HTML = // ================ case 'tags_html': if( $this->tags_html === null ) { $tags = wp_get_post_terms( $this->post_id, 'events_tags' ); foreach( $tags as &$tag ) { $tag = 'description ? 'title="' . esc_attr( $tag->description ) . '" ' : '' ) . 'href="' . get_term_link( $tag ) . '">' . esc_html( $tag->name ) . ''; } $this->tags_html = join( ' ', $tags ); } return $this->tags_html; // ====================================== // = Style attribute for event category = // ====================================== case 'color_style': if( $this->color_style === null ) { $categories = wp_get_post_terms( $this->post_id, 'events_categories' ); $this->color_style = $ai1ec_events_helper->get_event_category_color_style( $categories[0]->term_id, $this->allday ); } return $this->color_style; // =============================================== // = HTML of category color boxes for this event = // =============================================== case 'category_colors': if( $this->category_colors === null ) { $categories = wp_get_post_terms( $this->post_id, 'events_categories' ); $this->category_colors = $ai1ec_events_helper->get_event_category_colors( $categories ); } return $this->category_colors; // ======================== // = Contact info as HTML = // ======================== case 'contact_html': $contact = ''; if( $this->contact_name ) $contact .= '' . esc_html( $this->contact_name ) . '
'; if( $this->contact_phone ) $contact .= esc_html( $this->contact_phone ) . '
'; if( $this->contact_email ) $contact .= '' . esc_html( $this->contact_email ) . ''; return $contact; // =========================== // = Recurrence info as HTML = // =========================== case 'recurrence_html': if( ! $this->recurrence_rules ) return null; $rules = $ai1ec_events_helper->parse_recurrence_rules( $this ); $patterns = $ai1ec_events_helper->get_repeat_patterns(); $recurrence_html = '' . esc_html( $patterns[$rules['repeat']] ) . ''; unset( $rules['repeat'] ); if( $rules['count'] ) { $rules['count'] = sprintf( _n( 'ending after %d time', 'ending after %d times', $rules['count'], AI1EC_PLUGIN_NAME ), $rules['count'] ); } else { unset( $rules['count'] ); } if( $rules['until'] ) { $rules['until'] = sprintf( __( 'until %s', AI1EC_PLUGIN_NAME ), esc_html( $ai1ec_events_helper->get_long_date( $rules['until'], false ) ) ); } else { unset( $rules['until'] ); } // The "end" specifier shouldn't be output unset( $rules['end'] ); $end = join( __( ' or ', AI1EC_PLUGIN_NAME ), $rules ); if( $end ) $recurrence_html .= ', ' . $end; return $recurrence_html; } } /** * save function * * Saves the current event data to the database. If $this->post_id exists, * but $update is false, creates a new record in the ai1ec_events table of * this event data, but does not try to create a new post. Else if $update * is true, updates existing event record. If $this->post_id is empty, * creates a new post AND record in the ai1ec_events table for this event. * * @param bool $update Whether to update an existing event or create a * new one * @return int The post_id of the new or existing event. **/ function save( $update = false ) { global $wpdb, $ai1ec_events_helper; // =========================== // = Insert events meta data = // =========================== $columns = array( 'post_id' => $this->post_id, 'start' => $this->start, 'end' => $this->end, 'allday' => $this->allday, 'recurrence_rules' => $this->recurrence_rules, 'exception_rules' => $this->exception_rules, 'recurrence_dates' => $this->recurrence_dates, 'exception_dates' => $this->exception_dates, 'venue' => $this->venue, 'country' => $this->country, 'address' => $this->address, 'city' => $this->city, 'province' => $this->province, 'postal_code' => $this->postal_code, 'show_map' => $this->show_map, 'contact_name' => $this->contact_name, 'contact_phone' => $this->contact_phone, 'contact_email' => $this->contact_email, 'cost' => $this->cost, 'ical_feed_url' => $this->ical_feed_url, 'ical_source_url' => $this->ical_source_url, 'ical_uid' => $this->ical_uid, ); $format = array( '%d', 'FROM_UNIXTIME( %d )', 'FROM_UNIXTIME( %d )', '%d', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%s', '%d', '%s', '%s', '%s', '%s', '%s', '%s', '%s' ); $table_name = $wpdb->prefix . 'ai1ec_events'; if( $this->post_id ) { if( ! $update ) { // ========================= // = Insert new event data = // ========================= $wpdb->query( $wpdb->prepare( "INSERT INTO $table_name ( " . join( ', ', array_keys( $columns ) ) . " ) VALUES ( " . join( ', ', $format ) . " )", $columns ) ); } else { // ============================== // = Update existing event data = // ============================== $where = array( 'post_id' => $this->post_id ); $where_escape = array( '%d' ); $wpdb->update( $table_name, $columns, $where, $format, $where_escape ); } } else { // =================== // = Insert new post = // =================== $this->post_id = wp_insert_post( $this->post ); $columns['post_id'] = $this->post_id; wp_set_post_terms( $this->post_id, $this->categories, 'events_categories' ); wp_set_post_terms( $this->post_id, $this->tags, 'events_tags' ); // ========================= // = Insert new event data = // ========================= $wpdb->query( $wpdb->prepare( "INSERT INTO $table_name ( " . join( ', ', array_keys( $columns ) ) . " ) VALUES ( " . join( ', ', $format ) . " )", $columns ) ); } return $this->post_id; } /** * getProperty function * * Returns $property value * * @param string $property Property name * * @return mixed **/ function getProperty( $property ) { return $this->property; } /** * isWholeDay function * * Determines if an event is a whole day event * * @return bool **/ function isWholeDay() { return ( bool ) $this->allday; } /** * getStart function * * Returns the start time of the event * * @return int **/ function getStart() { return $this->start; } /** * getEnd function * * Returns the end time of the event * * @return int **/ function getEnd() { return $this->end; } /** * getFrequency function * * Returns the frequency of the event * * @return object **/ function getFrequency() { return new SG_iCal_Freq( $this->recurrence_rules, $this->start ); } /** * getDuration function * * Returns the duration of the event * * @return int **/ function getDuration() { return $this->end - $this->start; } } // END class