AutorÃa | Ultima modificación | Ver Log |
<?phpnamespace PhpOffice\PhpSpreadsheet\Calculation\DateTimeExcel;use Composer\Pcre\Preg;use Datetime;use PhpOffice\PhpSpreadsheet\Calculation\ArrayEnabled;use PhpOffice\PhpSpreadsheet\Calculation\Functions;use PhpOffice\PhpSpreadsheet\Calculation\Information\ExcelError;use PhpOffice\PhpSpreadsheet\Shared\Date as SharedDateHelper;class TimeValue{use ArrayEnabled;private const EXTRACT_TIME = '/\b'. '(\d+)' // match[1] - hour. '(:' // start of match[2] (rest of string) - colon. '(\d+' // start of match[3] - minute. '(:\d+' // start of match[4] - colon and seconds. '([.]\d+)?' // match[5] - optional decimal point followed by fractional seconds. ')?' // end of match[4], which is optional. ')' // end of match 3// Excel does not require 'm' to trail 'a' or 'p'; Php does. '(\s*(a|p))?' // match[6] optional whitespace followed by optional match[7] a or p. ')' // end of match[2]. '/i';/*** TIMEVALUE.** Returns a value that represents a particular time.* Use TIMEVALUE to convert a time represented by a text string to an Excel or PHP date/time stamp* value.** NOTE: When used in a Cell Formula, MS Excel changes the cell format so that it matches the time* format of your regional settings. PhpSpreadsheet does not change cell formatting in this way.** Excel Function:* TIMEVALUE(timeValue)** @param null|array|bool|float|int|string $timeValue A text string that represents a time in any one of the Microsoft* Excel time formats; for example, "6:45 PM" and "18:45" text strings* within quotation marks that represent time.* Date information in time_text is ignored.* Or can be an array of date/time values** @return array|Datetime|float|int|string Excel date/time serial value, PHP date/time serial value or PHP date/time object,* depending on the value of the ReturnDateType flag* If an array of numbers is passed as the argument, then the returned result will also be an array* with the same dimensions*/public static function fromString(null|array|string|int|bool|float $timeValue): array|string|Datetime|int|float{if (is_array($timeValue)) {return self::evaluateSingleArgumentArray([self::class, __FUNCTION__], $timeValue);}// try to parse as time iff there is at least one digitif (is_string($timeValue) && !Preg::isMatch('/\d/', $timeValue)) {return ExcelError::VALUE();}$timeValue = trim((string) $timeValue, '"');if (Preg::isMatch(self::EXTRACT_TIME, $timeValue, $matches)) {if (empty($matches[6])) { // am/pm$hour = (int) $matches[0];$timeValue = ($hour % 24) . $matches[2];} elseif ($matches[6] === $matches[7]) { // Excel wants space before am/pmreturn ExcelError::VALUE();} else {$timeValue = $matches[0] . 'm';}}$PHPDateArray = Helpers::dateParse($timeValue);$retValue = ExcelError::VALUE();if (Helpers::dateParseSucceeded($PHPDateArray)) {$hour = $PHPDateArray['hour'];$minute = $PHPDateArray['minute'];$second = $PHPDateArray['second'];// OpenOffice-specific code removed - it works just like Excel$excelDateValue = SharedDateHelper::formattedPHPToExcel(1900, 1, 1, $hour, $minute, $second) - 1;$retType = Functions::getReturnDateType();if ($retType === Functions::RETURNDATE_EXCEL) {$retValue = (float) $excelDateValue;} elseif ($retType === Functions::RETURNDATE_UNIX_TIMESTAMP) {$retValue = (int) SharedDateHelper::excelToTimestamp($excelDateValue + 25569) - 3600;} else {$retValue = new Datetime('1900-01-01 ' . $PHPDateArray['hour'] . ':' . $PHPDateArray['minute'] . ':' . $PHPDateArray['second']);}}return $retValue;}}