ILIAS  Release_4_0_x_branch Revision 61816
 All Data Structures Namespaces Files Functions Variables Groups Pages
class.ilDateTime.php
Go to the documentation of this file.
1 <?php
2 /*
3  +-----------------------------------------------------------------------------+
4  | ILIAS open source |
5  +-----------------------------------------------------------------------------+
6  | Copyright (c) 1998-2006 ILIAS open source, University of Cologne |
7  | |
8  | This program is free software; you can redistribute it and/or |
9  | modify it under the terms of the GNU General Public License |
10  | as published by the Free Software Foundation; either version 2 |
11  | of the License, or (at your option) any later version. |
12  | |
13  | This program is distributed in the hope that it will be useful, |
14  | but WITHOUT ANY WARRANTY; without even the implied warranty of |
15  | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
16  | GNU General Public License for more details. |
17  | |
18  | You should have received a copy of the GNU General Public License |
19  | along with this program; if not, write to the Free Software |
20  | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. |
21  +-----------------------------------------------------------------------------+
22 */
23 
24 include_once('Services/Calendar/classes/class.ilDateTimeException.php');
25 include_once('Services/Calendar/classes/class.ilTimeZone.php');
26 
27 
28 define('IL_CAL_DATETIME',1);
29 define('IL_CAL_DATE',2);
30 define('IL_CAL_UNIX',3);
31 define('IL_CAL_FKT_DATE',4);
32 define('IL_CAL_FKT_GETDATE',5);
33 define('IL_CAL_TIMESTAMP',6);
34 
35 define('IL_CAL_YEAR','year');
36 define('IL_CAL_MONTH','month');
37 define('IL_CAL_WEEK','week');
38 define('IL_CAL_DAY','day');
39 define('IL_CAL_HOUR','hour');
40 
41 
51 {
52  const YEAR = 'year';
53  const MONTH = 'month';
54  const WEEK = 'week';
55  const DAY = 'day';
56  const HOUR = 'hour';
57 
58  protected $log;
59 
60  protected $timezone = null;
61  protected $default_timezone = null;
62 
63  protected $unix = 0;
64 
65 
66 
77  public function __construct($a_date = null,$a_format = 0,$a_tz = '')
78  {
79  global $ilLog;
80 
81  $this->log = $ilLog;
82 
83  try
84  {
85  $this->timezone = ilTimeZone::_getInstance($a_tz);
86  $this->default_timezone = ilTimeZone::_getInstance('');
87 
88  if(!$a_date)
89  {
90  $this->setDate(0,IL_CAL_UNIX);
91  }
92  else
93  {
94  $this->setDate($a_date,$a_format);
95  }
96  }
97  catch(ilTimeZoneException $exc)
98  {
99  $this->log->write(__METHOD__.': '.$exc->getMessage());
100  throw new ilDateTimeException('Unsupported timezone given. Timezone: '.$a_tz);
101  }
102  }
103 
109  public function isNull()
110  {
111  return $this->unix ? false : true;
112  }
113 
121  public function switchTimeZone($a_timezone_identifier = '')
122  {
123  try
124  {
125  $this->timezone = ilTimeZone::_getInstance($a_timezone_identifier);
126  return true;
127  }
128  catch(ilTimeZoneException $e)
129  {
130  $this->log->write('Unsupported timezone given: '.$a_timezone_identifier);
131  throw new ilDateTimeException('Unsupported timezone given. Timezone: '.$a_timezone_identifier);
132  }
133  }
134 
141  public function getTimeZoneIdentifier()
142  {
143  return $this->timezone->getIdentifier();
144  }
145 
160  public static function _before(ilDateTime $start,ilDateTime $end,$a_compare_field = '',$a_tz = '')
161  {
162  switch($a_compare_field)
163  {
164  case IL_CAL_YEAR:
165  return $start->get(IL_CAL_FKT_DATE,'Y',$a_tz) < $end->get(IL_CAL_FKT_DATE,'Y',$a_tz);
166 
167  case IL_CAL_MONTH:
168  return (int) $start->get(IL_CAL_FKT_DATE,'Ym',$a_tz) < $end->get(IL_CAL_FKT_DATE,'Ym',$a_tz);
169 
170  case IL_CAL_DAY:
171  return (int) $start->get(IL_CAL_FKT_DATE,'Ymd',$a_tz) < $end->get(IL_CAL_FKT_DATE,'Ymd',$a_tz);
172 
173  case '':
174  default:
175  return $start->get(IL_CAL_UNIX) < $end->get(IL_CAL_UNIX);
176 
177  }
178  }
179 
191  public static function _equals(ilDateTime $start,ilDateTime $end,$a_compare_field = '',$a_tz = '')
192  {
193  switch($a_compare_field)
194  {
195  case IL_CAL_YEAR:
196  return $start->get(IL_CAL_FKT_DATE,'Y',$a_tz) == $end->get(IL_CAL_FKT_DATE,'Y',$a_tz);
197 
198  case IL_CAL_MONTH:
199  return (int) $start->get(IL_CAL_FKT_DATE,'Ym',$a_tz) == $end->get(IL_CAL_FKT_DATE,'Ym',$a_tz);
200 
201  case IL_CAL_DAY:
202  return (int) $start->get(IL_CAL_FKT_DATE,'Ymd',$a_tz) == $end->get(IL_CAL_FKT_DATE,'Ymd',$a_tz);
203 
204  case '':
205  default:
206  return $start->get(IL_CAL_UNIX) == $end->get(IL_CAL_UNIX);
207 
208  }
209  }
210 
223  public static function _after(ilDateTime $start,ilDateTime $end,$a_compare_field = '',$a_tz = '')
224  {
225  switch($a_compare_field)
226  {
227  case IL_CAL_YEAR:
228  return $start->get(IL_CAL_FKT_DATE,'Y',$a_tz) > $end->get(IL_CAL_FKT_DATE,'Y',$a_tz);
229 
230  case IL_CAL_MONTH:
231  return (int) $start->get(IL_CAL_FKT_DATE,'Ym',$a_tz) > $end->get(IL_CAL_FKT_DATE,'Ym',$a_tz);
232 
233  case IL_CAL_DAY:
234  return (int) $start->get(IL_CAL_FKT_DATE,'Ymd',$a_tz) > $end->get(IL_CAL_FKT_DATE,'Ymd',$a_tz);
235 
236  case '':
237  default:
238  return $start->get(IL_CAL_UNIX) > $end->get(IL_CAL_UNIX);
239 
240  }
241  }
242 
251  public function increment($a_type,$a_count = 1)
252  {
253  $count_str = $a_count > 0 ? ('+'.$a_count.' ') : ($a_count.' ');
254 
255  $this->timezone->switchTZ();
256  switch($a_type)
257  {
258  case self::YEAR:
259  $this->unix = strtotime($count_str.'year',$this->unix);
260  break;
261 
262  case self::MONTH:
263  // strtotime fails in the following case:
264  // 2008-03-31 (+1 month) => 2008-05-01
265  // In that case, we substract the new month day
266 
267  $old_day_of_month = $this->get(IL_CAL_FKT_DATE,'j');
268  $this->unix = strtotime($count_str.'month',$this->unix);
269 
270  // TODO: Fix monthly calculations.
271 
272  /*
273  $new_day_of_month = $this->get(IL_CAL_FKT_DATE,'j');
274  if($new_day_of_month != $old_day_of_month)
275  {
276  $this->unix = $this->increment(IL_CAL_DAY,$new_day_of_month * -1);
277  }
278  */
279  break;
280 
281  case self::WEEK:
282  $this->unix = strtotime($count_str.'week',$this->unix);
283  break;
284 
285  case self::DAY:
286  $this->unix = strtotime($count_str.'day',$this->unix);
287  break;
288 
289  case self::HOUR:
290  $this->unix = strtotime($count_str.'hour',$this->unix);
291  break;
292 
293  }
294  $this->timezone->restoreTZ();
295  return $this->unix;
296  }
297 
304  public function getUnixTime()
305  {
306  return $this->unix;
307  }
308 
309 
316  public function getUTCOffset()
317  {
318  $this->timezone->switchTZ();
319  // TODO: This is wrong: calculate UTC offset of given date
320  $offset = mktime(0,0,0,2,1,1970) - gmmktime(0,0,0,2,1,1970);
321  $this->timezone->restoreTZ();
322  return $offset;
323  }
324 
333  public function setDate($a_date,$a_format)
334  {
335  switch($a_format)
336  {
337  case IL_CAL_UNIX:
338  $this->unix = $a_date;
339  break;
340 
341  case IL_CAL_DATETIME:
342 
343  if(preg_match('/^(\d{4})-?(\d{2})-?(\d{2})([T\s]?(\d{2}):?(\d{2}):?(\d{2})(\.\d+)?(Z|[\+\-]\d{2}:?\d{2})?)$/i',$a_date,$d_parts) === false)
344  {
345  $this->log->write(__METHOD__.': Cannot parse date: '.$a_date);
346  throw new ilDateTimeException('Cannot parse date.');
347  }
348 
349  $this->timezone->switchTZ();
350  $this->unix = mktime(
351  isset($d_parts[5]) ? $d_parts[5] : 0,
352  isset($d_parts[6]) ? $d_parts[6] : 0,
353  isset($d_parts[7]) ? $d_parts[7] : 0,
354  $d_parts[2],
355  $d_parts[3],
356  $d_parts[1]);
357 
358  if($d_parts[0] == '0000-00-00 00:00:00')
359  {
360  $this->unix = 0;
361  }
362 
363  $this->timezone->restoreTZ();
364  break;
365 
366  case IL_CAL_DATE:
367  // Pure dates are not timezone sensible.
369  $timezone->switchTZ();
370  $unix = strtotime($a_date);
371  $timezone->restoreTZ();
372  if(!$unix or $unix == false)
373  {
374  $this->log->write(__METHOD__.': Cannot parse date: '.$a_date);
375  $this->unix = 0;
376  return false;
377  }
378  $this->unix = $unix;
379  break;
380 
381  case IL_CAL_FKT_GETDATE:
382  // Format like getdate parameters
383  $this->timezone->switchTZ();
384  $this->unix = mktime(
385  $a_date['hours'],
386  $a_date['minutes'],
387  $a_date['seconds'],
388  $a_date['mon'],
389  $a_date['mday'],
390  $a_date['year']);
391  $this->timezone->restoreTZ();
392 
393  // TODO: choose better error handling
394  if(!$a_date['year'])
395  {
396  $this->unix = 0;
397  }
398  break;
399 
400  case IL_CAL_TIMESTAMP:
401  if(preg_match("/(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})/", $a_date,$d_parts) == false)
402  {
403  $this->log->write(__METHOD__.': Cannot parse date: '.$a_date);
404  throw new ilDateTimeException('Cannot parse date.');
405  }
406  $this->timezone->switchTZ();
407  $this->unix = mktime(
408  isset($d_parts[4]) ? $d_parts[4] : 0,
409  isset($d_parts[5]) ? $d_parts[5] : 0,
410  isset($d_parts[6]) ? $d_parts[6] : 0,
411  $d_parts[2],
412  $d_parts[3],
413  $d_parts[1]);
414 
415  if($d_parts[0] == '00000000000000' or
416  $d_parts[0] == '00000000')
417  {
418  $this->unix = 0;
419  }
420  $this->timezone->restoreTZ();
421  break;
422  }
423  return true;
424  }
425 
434  public function get($a_format,$a_format_str = '',$a_tz = '')
435  {
436  if($a_tz)
437  {
438  try
439  {
441  }
442  catch(ilTimeZoneException $exc)
443  {
444  $this->log->write(__METHOD__.': Invalid timezone given. Timezone: '.$a_tz);
445  }
446  }
447  else
448  {
449  #$timezone = $this->timezone;
451  }
452 
453  switch($a_format)
454  {
455  case IL_CAL_UNIX:
456  $date = $this->getUnixTime();
457  break;
458 
459  case IL_CAL_DATE:
460  $timezone->switchTZ();
461  $date = date('Y-m-d',$this->getUnixTime());
462  $timezone->restoreTZ();
463  break;
464 
465  case IL_CAL_DATETIME:
466  $timezone->switchTZ();
467  $date = date('Y-m-d H:i:s',$this->getUnixTime());
468  $timezone->restoreTZ();
469  break;
470 
471  case IL_CAL_FKT_DATE:
472  $timezone->switchTZ();
473  $date = date($a_format_str,$this->getUnixTime());
474  $timezone->restoreTZ();
475  break;
476 
477  case IL_CAL_FKT_GETDATE:
478  $timezone->switchTZ();
479  $date = getdate($this->getUnixTime());
480  $timezone->restoreTZ();
481 
482  // add iso 8601 week day number (Sunday = 7)
483  $date['isoday'] = $date['wday'] == 0 ? 7 : $date['wday'];
484  break;
485 
486  case IL_CAL_TIMESTAMP:
487  $timezone->switchTZ();
488  $date = date('YmdHis',$this->getUnixTime());
489  $timezone->restoreTZ();
490  break;
491  }
492  return $date;
493  }
494 
502  public function __toString()
503  {
504  return $this->get(IL_CAL_DATETIME,'','UTC').'<br>';
505  }
506 }
507 ?>