Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
page_calendar_events_search.inc
1 <?php
17 require_once SQ_PACKAGES_PATH.'/search/search_page/search_page.inc';
18 require_once SQ_PACKAGES_PATH.'/calendar/lib/calendar_common.inc';
19 
20 
30 {
31 
32  /* Fuzzy date type options
33  *
34  * @var array
35  */
36  var $fuzzy_date_types = Array(
37  'today' => 1,
38  'tomorrow'=> 1,
39  'yesterday' => 1,
40  'this_weekend' => 0,
41  'next_weekend' => 0,
42  'previous_weekend' => 0,
43  'this_week' => 1,
44  'next_week' => 1,
45  'previous_week' => 1,
46  'this_fortnight' => 0,
47  'next_fortnight' => 0,
48  'previous_fortnight' => 0,
49  'this_month' => 1,
50  'next_month' => 1,
51  'previous_month' => 1,
52  'this_year' => 0,
53  'next_year' => 0,
54  'previous_year' => 0,
55  'anytime' => 0
56  );
57 
58 
67  function __construct($assetid=0)
68  {
69  $this->_ser_attrs = TRUE;
70  parent::__construct($assetid);
71 
72  }//end constructor
73 
74 
81  function printContents()
82  {
83  if (isset($_REQUEST[$this->getPrefix().'_submit_button']) && empty($_REQUEST['mode'])) {
84  $_REQUEST['mode'] = 'results';
85  }
86 
87  $mode = array_get_index($_REQUEST, 'mode', '');
88 
89  if (empty($mode)) {
90  // we dont know what button was pressed, so see if we have any query vars
91  // that show evidence that a search has been performed without submitting
92  // the button value
93  $queries = $this->_getEventSearchQuery();
94  foreach ($queries as $field_name => $value) {
95  if (!empty($value)) {
96  $mode = 'results';
97  break;
98  } else {
99  unset($queries[$field_name]);
100  }
101  }
102  $this->_tmp['searched_fqueries'] = $queries;
103  }
104 
105  if (empty($_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id])) {
106  $_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id] = Array();
107  } else if ($mode=='results') {
108  // preserve the previous query
109  $this->_tmp['potential_searched_fqueries'] = $_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id];
110  }
111 
112  parent::printContents();
113 
114  }//end printContents()
115 
116 
129  function processSearch($search=Array())
130  {
131  // Get the stored search parameters relevant to the event filters
132  $event_search = Array();
133  foreach($search as $key => $val) {
134  if (strpos($key, 'f:') === 0) {
135  unset($search[$key]);
136  $event_search[substr($key, 2)] = $val;
137  }
138  }
139 
140  $sm_result = parent::processSearch($search);
141  $sm_queries = $this->_getSearchedQueries();
142 
143  // Pick the multi-date assets from the root node
144  $multi_date_assets = Array();
145  $root_nodes = $this->getRootNodes(FALSE);
146  foreach($root_nodes as $root_node) {
147  $multi_date_assets += $GLOBALS['SQ_SYSTEM']->am->getChildren($root_node, 'calendar_event_multi_date', TRUE);
148  }
149 
150  // Map the "single" and "recurring" events to their respective multi-date event asset
151  $multi_date_events = Array();
152  foreach($multi_date_assets as $event_assetid => $val) {
153  // Include the events assoicated with the multi-date event into the search result
154  $multi_events = array_keys($GLOBALS['SQ_SYSTEM']->am->getChildren($event_assetid, 'calendar_event', FALSE, TRUE));
155  foreach($multi_events as $multi_event_id) {
156  if (isset($sm_result[$event_assetid])) {
157  if (!isset($sm_result[$multi_event_id])) {
158  $sm_result[$multi_event_id] = 1;
159  }
160  }
161  $multi_date_events[$multi_event_id] = $event_assetid;
162  }//end foreach
163  }//end foreach
164 
165  $sm_result_assetids = array_keys($sm_result);
166 
167  $date_filter_result = $this->processEventSearch($event_search);
168 
169  // Grouping logic for combing date filters and search field results
170  $result = Array();
171  if ($this->attr('main_logic') == 'AND') {
172  foreach($date_filter_result as $event => $start_ts) {
173  $assetid = substr($event, 0, strpos($event, ':'));
174  if (isset($multi_date_events[$assetid]) && strpos($event, ',type_code=') !== FALSE) {
175  $event = substr($event, 0, strpos($event, ',type_code=')).',type_code=calendar_event_multi_date';
176  }
177  if (!isset($result[$event]) && (empty($sm_queries) || in_array($assetid, $sm_result_assetids))) {
178  $result[$event] = array_get_index($sm_result, $assetid, 1);
179  }
180  }//end foreach
181  } else {
182  // Get the event instances for the events in the regular search result
183  $sm_fields_result = $this->getEventInstances($sm_result_assetids);
184  $combined_result = array_merge($sm_fields_result, $date_filter_result);
185  foreach($combined_result as $event => $start_ts) {
186  $assetid = substr($event, 0, strpos($event, ':'));
187  if (isset($multi_date_events[$assetid]) && strpos($event, ',type_code=') !== FALSE) {
188  $event = substr($event, 0, strpos($event, ',type_code=')).',type_code=calendar_event_multi_date';
189  }
190  $result[$event] = array_get_index($sm_result, $assetid, 1);
191  }//end foreach
192  }
193 
194  return $result;
195 
196  }//end processSearch()
197 
198 
199  /*
200  * Get all the instances for supplied events
201  *
202  * @param array $event_assetids Event assetids
203  *
204  * @return array
205  * @access public
206  */
207  function getEventInstances($event_assetids)
208  {
209  $query = $this->_getEventSearchQuery();
210  $events = $this->_getEvents();
211 
212  $relevant_events = Array();
213  foreach($events as $event) {
214  if (isset($event['assetid']) && in_array($event['assetid'], $event_assetids)) {
215  $relevant_events[] = $event;
216  }
217  }//end foreach
218  if (empty($relevant_events)) {
219  return Array();
220  }
221 
222  $grouping_logic = $this->attr('events_filter_logic');
223  $result = FALSE;
224  $instances = FALSE;
225  if ($this->isEmptyQuery($query)) {
226  $instances = Calendar_Common::getWholeEventInstances($relevant_events, '1970-01-01', '2030-12-31');
227  } else {
228  foreach($query as $query_field => $query_data) {
229  if (empty($query_data)) {
230  continue;
231  }
232  // Get event result for each filter
233  $field_result = Array();
234  foreach($query_data as $query_date) {
235  if (empty($query_date['from']) || empty($query_date['to'])) {
236  continue 2;
237  }
238  $field_result = array_merge($field_result, Calendar_Common::getWholeEventInstances($relevant_events, $query_date['from'], $query_date['to']));
239  }//end foreach
240 
241  // Combine the submitted field result based on the selected logical grouping
242  if ($instances === FALSE) {
243  $instances = $field_result;
244  } else {
245  $instances = $grouping_logic == 'AND' ? array_intersect($result, $field_result) : array_merge($result, $field_result);
246  }
247  }//end foreach
248  }
249 
250  return $instances ? $instances : Array();
251 
252  }//end getEventInstances()
253 
254 
255  /*
256  * Process events search
257  *
258  * @param array $search The search variables used for stored searches
259  *
260  * @return array
261  * @access public
262  */
263  function processEventSearch($search=Array())
264  {
265  $query = $this->_getEventSearchQuery($search);
266 
267  // See if we have result in the cache
268  $cache_key = md5(serialize($query).$this->attr('main_logic').$this->attr('events_filter_logic'));
269  $cm = $GLOBALS['SQ_SYSTEM']->am->getSystemAsset('cache_manager');
270  $result = $cm->loadFromCache($this->id, $this->type(), $cache_key);
271  if ($result !== FALSE) {
272  return unserialize($result);
273  }
274 
275  // Get all the relevant events for the searching
276  $events = $this->_getEvents();
277 
278  // Save the search terms into the session so that we can use them for
279  // search within search results
280  $_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id] = $query;
281 
282  // If empty Date search is allowed then search needs to be carried out
283  // in all the event instances, regardless of date filter query submitted
284  if ($this->attr('events_filter_allow_empty_search') && $this->isEmptyQuery($query)) {
285  $query = Array(
286  'default_field' => Array(
287  0 => Array(
288  'from' => '1970-01-01',
289  'to' => '2030-12-31',
290  )
291  )
292  );
293  }//end if
294 
295  if (empty($events) || empty($query)) {
296  return Array();
297  }
298 
299  // Grouping logic for the filters, AND/OR
300  $grouping_logic = $this->attr('events_filter_logic');
301 
302  $result = FALSE;
303 
304  foreach($query as $query_field => $query_data) {
305  if (empty($query_data)) {
306  continue;
307  }
308 
309  // Get event result for each filter
310  $field_result = Array();
311  foreach($query_data as $query_date) {
312  if (empty($query_date['from']) || empty($query_date['to'])) {
313  continue 2;
314  }
315  $field_result = array_merge($field_result, Calendar_Common::getWholeEventInstances($events, $query_date['from'], $query_date['to']));
316  }//end foreach
317 
318 
319 
320  // Combine the submitted field result based on the selected logical grouping
321  if ($result === FALSE) {
322  $result = $field_result;
323  } else {
324  $result = $grouping_logic == 'AND' ? array_intersect($result, $field_result) : array_merge($result, $field_result);
325  }
326  }//end foreach
327 
328  if (is_array($result)) {
329  $cm->saveToCache($this->id, $this->type(), $cache_key, serialize($result));
330  }
331 
332  return $result ? $result : Array();
333 
334  }//end processEventSearch()
335 
336 
337  /*
338  * Check if the submitted date filter query is empty
339  *
340  * @param array $query
341  *
342  * @return boolean
343  * @access public
344  */
345  function isEmptyQuery($query)
346  {
347  // Date filter queries grouping logic
348  $grouping_logic = $this->attr('events_filter_logic');
349 
350  $empty = $grouping_logic == 'AND' ? TRUE : FALSE;
351  foreach($query as $field => $val) {
352  foreach($val as $query_data) {
353  if ($grouping_logic == 'AND' && !empty($query_data['from']) && !empty($query_data['to'])) {
354  $empty = FALSE;
355  break 2;
356  } else if ($grouping_logic == 'OR' && empty($query_data['from']) && empty($query_data['to'])) {
357  $empty = TRUE;
358  break 2;
359  }
360  }
361  }
362 
363  return $empty;
364 
365  }//end isEmptyQuery()
366 
367 
368  /*
369  * Get "date" query data submitted in Event Search page
370  *
371  * @return array
372  * @access private
373  */
374  function _getEventSearchQuery($search=Array())
375  {
376  if (isset($this->_tmp['searched_fqueries'])) {
377  return $this->_tmp['searched_fqueries'];
378  }
379 
380  $filters = $this->attr('events_filters');
381  $queries = Array();
382 
383  $pmap = $this->getAttribute('stored_query_session');
384  $pmap_params = $pmap->getParameters();
385 
386  foreach ($filters as $field_name => $field_details) {
387  $queries[$field_name] = Array();
388  $query_var = 'queries_'.$field_name.'_fquery';
389  $clean_query_var = str_replace('.', '_', $query_var);
390 
391  $queries[$field_name] = $this->_processDateFilter($query_var, $field_details['type']);
392  if (!isset($queries[$field_name][0]['from'])) {
393  $queries[$field_name] = $this->_getStoredQueryValue($field_name, $filters[$field_name]['type']);
394  }
395 
396  }//end foreach fields
397 
398  // if it seems that nothing is submitted, check if there was a previous query
399  // and use its details
400  if (empty($queries) && !empty($this->_tmp['potential_searched_fqueries'])) {
401  $queries = $this->_tmp['potential_searched_fqueries'];
402  }
403 
404  return $queries;
405 
406  }//end _getEventSearchQuery()
407 
408 
409  /*
410  * Get all the "Single" and "Recurring" events under the root node(s)
411  *
412  * @return array
413  * @access private
414  */
415  function _getEvents()
416  {
417  $root_nodes = $this->getRootNodes();
418 
419  // Get single calendar events
420  $bind_vars = Array();
421  $sql = Calendar_Common::getSingleEventQueryBase($root_nodes, 'calendar_event_single', TRUE, $bind_vars);
422  $single_result = Array();
423  try {
424  $query = MatrixDAL::preparePdoQuery($sql);
425  foreach($bind_vars as $bind_value => $bind_var) {
426  MatrixDAL::bindValueToPdo($query, $bind_var, $bind_value);
427  }
428 
429  $single_result = MatrixDAL::executePdoAll($query);
430  } catch (Exception $e) {
431  throw new Exception($e->getMessage());
432  }
433  $single_result = Calendar_Common::condenseResultTreeids($single_result);
434 
435  // Get recurring calendar events
436  $bind_vars = Array();
437  $sql = Calendar_Common::getSingleEventQueryBase($root_nodes, 'calendar_event_recurring', TRUE, $bind_vars);
438  $recurring_result = Array();
439  try {
440  $query = MatrixDAL::preparePdoQuery($sql);
441  foreach($bind_vars as $bind_value => $bind_var) {
442  MatrixDAL::bindValueToPdo($query, $bind_var, $bind_value);
443  }
444  $recurring_result = MatrixDAL::executePdoAll($query);
445  } catch (Exception $e) {
446  throw new Exception($e->getMessage());
447  }
448  $recurring_result = Calendar_Common::condenseResultTreeids($recurring_result);
449 
450  return array_merge($single_result, $recurring_result);
451 
452  }//end _getEvents()
453 
454 
465  function getGeneralReplacement($keyword)
466  {
467  if (strpos($keyword, 'event_filter_') !== FALSE) {
468  $replacement = $this->getEventFilterField(substr($keyword, strlen('event_filter_')));
469  } else {
470  $replacement = parent::getGeneralReplacement($keyword);
471  }
472 
473  return $replacement;
474 
475  }//end getGeneralReplacement()
476 
477  /*
478  * Get the value of a stored stored session variable
479  * for the given field, if any
480  *
481  * @param string $filter_name
482  * @param string $filter_type
483  *
484  * @return array
485  * @access private
486  */
487  function _getStoredQueryValue($filter_name, $filter_type)
488  {
489  $query = Array();
490 
491  // Don't touch it if there was some SESSION var already set
492  $pmap = $this->getAttribute('stored_query_session');
493  $pmap_params = $pmap->getParameters();
494 
495  if (is_array($pmap_params) && !empty($pmap_params)) {
496  // Check for current field
497  if (in_array('f:'.$filter_name, $pmap_params)) {
498  $key_field = array_search('f:'.$filter_name, $pmap_params);
499  $raw_val = $pmap->getParameterValue($pmap_params[$key_field]);
500  replace_global_keywords($raw_val);
501  // Values are expected to be in following format:
502  //
503  // Single date: [DATE]
504  // Range date: [FROM_DATE],[TO_DATE]
505  // Fuzzy dropdown: fuzzy_type
506  // Fuzzy checkbox: fuzzy_type1,fuzzy_type2,...
507  // where date are in YYYY-MM-DD format
508 
509  switch ($filter_type) {
510  case 'single_date':
511  $query[] = Array(
512  'from' => trim($raw_val),
513  'to' => trim($raw_val),
514  );
515  break;
516 
517  case 'date_range':
518  $pq_data = explode(',', $raw_val);
519  list($from, $to) = $pq_data;
520  $query[] = Array(
521  'from' => trim($from),
522  'to' => trim($to),
523  );
524  break;
525 
526  case 'fuzzy_dropdown':
527  $raw_val = trim($raw_val);
528  if (isset($this->fuzzy_date_types[$raw_val])) {
529  $query[] = $this->_processFuzzyDate($raw_val);
530  }
531  break;
532 
533  case 'fuzzy_checkboxes':
534  $fuzzy_types = explode(',', $raw_val);
535  foreach($fuzzy_types as $fuzzy_type) {
536  $fuzzy_type = trim($fuzzy_type);
537  if (isset($this->fuzzy_date_types[$fuzzy_type])) {
538  $query[] = $this->_processFuzzyDate($fuzzy_type);
539  }
540  }
541  break;
542  }
543  }
544  }
545 
546  return $query;
547 
548  }//end _getStoredQueryValue()
549 
550 
559  function getEventFilterField($filter_name)
560  {
561  $query_var = $filter_name.'_fquery';
562  $filters = $this->attr('events_filters');
563  if (!isset($filters[$filter_name]['type'])) {
564  return '';
565  }
566  $this->registerFormField('queries_'.$query_var.'%');
567  $query = Array();
568 
569  if (isset($_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id])) {
570  $query = array_get_index($_SESSION['SQ_LAST_EVENT_SEARCH'][$this->id], $filter_name, Array());
571  }
572  $read_only = FALSE;
573 
574  $current_value = $this->_processDateFilter('queries_'.$query_var, $filters[$filter_name]['type']);
575  if (!isset($current_value[0]['from'])) {
576  $current_value = $this->_getStoredQueryValue($filter_name, $filters[$filter_name]['type']);
577  }
578 
579  $fuzzy_date_options = array_get_index($filters[$filter_name], 'fuzzy_options', Array());
580  foreach($fuzzy_date_options as $key => $val) {
581  $fuzzy_date_options[$val] = str_replace('_', ' ', ucfirst($val));
582  unset($fuzzy_date_options[$key]);
583  }
584 
585  ob_start();
586 
587  switch($filters[$filter_name]['type']) {
588  case 'single_date':
589  $this->_printDateRange('queries_'.$query_var, array_get_index($current_value, 0, Array()), TRUE, $filters[$filter_name]['use_picker']);
590  break;
591 
592  case 'date_range':
593  $this->_printDateRange('queries_'.$query_var, array_get_index($current_value, 0, Array()), FALSE, $filters[$filter_name]['use_picker']);
594  break;
595 
596  case 'fuzzy_dropdown':
597  $fuzzy_date_options = array_reverse($fuzzy_date_options, TRUE);
598  $fuzzy_date_options['none'] = '';
599  $fuzzy_date_options = array_reverse($fuzzy_date_options, TRUE);
600  combo_box('queries_'.$query_var, $fuzzy_date_options, FALSE, isset($current_value[0]) ? array_get_index($current_value[0], 'fuzzy_type', '') : '');
601  break;
602 
603  case 'fuzzy_checkboxes':
604  $selected_opts = Array();
605  foreach($current_value as $selected_val) {
606  if (isset($selected_val['fuzzy_type'])) {
607  $selected_opts[] = $selected_val['fuzzy_type'];
608  }//end if
609  }//end foreach
610  foreach($fuzzy_date_options as $key => $val) {
611  echo "<br />";
612  check_box('queries_'.$query_var.'_raw[]', $key, in_array($key, $selected_opts));
613  echo "&nbsp;$val";
614  }//end foreach
615 
616  break;
617  }//end switch
618 
619  if (!$read_only) {
620  $this->registerFormField('queries_'.$query_var);
621  }
622 
623  $replacement = ob_get_contents();
624 
625  ob_end_clean();
626 
627  return $replacement;
628 
629  }//end getGeneralReplacement()
630 
631 
644  function _printDateRange($field_name, $current_value=Array(), $single_field=TRUE, $use_picker=TRUE, $read_only=FALSE)
645  {
646  if (!isset($current_value['from'])) {
647  $current_value['from'] = '---------- --:--:--';
648  }
649 
650  if (!isset($current_value['to'])) {
651  $current_value['to'] = '---------- --:--:--';
652  }
653 
654  if ($use_picker) {
655  require_once SQ_LIB_PATH.'/js_calendar/js_calendar.inc';
656 
657  if (!JS_Calendar::isInit()) {
658  ?><script src="<?php echo sq_web_path('lib'); ?>/html_form/html_form.js"
659  type="text/javascript"></script><?php
660  }
661  }
662 
663  ?>
664  <table border="0" cellspacing="0" cellpadding="0">
665  <tr>
666  <?php
667  if (!$single_field) {
668  echo '<td align="right">'.ucfirst(translate('from')).':</td>';
669  }
670  ?>
671  <td>
672  <?php
673  if ($read_only && $current_value['from'] != '---------- --:--:--') {
674  $from = iso8601_ts($current_value['from']);
675  echo date('j M Y', $from);
676  } else {
677  $field = $this->_getDateField($field_name.'_from');
678  if (!$field->processField() || $field->value == '---------- --:--:--') {
679  $field->setValue($current_value['from']);
680  } else {
681 
682  }
683  $field->printField();
684  }
685  ?>
686  </td>
687  <?php
688  if ($use_picker && (!$read_only || $current_value['from'] == '---------- --:--:--')) {
689  ?>
690  <td>
691  &nbsp;
692  <?php
693  // print the JS calendar popup date selecta
694  $calendar = new JS_Calendar();
695  $calendar->changeSetting('onDayClick', 'datetime_set_date');
696  $calendar->paint($field_name.'_from', '', TRUE);
697  ?>
698  </td>
699  <?php
700  }
701  ?>
702  </tr>
703  <?php
704  if (!$single_field) {
705  ?>
706  <tr>
707  <td align="right"><?php echo ucfirst(translate('to')) ?>:</td>
708  <td>
709  <?php
710  if ($read_only && $current_value['to'] != '---------- --:--:--') {
711  $to = iso8601_ts($current_value['to']);
712  echo date('j M Y', $to);
713  } else {
714  $field = $this->_getDateField($field_name.'_to');
715  if (!$field->processField() || $field->value == '---------- --:--:--') {
716  $field->setValue($current_value['to']);
717  }
718  $field->printField();
719  }
720  ?>
721  </td>
722  <?php
723  if ($use_picker && (!$read_only || $current_value['to'] == '---------- --:--:--')) {
724  ?>
725  <td>
726  &nbsp;
727  <?php
728  // print the JS calendar popup date selecta
729  $calendar = new JS_Calendar();
730  $calendar->changeSetting('onDayClick', 'datetime_set_date');
731  $calendar->paint($field_name.'_to', '', TRUE);
732  ?>
733  </td>
734  <?php
735  }
736  ?>
737  </tr>
738  <?php
739  }
740  ?>
741  </table>
742  <?php
743 
744  }//end _printDateRange()
745 
746 
755  function &_getDateField($field_name)
756  {
757  $parameters = Array(
758  'min' => '0000-01-01 00:00:00',
759  'max' => '9999-12-31 23:59:59',
760  'allow_circa' => '0',
761  'print_format' => '',
762  'show' => Array('y', 'm', 'd'),
763  'null' => Array('y', 'm', 'd'),
764  'style' => Array(
765  'y' => 't',
766  'm' => 's',
767  'd' => 's',
768  ),
769  );
770 
771  $value = '---------- --:--:--';
772  $field = new DateTime_Field($field_name, $value, $parameters, TRUE);
773  return $field;
774 
775  }//end _getDateField()
776 
777 
786  function _printDateRangeDescription($current_value)
787  {
788  if (!isset($current_value['from'])) {
789  $current_value['from'] = '---------- --:--:--';
790  }
791 
792  if (!isset($current_value['to'])) {
793  $current_value['to'] = '---------- --:--:--';
794  }
795 
796  $from_string = '';
797  if ($current_value['from'] != '---------- --:--:--') {
798  $from = iso8601_ts($current_value['from']);
799  $from_string = date('j M Y', $from);
800  }
801 
802  $to_string = '';
803  if ($current_value['to'] != '---------- --:--:--') {
804  $to = iso8601_ts($current_value['to']);
805  $to_string = date('j M Y', $to);
806  }
807 
808  if (empty($from_string) && empty($to_string)) {
809  return;
810  } else if (empty($from_string)) {
811  echo translate('sch_page_date_range_prior_to', $to_string);
812  } else if (empty($to_string)) {
813  echo translate('sch_page_date_range_onwards', $from_string);
814  } else if ($from_string == $to_string) {
815  echo $from_string;
816  } else {
817  echo $from_string.' - '.$to_string;
818  }
819 
820  }//end _printDateRangeDescription()
821 
822 
832  function _processDateFilter($field_name, $type)
833  {
834  $result = Array();
835 
836  switch ($type) {
837  case 'single_date':
838  case 'date_range':
839  $field = $this->_getDateField($field_name.'_from');
840  if ($field->processField()) {
841  $result[0]['from'] = rtrim($field->value, "-: ");
842  }
843 
844  $field = $this->_getDateField($field_name.'_to');
845  if ($field->processField()) {
846  $result[0]['to'] = rtrim($field->value, "-: ");
847  }
848 
849  if (isset($result[0]['from']) && !isset($result[0]['to'])) {
850  $result[0]['to'] = $result[0]['from'];
851  }
852  break;
853 
854  case 'fuzzy_dropdown':
855  if (isset($_REQUEST[$field_name])) {
856  $result[0] = $this->_processFuzzyDate($_REQUEST[$field_name]);
857  }
858  break;
859 
860  case 'fuzzy_checkboxes':
861  $fuzzy_types = Array();
862  if (isset($_REQUEST[$field_name.'_raw'])) {
863  // submitted via form
864  $fuzzy_types = $_REQUEST[$field_name.'_raw'];
865  } else if (isset($_REQUEST[$field_name])) {
866  // submitted via stored search
867  $fuzzy_types = explode(',', $_REQUEST[$field_name]);
868  }
869 
870  if (!empty($fuzzy_types)) {
871  foreach($fuzzy_types as $index => $selected_date_type) {
872  $result[$index] = $this->_processFuzzyDate(trim($selected_date_type));
873  }//end foreach
874  }
875  break;
876 
877  }//end switch
878 
879  return $result;
880 
881  }//end _processDateFilter()
882 
883 
892  function _processFuzzyDate($type)
893  {
894  // Current date
895  $today = date("Y-m-d");
896 
897  switch ($type) {
898  case 'today':
899  $from = $today;
900  $to = $today;
901  break;
902 
903  case 'tomorrow':
904  $from = date("Y-m-d", strtotime($today. " +1 day"));
905  $to = date("Y-m-d", strtotime($today. " +1 day"));
906  break;
907 
908  case 'yesterday':
909  $from = date("Y-m-d", strtotime($today. " -1 day"));
910  $to = date("Y-m-d", strtotime($today. " -1 day"));
911  break;
912 
913  case 'this_weekend':
914  $from = date("N") == 7 ? $today : date("Y-m-d", strtotime('next Saturday'));
915  $to = date("N") == 7 ? $today : date("Y-m-d", strtotime('next Sunday'));
916  break;
917 
918  case 'next_weekend':
919  $from = date("N") == 7 ? date("Y-m-d", strtotime('next Saturday')) : date("Y-m-d", strtotime('next Saturday +1 week'));
920  $to = date("Y-m-d", strtotime('this Sunday +1 week'));
921  break;
922 
923  case 'previous_weekend':
924  $from = date("N") == 7 ? date("Y-m-d", strtotime('last Saturday -1 week')) : date("Y-m-d", strtotime('last Saturday'));
925  $to = date("Y-m-d", strtotime('last Sunday -1 week'));
926  break;
927 
928  case 'this_week':
929  // "2" for Day week means its first day of the week i.e. Monday
930  $from = date("N") == 2 ? $today : date("Y-m-d", strtotime('last Monday'));
931  $to = date("Y-m-d", strtotime($from. " +1 week"));
932  break;
933 
934  case 'next_week':
935  $from = date("Y-m-d", strtotime('next Monday'));
936  $to = date("Y-m-d", strtotime($from. " +1 week"));
937  break;
938 
939  case 'previous_week':
940  $from = date("N") == 2 ? date("Y-m-d", strtotime('last Monday')) : date("Y-m-d", strtotime('last Monday -1 week'));
941  $to = date("Y-m-d", strtotime($from. " +1 week"));
942  break;
943 
944  case 'this_fortnight':
945  $from = date("N") == 2 ? $today : date("Y-m-d", strtotime('last Monday'));
946  $to = date("Y-m-d", strtotime($from. " +2 weeks"));
947  break;
948 
949  case 'next_fortnight':
950  $from = date("Y-m-d", strtotime('next Monday +1 week'));
951  $to = date("Y-m-d", strtotime($from. " +2 weeks"));
952  break;
953 
954  case 'previous_fortnight':
955  $from = date("N") == 2 ? date("Y-m-d", strtotime('last Monday -1 week')) : date("Y-m-d", strtotime('last Monday -2 weeks'));
956  $to = date("Y-m-d", strtotime($from. " +2 weeks"));
957  break;
958 
959  case 'this_month':
960  $from = date("Y-m-d", strtotime(date('m').'/01/'.date('Y')));
961  $to = date("Y-m-d", strtotime((date('m')+1).'/01/'.date('Y'))-86400); // 86400 = 24*60*60
962  break;
963 
964  case 'next_month':
965  if (date('m') == 12) {
966  $month = 1;
967  $year = date('Y')+1;
968  } else {
969  $month = date('m')+1;
970  $year = date('Y');
971  }
972  $from = date("Y-m-d", strtotime($month.'/01/'.$year));
973  $to = date("Y-m-d", strtotime(($month+1).'/01/'.$year)-86400);
974  break;
975 
976  case 'previous_month':
977  if (date('m') == 1) {
978  $month = 12;
979  $year = date('Y')-1;
980  } else {
981  $month = date('m');
982  $year = date('Y');
983  }
984  $from = date("Y-m-d", strtotime($month.'/01/'.$year));
985  $to = date("Y-m-d", strtotime(($month == 12 ? 1 : $month+1).'/01/'.$year)-86400);
986  break;
987 
988  case 'this_year':
989  $year = date('Y');
990  $from = date("Y-m-d", strtotime('01/01/'.$year));
991  $to = date("Y-m-d", strtotime('12/31/'.$year));
992  break;
993 
994  case 'next_year':
995  $year = date('Y')+1;
996  $from = date("Y-m-d", strtotime('01/01/'.$year));
997  $to = date("Y-m-d", strtotime('12/31/'.$year));
998  break;
999 
1000  case 'previous_year':
1001  $year = date('Y')-1;
1002  $from = date("Y-m-d", strtotime('01/01/'.$year));
1003  $to = date("Y-m-d", strtotime('12/31/'.$year));
1004  break;
1005 
1006  case 'anytime':
1007  $from = '1970-01-01';
1008  $to = '2030-12-31';
1009  break;
1010 
1011  case 'none':
1012  $from = '';
1013  $to = '';
1014  break;
1015 
1016  }//end switch
1017 
1018  return Array (
1019  "from" => $from,
1020  "to" => $to,
1021  "fuzzy_type" => $type,
1022  ) ;
1023 
1024  }//end _processFuzzyDate()
1025 
1026 
1027 
1028  //-- KEYWORD DESCRIPTION --//
1029 
1030 
1041  function onRequestKeywords(&$broadcaster, $vars=Array())
1042  {
1043  $vars['keywords'] = isset($vars['keywords']) ? $vars['keywords'] : Array();
1044 
1045  $parents = $GLOBALS['SQ_SYSTEM']->am->getParents($broadcaster->id, 'bodycopy', TRUE);
1046  $bodycopy_links = $GLOBALS['SQ_SYSTEM']->am->getLinks($this->id, SQ_LINK_TYPE_2, 'bodycopy');
1047 
1048  // if there is a search in search bodycopy add it to the bodycopy list
1049  // it will need some of the initial page keywords
1050  $sis_bodycopy_link = $this->getFormatBodycopyLink('sis_form');
1051  if (!empty($sis_bodycopy_link)) {
1052  $bodycopy_links[] = $sis_bodycopy_link;
1053  }
1054 
1055  // if there is a search in search bodycopy add it to the bodycopy list
1056  // it will need some of the initial page keywords
1057  $search_bodycopy_link = $this->getFormatBodycopyLink('search_form');
1058  if (!empty($search_bodycopy_link)) {
1059  $bodycopy_links[] = $search_bodycopy_link;
1060  }
1061 
1062  $bodycopies = Array();
1063  $type_formats = Array();
1064  $keywords = Array();
1065 
1066  foreach ($bodycopy_links as $link_info) {
1067  if (isset($parents[$link_info['minorid']])) {
1068  $bodycopies[] = $link_info['value'];
1069  }
1070  }
1071 
1072  // ATTENTION!
1073  // this check relies on the fact that ALL single asset formats like type, default or position
1074  // are located in subfolders of this asset, and only its context bodycopies are its direct children
1075  if (empty($bodycopies)) {
1076  parent::onRequestKeywords($broadcaster, $vars);
1077  return;
1078  }
1079 
1080  // work out if forms are customised
1081  $search_bodycopy_link = $this->getFormatBodycopyLink('search_form');
1082  $search_customised = !empty($search_bodycopy_link) && $search_bodycopy_link['link_type'] != SQ_LINK_TYPE_3;
1083  $sis_customised = !empty($sis_bodycopy_link) && $sis_bodycopy_link['link_type'] != SQ_LINK_TYPE_3;
1084 
1085  foreach ($bodycopies as $bodycopy) {
1086  if ($bodycopy == 'initial' || $bodycopy == 'sis_form' || $bodycopy == 'search_form') {
1087  // work out the query field keywords
1088  $fields = $this->attr('fields');
1089  foreach ($fields as $field => $field_data) {
1090  $keywords[$field.'_query'] = translate('sch_page_keyword_search_field', $field);
1091  if ($bodycopy == 'initial') {
1092  $keywords[$field.'_query_logic'] = translate('sch_page_keyword_search_field_logic', $field);
1093  }
1094  }
1095  // work out the calendar events filter keywords
1096  $filters = $this->attr('events_filters');
1097  foreach ($filters as $filter => $filter_data) {
1098  if (isset($filter_data['type'])) {
1099  $keywords['event_filter_'.$filter] = translate('page_events_search_filter_field', $filter);
1100  }
1101  }
1102  // work out search category keywords
1103  foreach ($this->attr('categories') as $cat_name => $cat_details) {
1104  $keywords[$cat_name.'_category_chooser'] = 'Dropdown box for category set '.$cat_name;
1105  }
1106  }
1107 
1108  // add in the buttons for the customisation bodycopies
1109  if ($bodycopy == 'search_form') {
1110  $keywords['submit_button'] = translate('cms_listing_keyword_submit_button');
1111  }
1112  if ($bodycopy == 'sis_form') {
1113  $keywords['search_in_search_button'] = translate('sch_page_keyword_sis_button');
1114  }
1115 
1116  if ($bodycopy != 'sis_form' && $bodycopy != 'search_form') {
1117  foreach ($this->keywords[$bodycopy] as $keyword) {
1118  $keywords[$keyword] = ucwords(str_replace('_', ' ', $keyword));
1119  }
1120 
1121  // customised forms
1122  if ($search_customised) {
1123  $keywords += $this->_getCustomisedFormKeywords();
1124  }
1125 
1126  // search in search
1127  if ($sis_customised && $bodycopy == 'results') {
1128  $keywords += $this->_getSearchInSearchKeywords();
1129  }
1130  }
1131  }//end foreach
1132 
1133  $vars['keywords'] = array_merge($vars['keywords'], $keywords);
1134 
1135  }//end onRequestKeywords()
1136 
1137 }//end class
1138 ?>