2 /**********************************************************************
3 Copyright (C) FrontAccounting, LLC.
4 Released under the terms of the GNU General Public License, GPL,
5 as published by the Free Software Foundation, either version 3
6 of the License, or (at your option) any later version.
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10 See the License here <http://www.gnu.org/licenses/gpl-3.0.html>.
11 ***********************************************************************/
13 date validation and parsing functions
15 These functions refer to the global variable defining the date format
16 The date format is defined in config.php called dateformats
17 this can be a string either "d/m/Y" for UK/Australia/New Zealand dates or
18 "m/d/Y" for US/Canada format dates depending on setting in preferences.
22 function __date($year, $month, $day)
26 $how = user_date_format();
27 $sep = $dateseps[user_date_sep()];
35 return $month.$sep.$day.$sep.$year;
37 return $day.$sep.$month.$sep.$year;
39 return $year.$sep.$month.$sep.$day;
42 function is_date($date_)
46 if ($date_ == null || $date_ == "")
48 $how = user_date_format();
49 $sep = $dateseps[user_date_sep()];
51 $date_ = trim($date_);
52 $date_ = str_replace($sep, "", $date_);
53 if (strlen($date_) == 6)
57 $day = substr($date_,2,2);
58 $month = substr($date_,0,2);
59 $year = substr($date_,4,2);
63 $day = substr($date_,0,2);
64 $month = substr($date_,2,2);
65 $year = substr($date_,4,2);
69 $day = substr($date_,4,2);
70 $month = substr($date_,2,2);
71 $year = substr($date_,0,2);
74 elseif (strlen($date_) == 8)
78 $day = substr($date_,2,2);
79 $month = substr($date_,0,2);
80 $year = substr($date_,4,4);
84 $day = substr($date_,0,2);
85 $month = substr($date_,2,2);
86 $year = substr($date_,4,4);
90 $day = substr($date_,6,2);
91 $month = substr($date_,4,2);
92 $year = substr($date_,0,4);
95 if (!isset($year)|| (int)$year > 9999)
101 if (is_long((int)$day) && is_long((int)$month) && is_long((int)$year))
104 if ($date_system == 1)
105 list($year, $month, $day) = jalali_to_gregorian($year, $month, $day);
106 elseif ($date_system == 2)
107 list($year, $month, $day) = islamic_to_gregorian($year, $month, $day);
108 if (checkdate((int)$month, (int)$day, (int)$year))
118 { /*Can't be in an appropriate DefaultDateFormat */
121 } //end of is_date function
130 if ($date_system == 1)
131 list($year, $month, $day) = gregorian_to_jalali($year, $month, $day);
132 elseif ($date_system == 2)
133 list($year, $month, $day) = gregorian_to_islamic($year, $month, $day);
134 return __date($year, $month, $day);
139 if (user_date_format() == 0)
140 return date("h:i a");
145 // Retrieve and optionaly set default date for new document.
147 function new_doc_date($date=null)
149 if (isset($date) && $date != '')
150 $_SESSION['_default_date'] = $date;
152 if (!isset($_SESSION['_default_date']) || !sticky_doc_date())
153 $_SESSION['_default_date'] = Today();
155 return $_SESSION['_default_date'];
158 function is_date_in_fiscalyear($date, $convert=false)
160 global $path_to_root;
161 include_once($path_to_root . "/admin/db/fiscalyears_db.inc");
164 $date2 = sql2date($date);
168 if (user_check_access('SA_MULTIFISCALYEARS')) // allow all open years for this one
169 return is_date_in_fiscalyears($date2, false);
171 if (is_date_closed($date2))
173 $myrow = get_current_fiscalyear();
174 $begin = sql2date($myrow['begin']);
175 $end = sql2date($myrow['end']);
176 if (date1_greater_date2($begin, $date2) || date1_greater_date2($date2, $end))
183 function is_date_closed($date)
185 return !date1_greater_date2($date, sql2date(get_company_pref('gl_closing_date')));
188 function begin_fiscalyear()
190 global $path_to_root;
191 include_once($path_to_root . "/admin/db/fiscalyears_db.inc");
193 $myrow = get_current_fiscalyear();
194 return sql2date($myrow['begin']);
197 function end_fiscalyear()
199 global $path_to_root;
200 include_once($path_to_root . "/admin/db/fiscalyears_db.inc");
202 $myrow = get_current_fiscalyear();
203 return sql2date($myrow['end']);
206 function begin_month($date)
209 list($day, $month, $year) = explode_date_to_dmy($date);
210 if ($date_system == 1)
211 list($year, $month, $day) = gregorian_to_jalali($year, $month, $day);
212 elseif ($date_system == 2)
213 list($year, $month, $day) = gregorian_to_islamic($year, $month, $day);
214 return __date($year, $month, 1);
217 function days_in_month($month, $year)
221 if ($date_system == 1)
223 $days_in_month = array(31, 31, 31, 31, 31, 31, 30, 30, 30, 30, 30, ((((((($year - (($year > 0) ? 474 : 473)) % 2820) + 474) + 38) * 682) % 2816) < 682 ? 30 : 29));
225 elseif ($date_system == 2)
227 $days_in_month = array(30, 29, 30, 29, 30, 29, 30, 29, 30, 29, 30, (((((11 * $year) + 14) % 30) < 11) ? 30 : 29));
229 else // gregorian date
230 $days_in_month = array(31, ((!($year % 4 ) && (($year % 100) || !($year % 400)))?29:28), 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
232 return $days_in_month[$month - 1];
235 function end_month($date)
239 list($day, $month, $year) = explode_date_to_dmy($date);
240 if ($date_system == 1)
242 list($year, $month, $day) = gregorian_to_jalali($year, $month, $day);
244 elseif ($date_system == 2)
246 list($year, $month, $day) = gregorian_to_islamic($year, $month, $day);
249 return __date($year, $month, days_in_month($month, $year));
252 function add_days($date, $days) // accepts negative values as well
255 list($day, $month, $year) = explode_date_to_dmy($date);
256 $timet = mktime(0,0,0, $month, $day + $days, $year);
257 if ($date_system == 1 || $date_system == 2)
259 if ($date_system == 1)
260 list($year, $month, $day) = gregorian_to_jalali(date("Y", $timet), date("n", $timet), date("j", $timet));
261 elseif ($date_system == 2)
262 list($year, $month, $day) = gregorian_to_islamic(date("Y", $timet), date("n", $timet), date("j", $timet));
263 return __date($year, $month, $day);
265 return date(user_date_display(), $timet);
268 function add_months($date, $months) // accepts negative values as well
271 list($day, $month, $year) = explode_date_to_dmy($date);
273 $months += $year*12+$month;
274 $month = ($months-1)%12+1;
275 $year = ($months-$month)/12;
277 $timet = mktime(0,0,0, $month, min($day, days_in_month($month, $year)), $year);
279 if ($date_system == 1 || $date_system == 2)
281 if ($date_system == 1)
282 list($year, $month, $day) = gregorian_to_jalali(date("Y", $timet), date("n", $timet), date("j", $timet));
283 elseif ($date_system == 2)
284 list($year, $month, $day) = gregorian_to_islamic(date("Y", $timet), date("n", $timet), date("j", $timet));
285 return __date($year, $month, $day);
287 return date(user_date_display(), $timet);
290 function add_years($date, $years) // accepts negative values as well
293 list($day, $month, $year) = explode_date_to_dmy($date);
294 $timet = Mktime(0,0,0, $month, $day, $year + $years);
295 if ($date_system == 1 || $date_system == 2)
297 if ($date_system == 1)
298 list($year, $month, $day) = gregorian_to_jalali(date("Y", $timet), date("n", $timet), date("j", $timet));
299 elseif ($date_system == 2)
300 list($year, $month, $day) = gregorian_to_islamic(date("Y", $timet), date("n", $timet), date("j", $timet));
301 return __date($year, $month, $day);
303 return date(user_date_display(), $timet);
306 //_______________________________________________________________
308 function sql2date($date_)
312 //for MySQL dates are in the format YYYY-mm-dd
313 if ($date_ == null || strlen($date_) == 0)
316 if (strpos($date_, "/"))
317 { // In MySQL it could be either / or -
318 list($year, $month, $day) = explode("/", $date_);
320 elseif (strpos ($date_, "-"))
322 list($year, $month, $day) = explode("-", $date_);
325 if (strlen($day) > 4)
326 { /*chop off the time stuff */
327 $day = substr($day, 0, 2);
329 if ($date_system == 1)
330 list($year, $month, $day) = gregorian_to_jalali($year, $month, $day);
331 elseif ($date_system == 2)
332 list($year, $month, $day) = gregorian_to_islamic($year, $month, $day);
333 return __date($year, $month, $day);
334 } // end function sql2date
337 function date2sql($date_)
339 global $dateseps, $date_system;
340 /* takes a date in a the format specified in $DefaultDateFormat
341 and converts to a yyyy/mm/dd format */
343 $how = user_date_format();
344 $sep = $dateseps[user_date_sep()];
346 if ($date_ == null || strlen($date_) == 0)
349 $date_ = trim($date_);
350 $year = $month = $day = 0;
351 // Split up the date by the separator based on "how" to split it
352 if ($how == 0) // MMDDYYYY
353 list($month, $day, $year) = explode($sep, $date_);
354 elseif ($how == 1) // DDMMYYYY
355 list($day, $month, $year) = explode($sep, $date_);
356 else // $how == 2, YYYYMMDD
357 list($year, $month, $day) = explode($sep, $date_);
359 //to modify assumption in 2030
360 if ($date_system == 0 || $date_system == 3)
366 elseif ((int)$year > 59 && (int)$year < 100)
371 if ((int)$year > 9999)
375 if ($date_system == 1)
376 list($year, $month, $day) = jalali_to_gregorian($year, $month, $day);
377 elseif ($date_system == 2)
378 list($year, $month, $day) = islamic_to_gregorian($year, $month, $day);
380 return sprintf("%04d-%02d-%02d", $year, $month, $day);
383 function date1_greater_date2 ($date1, $date2)
386 /* returns 1 true if date1 is greater than date_ 2 */
388 $date1 = date2sql($date1);
389 $date2 = date2sql($date2);
391 @list($year1, $month1, $day1) = explode("-", $date1);
392 @list($year2, $month2, $day2) = explode("-", $date2);
398 elseif ($year1 == $year2)
400 if ($month1 > $month2)
404 elseif ($month1 == $month2)
416 function date_diff2 ($date1, $date2, $period)
419 /* expects dates in the format specified in $DefaultDateFormat - period can be one of 'd','w','y','m'
420 months are assumed to be 30 days and years 365.25 days This only works
421 provided that both dates are after 1970. Also only works for dates up to the year 2035 ish */
423 $date1 = date2sql($date1);
424 $date2 = date2sql($date2);
425 list($year1, $month1, $day1) = explode("-", $date1);
426 list($year2, $month2, $day2) = explode("-", $date2);
428 $stamp1 = mktime(0,0,0, (int)$month1, (int)$day1, (int)$year1);
429 $stamp2 = mktime(0,0,0, (int)$month2, (int)$day2, (int)$year2);
430 $difference = $stamp1 - $stamp2;
432 /* difference is the number of seconds between each date negative if date_ 2 > date_ 1 */
437 return (int)($difference / (24 * 60 * 60));
439 return (int)($difference / (24 * 60 * 60 * 7));
441 return (int)($difference / (24 * 60 * 60 * 30));
445 return (int)($difference / (24 * 60 * 60 * 365.25));
451 function explode_date_to_dmy($date_)
453 $date = date2sql($date_);
458 list($year, $month, $day) = explode("-", $date);
459 return array($day, $month, $year);
464 return (int) ($a / $b);
466 /* Based on convertor to and from Gregorian and Jalali calendars.
467 Copyright (C) 2000 Roozbeh Pournader and Mohammad Toossi
468 Released under GNU General Public License */
470 function gregorian_to_jalali ($g_y, $g_m, $g_d)
472 $g_days_in_month = array(31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
473 $j_days_in_month = array(31, 31, 31, 31, 31, 31, 30, 30, 30, 30, 30, 29);
479 $g_day_no = 365 * $gy + div($gy + 3, 4) - div($gy + 99, 100) + div($gy + 399, 400);
481 for ($i = 0; $i < $gm; ++$i)
482 $g_day_no += $g_days_in_month[$i];
483 if ($gm > 1 && (($gy % 4 == 0 && $gy % 100 != 0) || ($gy % 400 == 0)))
484 /* leap and after Feb */
487 $j_day_no = $g_day_no - 79;
489 $j_np = div($j_day_no, 12053); /* 12053 = 365*33 + 32/4 */
492 $jy = 979 + 33 * $j_np + 4 * div($j_day_no, 1461); /* 1461 = 365*4 + 4/4 */
496 if ($j_day_no >= 366)
498 $jy += div($j_day_no - 1, 365);
499 $j_day_no = ($j_day_no - 1) % 365;
502 for ($i = 0; $i < 11 && $j_day_no >= $j_days_in_month[$i]; ++$i)
503 $j_day_no -= $j_days_in_month[$i];
507 return array($jy, $jm, $jd);
510 function jalali_to_gregorian($j_y, $j_m, $j_d)
512 $g_days_in_month = array(31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31);
513 $j_days_in_month = array(31, 31, 31, 31, 31, 31, 30, 30, 30, 30, 30, 29);
519 $j_day_no = 365 * $jy + div($jy, 33) * 8 + div($jy % 33 + 3, 4);
520 for ($i = 0; $i < $jm; ++$i)
521 $j_day_no += $j_days_in_month[$i];
525 $g_day_no = $j_day_no + 79;
527 $gy = 1600 + 400 * div($g_day_no, 146097); /* 146097 = 365*400 + 400/4 - 400/100 + 400/400 */
531 if ($g_day_no >= 36525) /* 36525 = 365*100 + 100/4 */
534 $gy += 100 * div($g_day_no, 36524); /* 36524 = 365*100 + 100/4 - 100/100 */
537 if ($g_day_no >= 365)
543 $gy += 4 * div($g_day_no, 1461); /* 1461 = 365*4 + 4/4 */
546 if ($g_day_no >= 366)
551 $gy += div($g_day_no, 365);
555 for ($i = 0; $g_day_no >= $g_days_in_month[$i] + ($i == 1 && $leap); $i++)
556 $g_day_no -= $g_days_in_month[$i] + ($i == 1 && $leap);
560 return array($gy, $gm, $gd);
562 /* Based on Hidri Date Script
563 Released under GNU General Public License */
564 function gregorian_to_islamic($g_y, $g_m, $g_d)
569 if (($y > 1582) || (($y == 1582) && ($m > 10)) || (($y == 1582) &&
570 ($m == 10) && ($d > 14)))
572 $jd = (int)((1461 * ($y + 4800 + (int)(($m - 14) / 12)))/ 4) +
573 (int)((367 * ($m - 2 - 12 * ((int)(($m - 14) / 12)))) / 12) -
574 (int)((3 * ((int)(($y + 4900 + (int)(($m - 14) / 12)) / 100))) / 4) + $d - 32075;
578 $jd = 367 * $y - (int)((7 * ($y + 5001 + (int)(($m - 9) / 7))) / 4) +
579 (int)((275 * $m) / 9) + $d + 1729777;
581 $l = $jd - 1948440 + 10632;
582 $n = (int)(($l - 1) / 10631);
583 $l = $l - 10631 * $n + 354;
584 $j = ((int)((10985 - $l) / 5316)) * ((int)((50 * $l) / 17719)) +
585 ((int)($l / 5670)) * ((int)((43 * $l) / 15238));
586 $l = $l - ((int)((30 - $j) / 15)) * ((int)((17719 * $j) / 50)) -
587 ((int)($j / 16)) * ((int)((15238 * $j) / 43)) + 29;
588 $m = (int)((24 * $l) / 709);
589 $d = $l - (int)((709 * $m) / 24);
590 $y = 30 * $n + $j - 30;
591 return array($y, $m, $d);
594 function islamic_to_gregorian($i_y, $i_m, $i_d)
600 $jd = (int)((11 * $y + 3) / 30) + 354 * $y + 30 * $m - (int)(($m - 1) / 2) + $d + 1948440 - 385;
604 $n = (int)((4 * $l) / 146097);
605 $l = $l - (int)((146097 * $n + 3) / 4);
606 $i = (int)((4000 * ($l + 1)) / 1461001);
607 $l = $l - (int)((1461 * $i) / 4) + 31;
608 $j = (int)((80 * $l) / 2447);
609 $d = $l - (int)((2447 * $j) / 80);
611 $m = $j + 2 - 12 * $l;
612 $y = 100 * ($n - 49) + $i + $l;
617 $k = (int)(($j - 1) / 1461);
619 $n = (int)(($l - 1) / 365) - (int)($l / 1461);
620 $i = $l - 365 * $n + 30;
621 $j = (int)((80 * $i) / 2447);
622 $d = $i - (int)((2447 * $j) / 80);
624 $m = $j + 2 - 12 * $i;
625 $y = 4 * $k + $n + $i - 4716;
627 return array($y, $m, $d);