Commit | Line | Data |
---|---|---|
7f254ad8 AE |
1 | <?php |
2 | ||
3 | /** | |
4 | * @file | |
5 | * Contains the Calendar row style plugin. | |
6 | * | |
7 | * This plugin takes the view results, finds the date value for each, | |
8 | * then compares that date to the date range for the current view. | |
9 | * Items that started before or ended after the current date range | |
10 | * are shortened to the current range. Items that extend over more | |
11 | * than one day are cloned to create a calendar item for each day. | |
12 | * The resulting array of results (which may have a different number | |
13 | * of items than the original view result) are then passed back | |
14 | * to the style plugin so they can be displayed in a calendar. | |
15 | */ | |
16 | ||
17 | /** | |
18 | * Plugin which creates a view on the resulting object | |
19 | * and formats it as a Calendar node. | |
20 | */ | |
21 | class calendar_plugin_row_civicrm extends calendar_plugin_row { | |
22 | // Basic properties that let the row style follow relationships. | |
23 | var $base_table = ''; | |
24 | var $base_field = 'id'; | |
25 | function construct() { | |
26 | parent::construct(); | |
27 | if (!civicrm_initialize()) { | |
28 | return; | |
29 | } | |
30 | $this->base_table = $this->definition['base'][0]; | |
31 | } | |
32 | function option_definition() { | |
33 | $options = parent::option_definition(); | |
34 | $options['date_fields'] = array('default' => array()); | |
35 | $options['calendar_date_link'] = array('default' => ''); | |
36 | $options['colors'] = array( | |
37 | 'contains' => array( | |
38 | 'legend' => array('default' => ''), | |
39 | 'calendar_colors_type' => array('default' => array()), | |
40 | ), | |
41 | ); | |
42 | return $options; | |
43 | } | |
44 | ||
45 | /** | |
46 | * Provide a form for setting options. | |
47 | */ | |
48 | function options_form(&$form, &$form_state) { | |
49 | parent::options_form($form, $form_state); | |
50 | ||
51 | $form['markup']['#markup'] = t("The calendar row plugin will format view results as calendar items. Make sure this display has a 'Calendar' format and uses a 'Date' contextual filter, or this plugin will not work correctly."); | |
52 | $form['calendar_date_link'] = array( | |
53 | '#title' => t('Add new date link'), | |
54 | '#type' => 'select', | |
55 | '#default_value' => $this->options['calendar_date_link'], | |
56 | '#options' => array('' => t('No link')) + node_type_get_names(), | |
57 | '#description' => t('Display a link to add a new date of the specified content type. Displayed only to users with appropriate permissions.'), | |
58 | ); | |
59 | $form['colors'] = array( | |
60 | '#type' => 'fieldset', | |
61 | '#title' => t('Legend Colors'), | |
62 | '#description' => t('Set a hex color value (like #ffffff) to use in the calendar legend for each content type. Items with empty values will have no stripe in the calendar and will not be added to the legend.'), | |
63 | ); | |
64 | $form['colors']['legend'] = array( | |
65 | '#type' => 'value', | |
66 | '#value' => '', | |
67 | ); | |
68 | } | |
69 | ||
70 | function pre_render($values) { | |
71 | ||
72 | $ids = array(); | |
73 | foreach ($values as $row) { | |
74 | // Use the $id as the key so we don't create more than one value per object. | |
75 | $id = $row->{$this->field_alias}; | |
76 | $ids[$id] = $id; | |
77 | } | |
78 | // @TODO Move to CiviCRM API, currently API only returns arrays | |
79 | // the render() method of this class and the calander_pluing_style are expecting | |
80 | // an object, hence using DAO. | |
81 | // Sadly neither DAO nor API allows you to load multiple at once eg node_load_multiple() | |
82 | foreach ($ids as $key => $id) { | |
83 | require_once str_replace('_', DIRECTORY_SEPARATOR, $this->definition['dao class']) . '.php'; | |
84 | $dao = New $this->definition['dao class']; | |
85 | $dao->id = $id; | |
86 | $dao->find(); | |
87 | $dao->fetch(); | |
88 | // Make sure no NULL records get through | |
89 | if (!empty($dao->{$this->definition['title field']})) { | |
90 | $this->entities[$dao->id] = $dao; | |
91 | } | |
92 | $dao->release(); | |
93 | } | |
94 | ||
95 | ||
96 | // Identify the date argument and fields that apply to this view. | |
97 | // Preload the Date Views field info for each field, keyed by the | |
98 | // field name, so we know how to retrieve field values from the cached node. | |
99 | $data = date_views_fields($this->base_table); | |
100 | $data = $data['name']; | |
101 | $date_fields = array(); | |
102 | foreach ($this->view->argument as $handler) { | |
103 | if (date_views_handler_is_date($handler, 'argument')) { | |
104 | // If this is the complex Date argument, the date fields are stored in the handler options, | |
105 | // otherwise we are using the simple date field argument handler. | |
106 | if ($handler->definition['handler'] != 'date_views_argument_handler') { | |
107 | $alias = $handler->table_alias . '.' . $handler->field; | |
108 | $info = $data[$alias]; | |
109 | $field_name = str_replace(array('_value2', '_value'), '', $info['real_field_name']); | |
110 | $date_fields[$field_name] = $info; | |
111 | } | |
112 | else { | |
113 | foreach ($handler->options['date_fields'] as $alias) { | |
114 | $info = $data[$alias]; | |
115 | $field_name = str_replace(array('_value2', '_value'), '', $info['real_field_name']); | |
116 | $date_fields[$field_name] = $info; | |
117 | } | |
118 | } | |
119 | $this->date_argument = $handler; | |
120 | $this->date_fields = $date_fields; | |
121 | } | |
122 | } | |
123 | } | |
124 | ||
125 | function render($row) { | |
126 | global $base_url; | |
127 | $date_info = $this->date_argument->view->date_info; | |
128 | $id = $row->{$this->field_alias}; | |
129 | ||
130 | if (!is_numeric($id)) { | |
131 | return $rows; | |
132 | } | |
133 | ||
134 | // Load the specified object: | |
135 | $node = (object) $this->entities[$id]; | |
136 | if (empty($node)) { | |
137 | return; | |
138 | } | |
139 | ||
140 | // There could be more than one date field in a view | |
141 | // so iterate through all of them to find the right values | |
142 | // for this view result. | |
143 | $rows = array(); | |
144 | foreach ($this->date_fields as $field_name => $info) { | |
145 | ||
146 | $table_name = $info['table_name']; | |
147 | $delta_field = $info['delta_field']; | |
148 | $tz_handling = $info['tz_handling']; | |
149 | $tz_field = $info['timezone_field']; | |
150 | $rrule_field = $info['rrule_field']; | |
151 | $is_field = substr($info['real_field_name'], 0, 6) == 'field_'; | |
152 | ||
153 | // Retrieve the field value that matched our query from the cached node. | |
154 | // Find the date and set it to the right timezone. | |
155 | ||
156 | $item = $node->$field_name; | |
157 | $node->date_id = array(); | |
158 | $item_start_date = NULL; | |
159 | $item_end_date = NULL; | |
160 | ||
161 | $db_tz = date_get_timezone_db($tz_handling, isset($item->$tz_field) ? $item->$tz_field : $date_info->display_timezone_name); | |
162 | $to_zone = date_get_timezone($tz_handling, isset($item->$tz_field) ? $item->$tz_field : $date_info->display_timezone_name); | |
163 | $granularity = 'second'; | |
164 | $increment = 1; | |
165 | ||
166 | if ($is_field) { | |
167 | ||
168 | // @TODO Not sure if this is the correct way to retrieve the right language value, but I think so. | |
169 | $lang = $node->language; | |
170 | $delta = isset($row->$delta_field) ? $row->$delta_field : 0; | |
171 | $item = array_key_exists($lang, $item) ? $item[$lang][$delta] : $item['und'][$delta]; | |
172 | ||
173 | // Set the date_id for the node, used to identify which field value to display for | |
174 | // fields that have multiple values. The theme expects it to be an array. | |
175 | $node->date_id = array('calendar.' . $node->id . '.' . $field_name . '.' . $delta); | |
176 | ||
177 | if (!empty($item['value'])) { | |
178 | $item_start_date = new dateObject($item['value'], $db_tz); | |
179 | $item_end_date = array_key_exists('value2', $item) ? new dateObject($item['value2'], $db_tz) : $item_start_date; | |
180 | } | |
181 | ||
182 | $cck_field = field_info_field($field_name); | |
183 | $instance = field_info_instance($this->view->base_table, $field_name, $node->type); | |
184 | $granularity = date_granularity_precision($cck_field['settings']['granularity']); | |
185 | $increment = $instance['widget']['settings']['increment']; | |
186 | } | |
187 | elseif (!$is_field && !empty($item)) { | |
188 | $item_start_date = new dateObject($item, $db_tz); | |
189 | $item_end_date = $item_start_date; | |
190 | $node->date_id = array('calendar.' . $node->id . '.' . $field_name . '.0'); | |
191 | } | |
192 | ||
193 | // If we don't have date value, go no further. | |
194 | if (empty($item_start_date)) { | |
195 | return; | |
196 | } | |
197 | ||
198 | // Set the item date to the proper display timezone; | |
199 | $item_start_date->setTimezone(new dateTimezone($to_zone)); | |
200 | $item_end_date->setTimezone(new dateTimezone($to_zone)); | |
201 | $event = new stdClass(); | |
202 | $event->nid = $node->id; | |
203 | $event->title = $node->{$this->definition['title field']}; | |
204 | //$event->type = $node->event_type_id; | |
205 | $event->date_start = $item_start_date; | |
206 | $event->date_end = $item_end_date; | |
207 | $event->db_tz = $db_tz; | |
208 | $event->to_zone = $to_zone; | |
209 | $event->granularity = $granularity; | |
210 | $event->increment = $increment; | |
211 | $event->field = $is_field ? $item : NULL; | |
212 | $event->row = $row; | |
213 | $event->node = $node; | |
214 | ||
215 | // All calendar row plugins should provide a date_id that the theme can use. | |
216 | $event->date_id = $node->date_id[0]; | |
217 | ||
218 | $nodes = $this->explode_values($event); | |
219 | foreach ($nodes as $node) { | |
220 | $rows[] = $node; | |
221 | } | |
222 | } | |
223 | return $rows; | |
224 | } | |
225 | } | |
226 |