/** * Returns a formatted string that represents a date in user time * WARNING: note that the format is for strftime(), not date(). * Because of a bug in most Windows time libraries, we can't use * the nicer %e, so we have to use %d which has leading zeroes. * A lot of the fuss in the function is just getting rid of these leading * zeroes as efficiently as possible. * * If parameter fixday = true (default), then take off leading * zero from %d, else mantain it. * * @param int $date timestamp in GMT * @param string $format strftime format * If empty (default) then 'strftimedaydatetime' from the language pack * will be used * @param float $timezone * @param bool $fixday * If true (default) then the leading zero from %d is removed, * otherwise the leading zero is mantained. * Can be overridden by setting $CFG->nofixday to true in config.php * @param bool $fixmonth * If true (default) then the leading zero from %m is removed, * otherwise the leading zero is mantained. * Can be overridden by setting $CFG->nofixmonth to true in config.php * @return string */ function userdate($date, $format='', $timezone=99, $fixday = true, $fixmonth = true) { global $CFG; if (empty($format)) { $format = get_string('strftimedaydatetime'); } // variables required for fixing dates in some multibyte language packs on Windows servers static $endchar = ''; static $textlib = false; static $localewin = null; // set up date fixing variables if they are required for this language pack if (is_null($localewin)) { $localewin = new stdClass(); if ($CFG->ostype=='WINDOWS') { $localewin->charset = get_string('localewincharset'); $localewin->charsetdaymonth = get_string('localewincharsetdaymonth'); } else { $localewin->charset = false; $localewin->charsetdaymonth = false; } if ($localewin->charsetdaymonth) { // $endchar helps strftime() to detect the end of the format string // when the last character would otherwise be a multibyte character $endchar = ' '; } if ($localewin->charset || $localewin->charsetdaymonth) { $textlib = textlib_get_instance(); } } // assemble an array of fixes to be applied during date formatting $fix = array(); if (empty($CFG->nofixday) && $fixday) { $fix['%d'] = 'dd'; // two-digit day number (01 - 31) } if (empty($CFG->nofixmonth) && $fixmonth) { $fix['%m'] = 'mm'; // two-digit month number (01 - 12) } if ($localewin->charsetdaymonth) { $fix['%A'] = 'AA'; // full weekday name $fix['%a'] = 'aa'; // abbreviated weekday name $fix['%B'] = 'BB'; // full month name $fix['%b'] = 'bb'; // abbreviated month name $fix['%p'] = 'pp'; // 'am' or 'pm' (or the corresponding strings for the current locale) } // modify format string for each relevant fix (unnecessary fixes are discarded) foreach ($fix as $fmt=>$str) { if (strpos($format, $fmt)===false) { unset($fix[$fmt]); } else { $format = str_replace($fmt, $str, $format); } } // adjust date for this time zone $date += dst_offset_on($date); $timezone = get_user_timezone_offset($timezone); // define date formatting function if (abs($timezone) > 13) { /// Server time $strftime = 'strftime'; } else { $strftime = 'gmstrftime'; $date += (int)($timezone * 3600); } // format the date using the modified $format string $datestring = $strftime($format.$endchar, $date); // if necessary, remove $endchar from the end of $datestring if ($endchar) { $datestring = substr($datestring, 0, -1); } // apply relevant fixes for this format string foreach ($fix as $fmt=>$str) { switch ($fmt) { case '%d': case '%m': $replace = $strftime($fmt, $date); if (substr($replace, 0, 1)==='0') { $replace = substr($replace, 1); // remove leading zero } $datestring = str_replace($str, $replace, $datestring); break; case '%A': case '%a': case '%B': case '%b': case '%p': $replace = $textlib->convert($strftime($fmt, $date), $localewin->charsetdaymonth, 'utf-8'); $datestring = str_replace($str, $replace, $datestring); break; } } // If we are running under Windows convert from windows encoding to UTF-8 // (because it's impossible to specify UTF-8 to fetch locale info in Win32) if ($localewin->charset) { $datestring = $textlib->convert($datestring, $localewin->charset, 'utf-8'); } return $datestring; }