source: branches/version-2_5-dev/data/module/Calendar/Calendar.php @ 20119

Revision 20119, 20.6 KB checked in by nanasess, 13 years ago (diff)

module 以下は svn:keywords を除外

  • Property svn:eol-style set to LF
  • Property svn:mime-type set to text/x-httpd-php; charset=UTF-8
Line 
1<?php
2/* vim: set expandtab tabstop=4 shiftwidth=4: */
3//
4// +----------------------------------------------------------------------+
5// | PHP Version 4                                                        |
6// +----------------------------------------------------------------------+
7// | Copyright (c) 1997-2002 The PHP Group                                |
8// +----------------------------------------------------------------------+
9// | This source file is subject to version 2.02 of the PHP license,      |
10// | that is bundled with this package in the file LICENSE, and is        |
11// | available at through the world-wide-web at                           |
12// | http://www.php.net/license/3_0.txt.                                  |
13// | If you did not receive a copy of the PHP license and are unable to   |
14// | obtain it through the world-wide-web, please send a note to          |
15// | license@php.net so we can mail you a copy immediately.               |
16// +----------------------------------------------------------------------+
17// | Authors: Harry Fuecks <hfuecks@phppatterns.com>                      |
18// |          Lorenzo Alberton <l dot alberton at quipo dot it>           |
19// +----------------------------------------------------------------------+
20//
21// $Id: Calendar.php,v 1.3 2005/10/22 10:07:11 quipo Exp $
22//
23/**
24 * @package Calendar
25 * @version $Id: Calendar.php,v 1.3 2005/10/22 10:07:11 quipo Exp $
26 */
27
28/**
29 * Allows Calendar include path to be redefined
30 */
31if (!defined('CALENDAR_ROOT')) {
32    define('CALENDAR_ROOT', 'Calendar'.DIRECTORY_SEPARATOR);
33}
34
35/**
36 * Constant which defines the calculation engine to use
37 */
38if (!defined('CALENDAR_ENGINE')) {
39    define('CALENDAR_ENGINE', 'UnixTS');
40}
41
42/**
43 * Define Calendar Month states
44 */
45define('CALENDAR_USE_MONTH',          1);
46define('CALENDAR_USE_MONTH_WEEKDAYS', 2);
47define('CALENDAR_USE_MONTH_WEEKS',    3);
48
49/**
50 * Contains a factory method to return a Singleton instance of a class
51 * implementing the Calendar_Engine_Interface.<br>
52 * <b>Note:</b> this class must be modified to "register" alternative
53 * Calendar_Engines. The engine used can be controlled with the constant
54 * CALENDAR_ENGINE
55 * @see Calendar_Engine_Interface
56 * @package Calendar
57 * @access protected
58 */
59class Calendar_Engine_Factory
60{
61    /**
62     * Returns an instance of the engine
63     * @return object instance of a calendar calculation engine
64     * @access protected
65     */
66    function & getEngine()
67    {
68        static $engine = false;
69        switch (CALENDAR_ENGINE) {
70            case 'PearDate':
71                $class = 'Calendar_Engine_PearDate';
72                break;
73            case 'UnixTS':
74            default:
75                $class = 'Calendar_Engine_UnixTS';
76            break;
77        }
78        if (!$engine) {
79            if (!class_exists($class)) {
80                require_once CALENDAR_ROOT.'Engine'.DIRECTORY_SEPARATOR.CALENDAR_ENGINE.'.php';
81            }
82            $engine = new $class;
83        }
84        return $engine;
85    }
86}
87
88/**
89 * Base class for Calendar API. This class should not be instantiated
90 * directly.
91 * @abstract
92 * @package Calendar
93 */
94class Calendar
95{
96    /**
97     * Instance of class implementing calendar engine interface
98     * @var object
99     * @access private
100     */
101    var $cE;
102
103    /**
104     * Instance of Calendar_Validator (lazy initialized when isValid() or
105     * getValidor() is called
106     * @var Calendar_Validator
107     * @access private
108     */
109    var $validator;
110
111    /**
112     * Year for this calendar object e.g. 2003
113     * @access private
114     * @var int
115     */
116   var $year;
117
118    /**
119     * Month for this calendar object e.g. 9
120     * @access private
121     * @var int
122     */
123    var $month;
124
125    /**
126     * Day of month for this calendar object e.g. 23
127     * @access private
128     * @var int
129     */
130    var $day;
131
132    /**
133     * Hour of day for this calendar object e.g. 13
134     * @access private
135     * @var int
136     */
137    var $hour;
138
139    /**
140     * Minute of hour this calendar object e.g. 46
141     * @access private
142     * @var int
143     */
144    var $minute;
145
146    /**
147     * Second of minute this calendar object e.g. 34
148     * @access private
149     * @var int
150     */
151    var $second;
152
153    /**
154     * Marks this calendar object as selected (e.g. 'today')
155     * @access private
156     * @var boolean
157     */
158    var $selected = false;
159
160    /**
161     * Collection of child calendar objects created from subclasses
162     * of Calendar. Type depends on the object which created them.
163     * @access private
164     * @var array
165     */
166    var $children = array();
167
168    /**
169     * Constructs the Calendar
170     * @param int year
171     * @param int month
172     * @param int day
173     * @param int hour
174     * @param int minute
175     * @param int second
176     * @access protected
177     */
178    function Calendar($y = 2000, $m = 1, $d = 1, $h = 0, $i = 0, $s = 0)
179    {
180        static $cE = null;
181        if (!isset($cE)) {
182            $cE = & Calendar_Engine_Factory::getEngine();
183        }
184        $this->cE = & $cE;
185        $this->year   = (int)$y;
186        $this->month  = (int)$m;
187        $this->day    = (int)$d;
188        $this->hour   = (int)$h;
189        $this->minute = (int)$i;
190        $this->second = (int)$s;
191    }
192
193    /**
194     * Defines the calendar by a timestamp (Unix or ISO-8601), replacing values
195     * passed to the constructor
196     * @param int|string Unix or ISO-8601 timestamp
197     * @return void
198     * @access public
199     */
200    function setTimestamp($ts)
201    {
202        $this->year   = $this->cE->stampToYear($ts);
203        $this->month  = $this->cE->stampToMonth($ts);
204        $this->day    = $this->cE->stampToDay($ts);
205        $this->hour   = $this->cE->stampToHour($ts);
206        $this->minute = $this->cE->stampToMinute($ts);
207        $this->second = $this->cE->stampToSecond($ts);
208    }
209
210    /**
211     * Returns a timestamp from the current date / time values. Format of
212     * timestamp depends on Calendar_Engine implementation being used
213     * @return int|string timestamp
214     * @access public
215     */
216    function getTimestamp()
217    {
218        return $this->cE->dateToStamp(
219            $this->year, $this->month, $this->day,
220            $this->hour, $this->minute, $this->second);
221    }
222
223    /**
224     * Defines calendar object as selected (e.g. for today)
225     * @param boolean state whether Calendar subclass
226     * @return void
227     * @access public
228     */
229    function setSelected($state = true)
230    {
231        $this->selected = $state;
232    }
233
234    /**
235     * True if the calendar subclass object is selected (e.g. today)
236     * @return boolean
237     * @access public
238     */
239    function isSelected()
240    {
241        return $this->selected;
242    }
243
244    /**
245     * Adjusts the date (helper method)
246     * @return void
247     * @access public
248     */
249    function adjust()
250    {
251        $stamp = $this->getTimeStamp();
252        $this->year   = $this->cE->stampToYear($stamp);
253        $this->month  = $this->cE->stampToMonth($stamp);
254        $this->day    = $this->cE->stampToDay($stamp);
255        $this->hour   = $this->cE->stampToHour($stamp);
256        $this->minute = $this->cE->stampToMinute($stamp);
257        $this->second = $this->cE->stampToSecond($stamp);
258    }
259
260    /**
261     * Returns the date as an associative array (helper method)
262     * @param mixed timestamp (leave empty for current timestamp)
263     * @return array
264     * @access public
265     */
266    function toArray($stamp=null)
267    {
268        if (is_null($stamp)) {
269            $stamp = $this->getTimeStamp();
270        }
271        return array(
272            'year'   => $this->cE->stampToYear($stamp),
273            'month'  => $this->cE->stampToMonth($stamp),
274            'day'    => $this->cE->stampToDay($stamp),
275            'hour'   => $this->cE->stampToHour($stamp),
276            'minute' => $this->cE->stampToMinute($stamp),
277            'second' => $this->cE->stampToSecond($stamp)
278        );
279    }
280
281    /**
282     * Returns the value as an associative array (helper method)
283     * @param string type of date object that return value represents
284     * @param string $format ['int' | 'array' | 'timestamp' | 'object']
285     * @param mixed timestamp (depending on Calendar engine being used)
286     * @param int integer default value (i.e. give me the answer quick)
287     * @return mixed
288     * @access private
289     */
290    function returnValue($returnType, $format, $stamp, $default)
291    {
292        switch (strtolower($format)) {
293            case 'int':
294                return $default;
295            case 'array':
296                return $this->toArray($stamp);
297                break;
298            case 'object':
299                require_once CALENDAR_ROOT.'Factory.php';
300                return Calendar_Factory::createByTimestamp($returnType,$stamp);
301                break;
302            case 'timestamp':
303            default:
304                return $stamp;
305                break;
306        }
307    }
308
309    /**
310     * Abstract method for building the children of a calendar object.
311     * Implemented by Calendar subclasses
312     * @param array containing Calendar objects to select (optional)
313     * @return boolean
314     * @access public
315     * @abstract
316     */
317    function build($sDates = array())
318    {
319        require_once 'PEAR.php';
320        PEAR::raiseError(
321            'Calendar::build is abstract', null, PEAR_ERROR_TRIGGER,
322            E_USER_NOTICE, 'Calendar::build()');
323        return false;
324    }
325
326    /**
327     * Abstract method for selected data objects called from build
328     * @param array
329     * @return boolean
330     * @access public
331     * @abstract
332     */
333    function setSelection($sDates)
334    {
335        require_once 'PEAR.php';
336        PEAR::raiseError(
337            'Calendar::setSelection is abstract', null, PEAR_ERROR_TRIGGER,
338            E_USER_NOTICE, 'Calendar::setSelection()');
339        return false;
340    }
341
342    /**
343     * Iterator method for fetching child Calendar subclass objects
344     * (e.g. a minute from an hour object). On reaching the end of
345     * the collection, returns false and resets the collection for
346     * further iteratations.
347     * @return mixed either an object subclass of Calendar or false
348     * @access public
349     */
350    function fetch()
351    {
352        $child = each($this->children);
353        if ($child) {
354            return $child['value'];
355        } else {
356            reset($this->children);
357            return false;
358        }
359    }
360
361    /**
362     * Fetches all child from the current collection of children
363     * @return array
364     * @access public
365     */
366    function fetchAll()
367    {
368        return $this->children;
369    }
370
371    /**
372     * Get the number Calendar subclass objects stored in the internal
373     * collection.
374     * @return int
375     * @access public
376     */
377    function size()
378    {
379        return count($this->children);
380    }
381
382    /**
383     * Determine whether this date is valid, with the bounds determined by
384     * the Calendar_Engine. The call is passed on to
385     * Calendar_Validator::isValid
386     * @return boolean
387     * @access public
388     */
389    function isValid()
390    {
391        $validator = & $this->getValidator();
392        return $validator->isValid();
393    }
394
395    /**
396     * Returns an instance of Calendar_Validator
397     * @return Calendar_Validator
398     * @access public
399     */
400    function & getValidator()
401    {
402        if (!isset($this->validator)) {
403            require_once CALENDAR_ROOT.'Validator.php';
404            $this->validator = & new Calendar_Validator($this);
405        }
406        return $this->validator;
407    }
408
409    /**
410     * Returns a reference to the current Calendar_Engine being used. Useful
411     * for Calendar_Table_Helper and Calendar_Validator
412     * @return object implementing Calendar_Engine_Inteface
413     * @access protected
414     */
415    function & getEngine()
416    {
417        return $this->cE;
418    }
419
420    /**
421     * Set the CALENDAR_FIRST_DAY_OF_WEEK constant to the $firstDay value
422     * if the constant is not set yet.
423     * @throws E_USER_WARNING this method throws a WARNING if the
424     *    CALENDAR_FIRST_DAY_OF_WEEK constant is already defined and
425     *    the $firstDay parameter is set to a different value
426     * @param integer $firstDay first day of the week (0=sunday, 1=monday, ...)
427     * @return integer
428     * @access protected
429     */
430    function defineFirstDayOfWeek($firstDay = null)
431    {
432        if (defined('CALENDAR_FIRST_DAY_OF_WEEK')) {
433            if (!is_null($firstDay) && ($firstDay != CALENDAR_FIRST_DAY_OF_WEEK)) {
434                $msg = 'CALENDAR_FIRST_DAY_OF_WEEK constant already defined.'
435                  .' The $firstDay parameter will be ignored.';
436                trigger_error($msg, E_USER_WARNING);
437            }
438            return CALENDAR_FIRST_DAY_OF_WEEK;
439        }
440        if (is_null($firstDay)) {
441            $firstDay = $this->cE->getFirstDayOfWeek(
442                $this->thisYear(),
443                $this->thisMonth(),
444                $this->thisDay()
445            );
446        }
447        define ('CALENDAR_FIRST_DAY_OF_WEEK', $firstDay);
448        return CALENDAR_FIRST_DAY_OF_WEEK;
449    }
450
451    /**
452     * Returns the value for the previous year
453     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
454     * @return int e.g. 2002 or timestamp
455     * @access public
456     */
457    function prevYear($format = 'int')
458    {
459        $ts = $this->cE->dateToStamp($this->year-1, 1, 1, 0, 0, 0);
460        return $this->returnValue('Year', $format, $ts, $this->year-1);
461    }
462
463    /**
464     * Returns the value for this year
465     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
466     * @return int e.g. 2003 or timestamp
467     * @access public
468     */
469    function thisYear($format = 'int')
470    {
471        $ts = $this->cE->dateToStamp($this->year, 1, 1, 0, 0, 0);
472        return $this->returnValue('Year', $format, $ts, $this->year);
473    }
474
475    /**
476     * Returns the value for next year
477     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
478     * @return int e.g. 2004 or timestamp
479     * @access public
480     */
481    function nextYear($format = 'int')
482    {
483        $ts = $this->cE->dateToStamp($this->year+1, 1, 1, 0, 0, 0);
484        return $this->returnValue('Year', $format, $ts, $this->year+1);
485    }
486
487    /**
488     * Returns the value for the previous month
489     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
490     * @return int e.g. 4 or Unix timestamp
491     * @access public
492     */
493    function prevMonth($format = 'int')
494    {
495        $ts = $this->cE->dateToStamp($this->year, $this->month-1, 1, 0, 0, 0);
496        return $this->returnValue('Month', $format, $ts, $this->cE->stampToMonth($ts));
497    }
498
499    /**
500     * Returns the value for this month
501     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
502     * @return int e.g. 5 or timestamp
503     * @access public
504     */
505    function thisMonth($format = 'int')
506    {
507        $ts = $this->cE->dateToStamp($this->year, $this->month, 1, 0, 0, 0);
508        return $this->returnValue('Month', $format, $ts, $this->month);
509    }
510
511    /**
512     * Returns the value for next month
513     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
514     * @return int e.g. 6 or timestamp
515     * @access public
516     */
517    function nextMonth($format = 'int')
518    {
519        $ts = $this->cE->dateToStamp($this->year, $this->month+1, 1, 0, 0, 0);
520        return $this->returnValue('Month', $format, $ts, $this->cE->stampToMonth($ts));
521    }
522
523    /**
524     * Returns the value for the previous day
525     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
526     * @return int e.g. 10 or timestamp
527     * @access public
528     */
529    function prevDay($format = 'int')
530    {
531        $ts = $this->cE->dateToStamp(
532            $this->year, $this->month, $this->day-1, 0, 0, 0);
533        return $this->returnValue('Day', $format, $ts, $this->cE->stampToDay($ts));
534    }
535
536    /**
537     * Returns the value for this day
538     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
539     * @return int e.g. 11 or timestamp
540     * @access public
541     */
542    function thisDay($format = 'int')
543    {
544        $ts = $this->cE->dateToStamp(
545            $this->year, $this->month, $this->day, 0, 0, 0);
546        return $this->returnValue('Day', $format, $ts, $this->day);
547    }
548
549    /**
550     * Returns the value for the next day
551     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
552     * @return int e.g. 12 or timestamp
553     * @access public
554     */
555    function nextDay($format = 'int')
556    {
557        $ts = $this->cE->dateToStamp(
558            $this->year, $this->month, $this->day+1, 0, 0, 0);
559        return $this->returnValue('Day', $format, $ts, $this->cE->stampToDay($ts));
560    }
561
562    /**
563     * Returns the value for the previous hour
564     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
565     * @return int e.g. 13 or timestamp
566     * @access public
567     */
568    function prevHour($format = 'int')
569    {
570        $ts = $this->cE->dateToStamp(
571            $this->year, $this->month, $this->day, $this->hour-1, 0, 0);
572        return $this->returnValue('Hour', $format, $ts, $this->cE->stampToHour($ts));
573    }
574
575    /**
576     * Returns the value for this hour
577     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
578     * @return int e.g. 14 or timestamp
579     * @access public
580     */
581    function thisHour($format = 'int')
582    {
583        $ts = $this->cE->dateToStamp(
584            $this->year, $this->month, $this->day, $this->hour, 0, 0);
585        return $this->returnValue('Hour', $format, $ts, $this->hour);
586    }
587
588    /**
589     * Returns the value for the next hour
590     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
591     * @return int e.g. 14 or timestamp
592     * @access public
593     */
594    function nextHour($format = 'int')
595    {
596        $ts = $this->cE->dateToStamp(
597            $this->year, $this->month, $this->day, $this->hour+1, 0, 0);
598        return $this->returnValue('Hour', $format, $ts, $this->cE->stampToHour($ts));
599    }
600
601    /**
602     * Returns the value for the previous minute
603     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
604     * @return int e.g. 23 or timestamp
605     * @access public
606     */
607    function prevMinute($format = 'int')
608    {
609        $ts = $this->cE->dateToStamp(
610            $this->year, $this->month, $this->day,
611            $this->hour, $this->minute-1, 0);
612        return $this->returnValue('Minute', $format, $ts, $this->cE->stampToMinute($ts));
613    }
614
615    /**
616     * Returns the value for this minute
617     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
618     * @return int e.g. 24 or timestamp
619     * @access public
620     */
621    function thisMinute($format = 'int')
622    {
623        $ts = $this->cE->dateToStamp(
624            $this->year, $this->month, $this->day,
625            $this->hour, $this->minute, 0);
626        return $this->returnValue('Minute', $format, $ts, $this->minute);
627    }
628
629    /**
630    * Returns the value for the next minute
631     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
632     * @return int e.g. 25 or timestamp
633     * @access public
634     */
635    function nextMinute($format = 'int')
636    {
637        $ts = $this->cE->dateToStamp(
638            $this->year, $this->month, $this->day,
639            $this->hour, $this->minute+1, 0);
640        return $this->returnValue('Minute', $format, $ts, $this->cE->stampToMinute($ts));
641    }
642
643    /**
644     * Returns the value for the previous second
645     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
646     * @return int e.g. 43 or timestamp
647     * @access public
648     */
649    function prevSecond($format = 'int')
650    {
651        $ts = $this->cE->dateToStamp(
652            $this->year, $this->month, $this->day,
653            $this->hour, $this->minute, $this->second-1);
654        return $this->returnValue('Second', $format, $ts, $this->cE->stampToSecond($ts));
655    }
656
657    /**
658     * Returns the value for this second
659    * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
660     * @return int e.g. 44 or timestamp
661     * @access public
662     */
663    function thisSecond($format = 'int')
664    {
665        $ts = $this->cE->dateToStamp(
666            $this->year, $this->month, $this->day,
667            $this->hour, $this->minute, $this->second);
668        return $this->returnValue('Second', $format, $ts, $this->second);
669    }
670
671    /**
672     * Returns the value for the next second
673     * @param string return value format ['int' | 'timestamp' | 'object' | 'array']
674     * @return int e.g. 45 or timestamp
675     * @access public
676     */
677    function nextSecond($format = 'int')
678    {
679        $ts = $this->cE->dateToStamp(
680            $this->year, $this->month, $this->day,
681            $this->hour, $this->minute, $this->second+1);
682        return $this->returnValue('Second', $format, $ts, $this->cE->stampToSecond($ts));
683    }
684}
685?>
Note: See TracBrowser for help on using the repository browser.