61 if (!
defined(
'PHPEXCEL_ROOT')) {
65 define(
'PHPEXCEL_ROOT', dirname(__FILE__) .
'/../../');
66 require(PHPEXCEL_ROOT .
'PHPExcel/Autoloader.php');
442 if (!file_exists($pFilename)) {
451 $res = $ole->read($pFilename);
468 if (!file_exists($pFilename)) {
472 $worksheetNames =
array();
478 $this->_dataSize = strlen($this->_data);
481 $this->_sheets =
array();
484 while ($this->_pos < $this->_dataSize) {
485 $code = self::_GetInt2d($this->_data, $this->_pos);
488 case self::XLS_Type_BOF: $this->
_readBof();
break;
489 case self::XLS_Type_SHEET: $this->
_readSheet();
break;
490 case self::XLS_Type_EOF: $this->
_readDefault();
break 2;
495 foreach ($this->_sheets as $sheet) {
496 if ($sheet[
'sheetType'] != 0x00) {
501 $worksheetNames[] = $sheet[
'name'];
504 return $worksheetNames;
517 if (!file_exists($pFilename)) {
521 $worksheetInfo =
array();
527 $this->_dataSize = strlen($this->_data);
531 $this->_sheets =
array();
534 while ($this->_pos < $this->_dataSize) {
535 $code = self::_GetInt2d($this->_data, $this->_pos);
538 case self::XLS_Type_BOF: $this->
_readBof();
break;
539 case self::XLS_Type_SHEET: $this->
_readSheet();
break;
540 case self::XLS_Type_EOF: $this->
_readDefault();
break 2;
546 foreach ($this->_sheets as $sheet) {
548 if ($sheet[
'sheetType'] != 0x00) {
556 $tmpInfo[
'worksheetName'] = $sheet[
'name'];
557 $tmpInfo[
'lastColumnLetter'] =
'A';
558 $tmpInfo[
'lastColumnIndex'] = 0;
559 $tmpInfo[
'totalRows'] = 0;
560 $tmpInfo[
'totalColumns'] = 0;
562 $this->_pos = $sheet[
'offset'];
564 while ($this->_pos <= $this->_dataSize - 4) {
565 $code = self::_GetInt2d($this->_data, $this->_pos);
568 case self::XLS_Type_RK:
569 case self::XLS_Type_LABELSST:
570 case self::XLS_Type_NUMBER:
571 case self::XLS_Type_FORMULA:
572 case self::XLS_Type_BOOLERR:
573 case self::XLS_Type_LABEL:
574 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
575 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
578 $this->_pos += 4 + $length;
580 $rowIndex = self::_GetInt2d($recordData, 0) + 1;
581 $columnIndex = self::_GetInt2d($recordData, 2);
583 $tmpInfo[
'totalRows'] = max($tmpInfo[
'totalRows'], $rowIndex);
584 $tmpInfo[
'lastColumnIndex'] = max($tmpInfo[
'lastColumnIndex'], $columnIndex);
586 case self::XLS_Type_BOF: $this->
_readBof();
break;
587 case self::XLS_Type_EOF: $this->
_readDefault();
break 2;
593 $tmpInfo[
'totalColumns'] = $tmpInfo[
'lastColumnIndex'] + 1;
595 $worksheetInfo[] = $tmpInfo;
598 return $worksheetInfo;
609 public function load($pFilename)
616 $this->_phpExcel->removeSheetByIndex(0);
617 if (!$this->_readDataOnly) {
618 $this->_phpExcel->removeCellStyleXfByIndex(0);
619 $this->_phpExcel->removeCellXfByIndex(0);
629 $this->_dataSize = strlen($this->_data);
633 $this->_codepage =
'CP1252';
634 $this->_formats =
array();
635 $this->_objFonts =
array();
636 $this->_palette =
array();
637 $this->_sheets =
array();
638 $this->_externalBooks =
array();
639 $this->_ref =
array();
640 $this->_definedname =
array();
641 $this->_sst =
array();
642 $this->_drawingGroupData =
'';
643 $this->_xfIndex =
'';
644 $this->_mapCellXfIndex =
array();
645 $this->_mapCellStyleXfIndex =
array();
648 while ($this->_pos < $this->_dataSize) {
649 $code = self::_GetInt2d($this->_data, $this->_pos);
652 case self::XLS_Type_BOF: $this->
_readBof();
break;
656 case self::XLS_Type_FONT: $this->
_readFont();
break;
657 case self::XLS_Type_FORMAT: $this->
_readFormat();
break;
658 case self::XLS_Type_XF: $this->
_readXf();
break;
659 case self::XLS_Type_XFEXT: $this->
_readXfExt();
break;
660 case self::XLS_Type_STYLE: $this->
_readStyle();
break;
661 case self::XLS_Type_PALETTE: $this->
_readPalette();
break;
662 case self::XLS_Type_SHEET: $this->
_readSheet();
break;
668 case self::XLS_Type_SST: $this->
_readSst();
break;
669 case self::XLS_Type_EOF: $this->
_readDefault();
break 2;
676 if (!$this->_readDataOnly) {
677 foreach ($this->_objFonts as $objFont) {
678 if (isset($objFont->colorIndex)) {
679 $color = self::_readColor($objFont->colorIndex,$this->_palette,$this->_version);
680 $objFont->getColor()->setRGB($color[
'rgb']);
684 foreach ($this->_phpExcel->getCellXfCollection() as $objStyle) {
686 $fill = $objStyle->getFill();
688 if (isset($fill->startcolorIndex)) {
689 $startColor = self::_readColor($fill->startcolorIndex,$this->_palette,$this->_version);
690 $fill->getStartColor()->setRGB($startColor[
'rgb']);
693 if (isset($fill->endcolorIndex)) {
694 $endColor = self::_readColor($fill->endcolorIndex,$this->_palette,$this->_version);
695 $fill->getEndColor()->setRGB($endColor[
'rgb']);
699 $top = $objStyle->getBorders()->getTop();
700 $right = $objStyle->getBorders()->getRight();
701 $bottom = $objStyle->getBorders()->getBottom();
702 $left = $objStyle->getBorders()->getLeft();
703 $diagonal = $objStyle->getBorders()->getDiagonal();
705 if (isset($top->colorIndex)) {
706 $borderTopColor = self::_readColor($top->colorIndex,$this->_palette,$this->_version);
707 $top->getColor()->setRGB($borderTopColor[
'rgb']);
710 if (isset($right->colorIndex)) {
711 $borderRightColor = self::_readColor($right->colorIndex,$this->_palette,$this->_version);
712 $right->getColor()->setRGB($borderRightColor[
'rgb']);
715 if (isset($bottom->colorIndex)) {
716 $borderBottomColor = self::_readColor($bottom->colorIndex,$this->_palette,$this->_version);
717 $bottom->getColor()->setRGB($borderBottomColor[
'rgb']);
720 if (isset($left->colorIndex)) {
721 $borderLeftColor = self::_readColor($left->colorIndex,$this->_palette,$this->_version);
722 $left->getColor()->setRGB($borderLeftColor[
'rgb']);
725 if (isset($diagonal->colorIndex)) {
726 $borderDiagonalColor = self::_readColor($diagonal->colorIndex,$this->_palette,$this->_version);
727 $diagonal->getColor()->setRGB($borderDiagonalColor[
'rgb']);
733 if (!$this->_readDataOnly && $this->_drawingGroupData) {
736 $escherWorkbook =
$reader->load($this->_drawingGroupData);
744 foreach ($this->_sheets as $sheet) {
746 if ($sheet[
'sheetType'] != 0x00) {
752 if (isset($this->_loadSheetsOnly) && !in_array($sheet[
'name'], $this->_loadSheetsOnly)) {
757 $this->_phpSheet = $this->_phpExcel->createSheet();
761 $this->_phpSheet->setTitle($sheet[
'name'],
false);
762 $this->_phpSheet->setSheetState($sheet[
'sheetState']);
764 $this->_pos = $sheet[
'offset'];
767 $this->_isFitToPages =
false;
770 $this->_drawingData =
'';
773 $this->_objs =
array();
776 $this->_sharedFormulaParts =
array();
779 $this->_sharedFormulas =
array();
782 $this->_textObjects =
array();
785 $this->_cellNotes =
array();
786 $this->textObjRef = -1;
788 while ($this->_pos <= $this->_dataSize - 4) {
789 $code = self::_GetInt2d($this->_data, $this->_pos);
792 case self::XLS_Type_BOF: $this->
_readBof();
break;
795 case self::XLS_Type_SHEETPR: $this->
_readSheetPr();
break;
798 case self::XLS_Type_HEADER: $this->
_readHeader();
break;
799 case self::XLS_Type_FOOTER: $this->
_readFooter();
break;
800 case self::XLS_Type_HCENTER: $this->
_readHcenter();
break;
801 case self::XLS_Type_VCENTER: $this->
_readVcenter();
break;
807 case self::XLS_Type_PROTECT: $this->
_readProtect();
break;
812 case self::XLS_Type_COLINFO: $this->
_readColInfo();
break;
813 case self::XLS_Type_DIMENSION: $this->
_readDefault();
break;
814 case self::XLS_Type_ROW: $this->
_readRow();
break;
815 case self::XLS_Type_DBCELL: $this->
_readDefault();
break;
816 case self::XLS_Type_RK: $this->
_readRk();
break;
818 case self::XLS_Type_MULRK: $this->
_readMulRk();
break;
819 case self::XLS_Type_NUMBER: $this->
_readNumber();
break;
820 case self::XLS_Type_FORMULA: $this->
_readFormula();
break;
822 case self::XLS_Type_BOOLERR: $this->
_readBoolErr();
break;
824 case self::XLS_Type_LABEL: $this->
_readLabel();
break;
825 case self::XLS_Type_BLANK: $this->
_readBlank();
break;
827 case self::XLS_Type_OBJ: $this->
_readObj();
break;
828 case self::XLS_Type_WINDOW2: $this->
_readWindow2();
break;
830 case self::XLS_Type_SCL: $this->
_readScl();
break;
831 case self::XLS_Type_PANE: $this->
_readPane();
break;
840 case self::XLS_Type_NOTE: $this->
_readNote();
break;
844 case self::XLS_Type_EOF: $this->
_readDefault();
break 2;
851 if (!$this->_readDataOnly && $this->_drawingData) {
854 $escherWorksheet =
$reader->load($this->_drawingData);
861 $allSpContainers = $escherWorksheet->getDgContainer()->getSpgrContainer()->getAllSpContainers();
865 foreach ($this->_objs as
$n => $obj) {
871 if (isset($allSpContainers[
$n + 1]) && is_object($allSpContainers[
$n + 1])) {
872 $spContainer = $allSpContainers[
$n + 1];
875 if ($spContainer->getNestingLevel() > 1) {
883 $startOffsetX = $spContainer->getStartOffsetX();
884 $startOffsetY = $spContainer->getStartOffsetY();
885 $endOffsetX = $spContainer->getEndOffsetX();
886 $endOffsetY = $spContainer->getEndOffsetY();
895 switch ($obj[
'otObjType']) {
901 if (isset($this->_cellNotes[$obj[
'idObjID']])) {
902 $cellNote = $this->_cellNotes[$obj[
'idObjID']];
904 if (isset($this->_textObjects[$obj[
'idObjID']])) {
905 $textObject = $this->_textObjects[$obj[
'idObjID']];
906 $this->_cellNotes[$obj[
'idObjID']][
'objTextData'] = $textObject;
916 $BSEindex = $spContainer->getOPT(0x0104);
917 $BSECollection = $escherWorkbook->getDggContainer()->getBstoreContainer()->getBSECollection();
918 $BSE = $BSECollection[$BSEindex - 1];
919 $blipType = $BSE->getBlipType();
922 if ($blip = $BSE->getBlip()) {
923 $ih = imagecreatefromstring($blip->getData());
925 $drawing->setImageResource($ih);
928 $drawing->setResizeProportional(
false);
929 $drawing->setWidth($width);
930 $drawing->setHeight($height);
931 $drawing->setOffsetX($offsetX);
932 $drawing->setOffsetY($offsetY);
946 $drawing->setWorksheet($this->_phpSheet);
947 $drawing->setCoordinates($spContainer->getStartCoordinates());
961 if ($this->_version == self::XLS_BIFF8) {
962 foreach ($this->_sharedFormulaParts as $cell => $baseCell) {
971 if (!empty($this->_cellNotes)) {
972 foreach($this->_cellNotes as $note => $noteDetails) {
973 if (!isset($noteDetails[
'objTextData'])) {
974 if (isset($this->_textObjects[$note])) {
975 $textObject = $this->_textObjects[$note];
976 $noteDetails[
'objTextData'] = $textObject;
978 $noteDetails[
'objTextData'][
'text'] =
'';
984 $cellAddress = str_replace(
'$',
'',$noteDetails[
'cellRef']);
985 $this->_phpSheet->getComment( $cellAddress )
986 ->setAuthor( $noteDetails[
'author'] )
987 ->setText($this->
_parseRichText($noteDetails[
'objTextData'][
'text']) );
993 foreach ($this->_definedname as $definedName) {
994 if ($definedName[
'isBuiltInName']) {
995 switch ($definedName[
'name']) {
997 case pack(
'C', 0x06):
1000 $ranges = explode(
',', $definedName[
'formula']);
1002 $extractedRanges =
array();
1003 foreach ($ranges as $range) {
1008 $explodes = explode(
'!', $range);
1009 $sheetName = trim($explodes[0],
"'");
1011 if (count($explodes) == 2) {
1012 if (strpos($explodes[1],
':') === FALSE) {
1013 $explodes[1] = $explodes[1] .
':' . $explodes[1];
1015 $extractedRanges[] = str_replace(
'$',
'', $explodes[1]);
1018 if ($docSheet = $this->_phpExcel->getSheetByName($sheetName)) {
1019 $docSheet->getPageSetup()->setPrintArea(implode(
',', $extractedRanges));
1023 case pack(
'C', 0x07):
1035 $ranges = explode(
',', $definedName[
'formula']);
1037 foreach ($ranges as $range) {
1042 $explodes = explode(
'!', $range);
1044 if (count($explodes) == 2) {
1045 if ($docSheet = $this->_phpExcel->getSheetByName($explodes[0])) {
1047 $extractedRange = $explodes[1];
1048 $extractedRange = str_replace(
'$',
'', $extractedRange);
1050 $coordinateStrings = explode(
':', $extractedRange);
1051 if (count($coordinateStrings) == 2) {
1055 if ($firstColumn ==
'A' and $lastColumn ==
'IV') {
1057 $docSheet->getPageSetup()->setRowsToRepeatAtTop(
array($firstRow, $lastRow));
1058 } elseif ($firstRow == 1
and $lastRow == 65536) {
1060 $docSheet->getPageSetup()->setColumnsToRepeatAtLeft(
array($firstColumn, $lastColumn));
1071 $explodes = explode(
'!', $definedName[
'formula']);
1073 if (count($explodes) == 2) {
1074 if (($docSheet = $this->_phpExcel->getSheetByName($explodes[0])) ||
1075 ($docSheet = $this->_phpExcel->getSheetByName(trim($explodes[0],
"'")))) {
1076 $extractedRange = $explodes[1];
1077 $extractedRange = str_replace(
'$',
'', $extractedRange);
1079 $localOnly = ($definedName[
'scope'] == 0) ?
false :
true;
1081 $scope = ($definedName[
'scope'] == 0) ?
1082 null : $this->_phpExcel->getSheetByName($this->_sheets[$definedName[
'scope'] - 1][
'name']);
1084 $this->_phpExcel->addNamedRange(
new PHPExcel_NamedRange((
string)$definedName[
'name'], $docSheet, $extractedRange, $localOnly, $scope) );
1092 $this->_data = null;
1111 if ($this->_encryption == self::MS_BIFF_CRYPTO_NONE || $pos < $this->_encryptionStartPos) {
1116 if ($this->_encryption == self::MS_BIFF_CRYPTO_RC4) {
1118 $oldBlock = floor($this->_rc4Pos / self::REKEY_BLOCK);
1119 $block = floor($pos / self::REKEY_BLOCK);
1120 $endBlock = floor(($pos + $len) / self::REKEY_BLOCK);
1124 if ($block != $oldBlock || $pos < $this->_rc4Pos || !$this->_rc4Key) {
1125 $this->_rc4Key = $this->
_makeKey($block, $this->_md5Ctxt);
1126 $step = $pos % self::REKEY_BLOCK;
1130 $this->_rc4Key->RC4(str_repeat(
"\0",
$step));
1133 while ($block != $endBlock) {
1134 $step = self::REKEY_BLOCK - ($pos % self::REKEY_BLOCK);
1135 $recordData .= $this->_rc4Key->RC4(substr(
$data, 0,
$step));
1140 $this->_rc4Key = $this->
_makeKey($block, $this->_md5Ctxt);
1142 $recordData .= $this->_rc4Key->RC4(substr(
$data, 0, $len));
1146 $this->_rc4Pos = $pos + $len;
1148 } elseif ($this->_encryption == self::MS_BIFF_CRYPTO_XOR) {
1165 $res = $ole->read($pFilename);
1167 $this->_data = $ole->getStream($ole->wrkbook);
1170 $this->_summaryInformation = $ole->getStream($ole->summaryInformation);
1173 $this->_documentSummaryInformation = $ole->getStream($ole->documentSummaryInformation);
1185 if (!isset($this->_summaryInformation)) {
1195 $secCount = self::_GetInt4d($this->_summaryInformation, 24);
1199 $secOffset = self::_GetInt4d($this->_summaryInformation, 44);
1203 $secLength = self::_GetInt4d($this->_summaryInformation, $secOffset);
1206 $countProperties = self::_GetInt4d($this->_summaryInformation, $secOffset+4);
1209 $codePage =
'CP1252';
1213 for ($i = 0; $i < $countProperties; ++$i) {
1216 $id = self::_GetInt4d($this->_summaryInformation, ($secOffset+8) + (8 * $i));
1220 $offset = self::_GetInt4d($this->_summaryInformation, ($secOffset+12) + (8 * $i));
1222 $type = self::_GetInt4d($this->_summaryInformation, $secOffset + $offset);
1230 $value = self::_GetInt2d($this->_summaryInformation, $secOffset + 4 + $offset);
1234 $value = self::_GetInt4d($this->_summaryInformation, $secOffset + 4 + $offset);
1242 $byteLength = self::_GetInt4d($this->_summaryInformation, $secOffset + 4 + $offset);
1243 $value = substr($this->_summaryInformation, $secOffset + 8 + $offset, $byteLength);
1245 $value = rtrim($value);
1264 $this->_phpExcel->getProperties()->setTitle($value);
1268 $this->_phpExcel->getProperties()->setSubject($value);
1272 $this->_phpExcel->getProperties()->setCreator($value);
1276 $this->_phpExcel->getProperties()->setKeywords($value);
1280 $this->_phpExcel->getProperties()->setDescription($value);
1288 $this->_phpExcel->getProperties()->setLastModifiedBy($value);
1304 $this->_phpExcel->getProperties()->setCreated($value);
1308 $this->_phpExcel->getProperties()->setModified($value);
1345 if (!isset($this->_documentSummaryInformation)) {
1355 $secCount = self::_GetInt4d($this->_documentSummaryInformation, 24);
1360 $secOffset = self::_GetInt4d($this->_documentSummaryInformation, 44);
1365 $secLength = self::_GetInt4d($this->_documentSummaryInformation, $secOffset);
1369 $countProperties = self::_GetInt4d($this->_documentSummaryInformation, $secOffset+4);
1373 $codePage =
'CP1252';
1377 for ($i = 0; $i < $countProperties; ++$i) {
1380 $id = self::_GetInt4d($this->_documentSummaryInformation, ($secOffset+8) + (8 * $i));
1385 $offset = self::_GetInt4d($this->_documentSummaryInformation, ($secOffset+12) + (8 * $i));
1387 $type = self::_GetInt4d($this->_documentSummaryInformation, $secOffset + $offset);
1396 $value = self::_GetInt2d($this->_documentSummaryInformation, $secOffset + 4 + $offset);
1400 $value = self::_GetInt4d($this->_documentSummaryInformation, $secOffset + 4 + $offset);
1404 $value = self::_GetInt2d($this->_documentSummaryInformation, $secOffset + 4 + $offset);
1405 $value = ($value == 0 ? false :
true);
1413 $byteLength = self::_GetInt4d($this->_documentSummaryInformation, $secOffset + 4 + $offset);
1414 $value = substr($this->_documentSummaryInformation, $secOffset + 8 + $offset, $byteLength);
1416 $value = rtrim($value);
1435 $this->_phpExcel->getProperties()->setCategory($value);
1483 $this->_phpExcel->getProperties()->setManager($value);
1487 $this->_phpExcel->getProperties()->setCompany($value);
1504 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1508 $this->_pos += 4 + $length;
1519 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1520 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1523 $this->_pos += 4 + $length;
1525 if ($this->_readDataOnly) {
1530 if ($this->_version == self::XLS_BIFF8) {
1531 $noteObjID = self::_GetInt2d($recordData, 6);
1532 $noteAuthor = self::_readUnicodeStringLong(substr($recordData, 8));
1533 $noteAuthor = $noteAuthor[
'value'];
1538 $this->_cellNotes[$noteObjID] =
array(
'cellRef' => $cellAddress,
1539 'objectID' => $noteObjID,
1540 'author' => $noteAuthor
1544 if ($cellAddress ==
'$B$65536') {
1548 $row = self::_GetInt2d($recordData, 0);
1550 $cellAddress = array_pop(array_keys($this->_phpSheet->getComments()));
1554 $cellAddress = str_replace(
'$',
'',$cellAddress);
1555 $noteLength = self::_GetInt2d($recordData, 4);
1556 $noteText = trim(substr($recordData, 6));
1562 $comment = $this->_phpSheet->getComment( $cellAddress );
1563 $commentText =
$comment->getText()->getPlainText();
1567 $this->_phpSheet->getComment( $cellAddress )
1581 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1582 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1585 $this->_pos += 4 + $length;
1587 if ($this->_readDataOnly) {
1597 $grbitOpts = self::_GetInt2d($recordData, 0);
1598 $rot = self::_GetInt2d($recordData, 2);
1599 $cchText = self::_GetInt2d($recordData, 10);
1600 $cbRuns = self::_GetInt2d($recordData, 12);
1603 $this->_textObjects[$this->textObjRef] =
array(
1604 'text' => substr(
$text[
"recordData"],
$text[
"spliceOffsets"][0]+1,$cchText),
1605 'format' => substr(
$text[
"recordData"],
$text[
"spliceOffsets"][1],$cbRuns),
1606 'alignment' => $grbitOpts,
1621 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1622 $recordData = substr($this->_data, $this->_pos + 4, $length);
1625 $this->_pos += 4 + $length;
1628 $substreamType = self::_GetInt2d($recordData, 2);
1630 switch ($substreamType) {
1631 case self::XLS_WorkbookGlobals:
1632 $version = self::_GetInt2d($recordData, 0);
1639 case self::XLS_Worksheet:
1648 $code = self::_GetInt2d($this->_data, $this->_pos);
1650 }
while (
$code != self::XLS_Type_EOF && $this->_pos < $this->_dataSize);
1673 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1675 if ($length != 54) {
1679 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1682 $this->_pos += 4 + $length;
1686 substr($recordData, 6, 16),
1687 substr($recordData, 22, 16),
1688 substr($recordData, 38, 16),
1694 $this->_encryption = self::MS_BIFF_CRYPTO_RC4;
1697 $this->_encryptionStartPos = $this->_pos + self::_GetInt2d($this->_data, $this->_pos + 2);
1710 $pwarray = str_repeat(
"\0", 64);
1712 for ($i = 0; $i < 5; $i++) {
1713 $pwarray[$i] = $valContext[$i];
1716 $pwarray[5] = chr($block & 0xff);
1717 $pwarray[6] = chr(($block >> 8) & 0xff);
1718 $pwarray[7] = chr(($block >> 16) & 0xff);
1719 $pwarray[8] = chr(($block >> 24) & 0xff);
1721 $pwarray[9] =
"\x80";
1722 $pwarray[56] =
"\x48";
1725 $md5->add($pwarray);
1727 $s = $md5->getContext();
1742 private function _verifyPassword($password, $docid, $salt_data, $hashedsalt_data, &$valContext)
1744 $pwarray = str_repeat(
"\0", 64);
1746 for ($i = 0; $i < strlen($password); $i++) {
1747 $o = ord(substr($password, $i, 1));
1748 $pwarray[2 * $i] = chr($o & 0xff);
1749 $pwarray[2 * $i + 1] = chr(($o >> 8) & 0xff);
1751 $pwarray[2 * $i] = chr(0x80);
1752 $pwarray[56] = chr(($i << 4) & 0xff);
1755 $md5->add($pwarray);
1757 $mdContext1 = $md5->getContext();
1765 while ($offset != 16) {
1766 if ((64 - $offset) < 5) {
1767 $tocopy = 64 - $offset;
1770 for ($i = 0; $i <= $tocopy; $i++) {
1771 $pwarray[$offset + $i] = $mdContext1[$keyoffset + $i];
1776 if ($offset == 64) {
1777 $md5->add($pwarray);
1778 $keyoffset = $tocopy;
1779 $tocopy = 5 - $tocopy;
1786 for ($i = 0; $i < 16; $i++) {
1787 $pwarray[$offset + $i] = $docid[$i];
1792 $pwarray[16] =
"\x80";
1793 for ($i = 0; $i < 47; $i++) {
1794 $pwarray[17 + $i] =
"\0";
1796 $pwarray[56] =
"\x80";
1797 $pwarray[57] =
"\x0a";
1799 $md5->add($pwarray);
1800 $valContext = $md5->getContext();
1802 $key = $this->
_makeKey(0, $valContext);
1804 $salt = $key->RC4($salt_data);
1805 $hashedsalt = $key->RC4($hashedsalt_data);
1807 $salt .=
"\x80" . str_repeat(
"\0", 47);
1812 $mdContext2 = $md5->getContext();
1814 return $mdContext2 == $hashedsalt;
1828 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1829 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1832 $this->_pos += 4 + $length;
1835 $codepage = self::_GetInt2d($recordData, 0);
1855 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1856 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1859 $this->_pos += 4 + $length;
1863 if (ord($recordData{0}) == 1) {
1874 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1875 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1878 $this->_pos += 4 + $length;
1880 if (!$this->_readDataOnly) {
1884 $size = self::_GetInt2d($recordData, 0);
1885 $objFont->setSize(
$size / 20);
1890 $isItalic = (0x0002 & self::_GetInt2d($recordData, 2)) >> 1;
1891 if ($isItalic) $objFont->setItalic(
true);
1895 $isStrike = (0x0008 & self::_GetInt2d($recordData, 2)) >> 3;
1896 if ($isStrike) $objFont->setStrikethrough(
true);
1899 $colorIndex = self::_GetInt2d($recordData, 4);
1900 $objFont->colorIndex = $colorIndex;
1903 $weight = self::_GetInt2d($recordData, 6);
1906 $objFont->setBold(
true);
1911 $escapement = self::_GetInt2d($recordData, 8);
1912 switch ($escapement) {
1914 $objFont->setSuperScript(
true);
1917 $objFont->setSubScript(
true);
1922 $underlineType = ord($recordData{10});
1923 switch ($underlineType) {
1944 if ($this->_version == self::XLS_BIFF8) {
1945 $string = self::_readUnicodeStringShort(substr($recordData, 14));
1949 $objFont->setName($string[
'value']);
1951 $this->_objFonts[] = $objFont;
1972 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
1973 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
1976 $this->_pos += 4 + $length;
1978 if (!$this->_readDataOnly) {
1979 $indexCode = self::_GetInt2d($recordData, 0);
1981 if ($this->_version == self::XLS_BIFF8) {
1982 $string = self::_readUnicodeStringLong(substr($recordData, 2));
1988 $formatString = $string[
'value'];
1989 $this->_formats[$indexCode] = $formatString;
2010 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2011 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2014 $this->_pos += 4 + $length;
2018 if (!$this->_readDataOnly) {
2020 if (self::_GetInt2d($recordData, 0) < 4) {
2021 $fontIndex = self::_GetInt2d($recordData, 0);
2025 $fontIndex = self::_GetInt2d($recordData, 0) - 1;
2027 $objStyle->setFont($this->_objFonts[$fontIndex]);
2030 $numberFormatIndex = self::_GetInt2d($recordData, 2);
2031 if (isset($this->_formats[$numberFormatIndex])) {
2033 $numberformat =
array(
'code' => $this->_formats[$numberFormatIndex]);
2039 $numberformat =
array(
'code' =>
'General');
2041 $objStyle->getNumberFormat()->setFormatCode($numberformat[
'code']);
2045 $xfTypeProt = self::_GetInt2d($recordData, 4);
2047 $isLocked = (0x01 & $xfTypeProt) >> 0;
2048 $objStyle->getProtection()->setLocked($isLocked ?
2052 $isHidden = (0x02 & $xfTypeProt) >> 1;
2053 $objStyle->getProtection()->setHidden($isHidden ?
2057 $isCellStyleXf = (0x04 & $xfTypeProt) >> 2;
2061 $horAlign = (0x07 & ord($recordData{6})) >> 0;
2062 switch ($horAlign) {
2086 $wrapText = (0x08 & ord($recordData{6})) >> 3;
2087 switch ($wrapText) {
2089 $objStyle->getAlignment()->setWrapText(
false);
2092 $objStyle->getAlignment()->setWrapText(
true);
2096 $vertAlign = (0x70 & ord($recordData{6})) >> 4;
2097 switch ($vertAlign) {
2112 if ($this->_version == self::XLS_BIFF8) {
2114 $angle = ord($recordData{7});
2118 }
else if (
$angle <= 180) {
2120 }
else if (
$angle == 255) {
2123 $objStyle->getAlignment()->setTextRotation($rotation);
2127 $indent = (0x0F & ord($recordData{8})) >> 0;
2128 $objStyle->getAlignment()->setIndent($indent);
2131 $shrinkToFit = (0x10 & ord($recordData{8})) >> 4;
2132 switch ($shrinkToFit) {
2134 $objStyle->getAlignment()->setShrinkToFit(
false);
2137 $objStyle->getAlignment()->setShrinkToFit(
true);
2145 if ($bordersLeftStyle = self::_mapBorderStyle((0x0000000F & self::_GetInt4d($recordData, 10)) >> 0)) {
2146 $objStyle->getBorders()->getLeft()->setBorderStyle($bordersLeftStyle);
2149 if ($bordersRightStyle = self::_mapBorderStyle((0x000000F0 & self::_GetInt4d($recordData, 10)) >> 4)) {
2150 $objStyle->getBorders()->getRight()->setBorderStyle($bordersRightStyle);
2153 if ($bordersTopStyle = self::_mapBorderStyle((0x00000F00 & self::_GetInt4d($recordData, 10)) >> 8)) {
2154 $objStyle->getBorders()->getTop()->setBorderStyle($bordersTopStyle);
2157 if ($bordersBottomStyle = self::_mapBorderStyle((0x0000F000 & self::_GetInt4d($recordData, 10)) >> 12)) {
2158 $objStyle->getBorders()->getBottom()->setBorderStyle($bordersBottomStyle);
2161 $objStyle->getBorders()->getLeft()->colorIndex = (0x007F0000 & self::_GetInt4d($recordData, 10)) >> 16;
2164 $objStyle->getBorders()->getRight()->colorIndex = (0x3F800000 & self::_GetInt4d($recordData, 10)) >> 23;
2167 $diagonalDown = (0x40000000 & self::_GetInt4d($recordData, 10)) >> 30 ?
2171 $diagonalUp = (0x80000000 & self::_GetInt4d($recordData, 10)) >> 31 ?
2174 if ($diagonalUp ==
false && $diagonalDown ==
false) {
2176 } elseif ($diagonalUp ==
true && $diagonalDown ==
false) {
2178 } elseif ($diagonalUp ==
false && $diagonalDown ==
true) {
2180 } elseif ($diagonalUp ==
true && $diagonalDown ==
true) {
2186 $objStyle->getBorders()->getTop()->colorIndex = (0x0000007F & self::_GetInt4d($recordData, 14)) >> 0;
2189 $objStyle->getBorders()->getBottom()->colorIndex = (0x00003F80 & self::_GetInt4d($recordData, 14)) >> 7;
2192 $objStyle->getBorders()->getDiagonal()->colorIndex = (0x001FC000 & self::_GetInt4d($recordData, 14)) >> 14;
2195 if ($bordersDiagonalStyle = self::_mapBorderStyle((0x01E00000 & self::_GetInt4d($recordData, 14)) >> 21)) {
2196 $objStyle->getBorders()->getDiagonal()->setBorderStyle($bordersDiagonalStyle);
2200 if ($fillType = self::_mapFillPattern((0xFC000000 & self::_GetInt4d($recordData, 14)) >> 26)) {
2201 $objStyle->getFill()->setFillType($fillType);
2205 $objStyle->getFill()->startcolorIndex = (0x007F & self::_GetInt2d($recordData, 18)) >> 0;
2208 $objStyle->getFill()->endcolorIndex = (0x3F80 & self::_GetInt2d($recordData, 18)) >> 7;
2213 $orientationAndFlags = ord($recordData{7});
2216 $xfOrientation = (0x03 & $orientationAndFlags) >> 0;
2217 switch ($xfOrientation) {
2219 $objStyle->getAlignment()->setTextRotation(0);
2222 $objStyle->getAlignment()->setTextRotation(-165);
2225 $objStyle->getAlignment()->setTextRotation(90);
2228 $objStyle->getAlignment()->setTextRotation(-90);
2233 $borderAndBackground = self::_GetInt4d($recordData, 8);
2236 $objStyle->getFill()->startcolorIndex = (0x0000007F & $borderAndBackground) >> 0;
2239 $objStyle->getFill()->endcolorIndex = (0x00003F80 & $borderAndBackground) >> 7;
2242 $objStyle->getFill()->setFillType(self::_mapFillPattern((0x003F0000 & $borderAndBackground) >> 16));
2245 $objStyle->getBorders()->getBottom()->setBorderStyle(self::_mapBorderStyle((0x01C00000 & $borderAndBackground) >> 22));
2248 $objStyle->getBorders()->getBottom()->colorIndex = (0xFE000000 & $borderAndBackground) >> 25;
2251 $borderLines = self::_GetInt4d($recordData, 12);
2254 $objStyle->getBorders()->getTop()->setBorderStyle(self::_mapBorderStyle((0x00000007 & $borderLines) >> 0));
2257 $objStyle->getBorders()->getLeft()->setBorderStyle(self::_mapBorderStyle((0x00000038 & $borderLines) >> 3));
2260 $objStyle->getBorders()->getRight()->setBorderStyle(self::_mapBorderStyle((0x000001C0 & $borderLines) >> 6));
2263 $objStyle->getBorders()->getTop()->colorIndex = (0x0000FE00 & $borderLines) >> 9;
2266 $objStyle->getBorders()->getLeft()->colorIndex = (0x007F0000 & $borderLines) >> 16;
2269 $objStyle->getBorders()->getRight()->colorIndex = (0x3F800000 & $borderLines) >> 23;
2273 if ($isCellStyleXf) {
2275 if ($this->_xfIndex == 0) {
2276 $this->_phpExcel->addCellStyleXf($objStyle);
2281 $this->_phpExcel->addCellXf($objStyle);
2282 $this->_mapCellXfIndex[
$this->_xfIndex] = count($this->_phpExcel->getCellXfCollection()) - 1;
2296 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2297 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2300 $this->_pos += 4 + $length;
2302 if (!$this->_readDataOnly) {
2312 $ixfe = self::_GetInt2d($recordData, 14);
2317 $cexts = self::_GetInt2d($recordData, 18);
2321 while ($offset < $length) {
2323 $extType = self::_GetInt2d($recordData, $offset);
2326 $cb = self::_GetInt2d($recordData, $offset + 2);
2329 $extData = substr($recordData, $offset + 4, $cb);
2333 $xclfType = self::_GetInt2d($extData, 0);
2334 $xclrValue = substr($extData, 4, 4);
2336 if ($xclfType == 2) {
2337 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2340 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2341 $fill = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getFill();
2342 $fill->getStartColor()->setRGB($rgb);
2343 unset($fill->startcolorIndex);
2349 $xclfType = self::_GetInt2d($extData, 0);
2350 $xclrValue = substr($extData, 4, 4);
2352 if ($xclfType == 2) {
2353 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2356 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2357 $fill = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getFill();
2358 $fill->getEndColor()->setRGB($rgb);
2359 unset($fill->endcolorIndex);
2365 $xclfType = self::_GetInt2d($extData, 0);
2366 $xclrValue = substr($extData, 4, 4);
2368 if ($xclfType == 2) {
2369 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2372 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2373 $top = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getBorders()->getTop();
2374 $top->getColor()->setRGB($rgb);
2375 unset($top->colorIndex);
2381 $xclfType = self::_GetInt2d($extData, 0);
2382 $xclrValue = substr($extData, 4, 4);
2384 if ($xclfType == 2) {
2385 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2388 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2389 $bottom = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getBorders()->getBottom();
2390 $bottom->getColor()->setRGB($rgb);
2391 unset($bottom->colorIndex);
2397 $xclfType = self::_GetInt2d($extData, 0);
2398 $xclrValue = substr($extData, 4, 4);
2400 if ($xclfType == 2) {
2401 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2404 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2405 $left = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getBorders()->getLeft();
2406 $left->getColor()->setRGB($rgb);
2407 unset($left->colorIndex);
2413 $xclfType = self::_GetInt2d($extData, 0);
2414 $xclrValue = substr($extData, 4, 4);
2416 if ($xclfType == 2) {
2417 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2420 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2421 $right = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getBorders()->getRight();
2422 $right->getColor()->setRGB($rgb);
2423 unset($right->colorIndex);
2429 $xclfType = self::_GetInt2d($extData, 0);
2430 $xclrValue = substr($extData, 4, 4);
2432 if ($xclfType == 2) {
2433 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2436 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2437 $diagonal = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getBorders()->getDiagonal();
2438 $diagonal->getColor()->setRGB($rgb);
2439 unset($diagonal->colorIndex);
2445 $xclfType = self::_GetInt2d($extData, 0);
2446 $xclrValue = substr($extData, 4, 4);
2448 if ($xclfType == 2) {
2449 $rgb = sprintf(
'%02X%02X%02X', ord($xclrValue{0}), ord($xclrValue{1}), ord($xclrValue{2}));
2452 if ( isset($this->_mapCellXfIndex[$ixfe]) ) {
2453 $font = $this->_phpExcel->getCellXfByIndex($this->_mapCellXfIndex[$ixfe])->getFont();
2454 $font->getColor()->setRGB($rgb);
2455 unset($font->colorIndex);
2473 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2474 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2477 $this->_pos += 4 + $length;
2479 if (!$this->_readDataOnly) {
2481 $ixfe = self::_GetInt2d($recordData, 0);
2484 $xfIndex = (0x0FFF & $ixfe) >> 0;
2487 $isBuiltIn = (bool) ((0x8000 & $ixfe) >> 15);
2491 $builtInId = ord($recordData{2});
2493 switch ($builtInId) {
2514 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2515 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2518 $this->_pos += 4 + $length;
2520 if (!$this->_readDataOnly) {
2522 $nm = self::_GetInt2d($recordData, 0);
2525 for ($i = 0; $i < $nm; ++$i) {
2526 $rgb = substr($recordData, 2 + 4 * $i, 4);
2527 $this->_palette[] = self::_readRGB($rgb);
2547 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2548 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2552 $rec_offset = self::_GetInt4d($this->_data, $this->_pos + 4);
2555 $this->_pos += 4 + $length;
2558 switch (ord($recordData{4})) {
2566 $sheetType = ord($recordData{5});
2569 if ($this->_version == self::XLS_BIFF8) {
2570 $string = self::_readUnicodeStringShort(substr($recordData, 6));
2571 $rec_name = $string[
'value'];
2572 } elseif ($this->_version == self::XLS_BIFF7) {
2574 $rec_name = $string[
'value'];
2577 $this->_sheets[] =
array(
2578 'name' => $rec_name,
2579 'offset' => $rec_offset,
2580 'sheetState' => $sheetState,
2581 'sheetType' => $sheetType,
2591 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2592 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2595 $this->_pos += 4 + $length;
2601 if (strlen($recordData) > 4) {
2604 $nm = self::_GetInt2d($recordData, 0);
2608 $encodedUrlString = self::_readUnicodeStringLong(substr($recordData, 2));
2609 $offset += $encodedUrlString[
'size'];
2612 $externalSheetNames =
array();
2613 for ($i = 0; $i < $nm; ++$i) {
2614 $externalSheetNameString = self::_readUnicodeStringLong(substr($recordData, $offset));
2615 $externalSheetNames[] = $externalSheetNameString[
'value'];
2616 $offset += $externalSheetNameString[
'size'];
2620 $this->_externalBooks[] =
array(
2621 'type' =>
'external',
2622 'encodedUrl' => $encodedUrlString[
'value'],
2623 'externalSheetNames' => $externalSheetNames,
2626 } elseif (substr($recordData, 2, 2) == pack(
'CC', 0x01, 0x04)) {
2630 $this->_externalBooks[] =
array(
2631 'type' =>
'internal',
2633 } elseif (substr($recordData, 0, 4) == pack(
'vCC', 0x0001, 0x01, 0x3A)) {
2636 $this->_externalBooks[] =
array(
2637 'type' =>
'addInFunction',
2639 } elseif (substr($recordData, 0, 2) == pack(
'v', 0x0000)) {
2643 $this->_externalBooks[] =
array(
2644 'type' =>
'DDEorOLE',
2655 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2656 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2659 $this->_pos += 4 + $length;
2662 if ($this->_version == self::XLS_BIFF8) {
2664 $options = self::_GetInt2d($recordData, 0);
2671 $nameString = self::_readUnicodeStringShort(substr($recordData, 6));
2674 $offset = 6 + $nameString[
'size'];
2677 $this->_externalNames[] =
array(
2678 'name' => $nameString[
'value'],
2679 'formula' => $formula,
2690 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2691 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2694 $this->_pos += 4 + $length;
2697 if ($this->_version == self::XLS_BIFF8) {
2699 $nm = self::_GetInt2d($recordData, 0);
2700 for ($i = 0; $i < $nm; ++$i) {
2701 $this->_ref[] =
array(
2703 'externalBookIndex' => self::_GetInt2d($recordData, 2 + 6 * $i),
2705 'firstSheetIndex' => self::_GetInt2d($recordData, 4 + 6 * $i),
2707 'lastSheetIndex' => self::_GetInt2d($recordData, 6 + 6 * $i),
2727 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2728 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2731 $this->_pos += 4 + $length;
2733 if ($this->_version == self::XLS_BIFF8) {
2737 $opts = self::_GetInt2d($recordData, 0);
2740 $isBuiltInName = (0x0020 & $opts) >> 5;
2745 $nlen = ord($recordData{3});
2749 $flen = self::_GetInt2d($recordData, 4);
2752 $scope = self::_GetInt2d($recordData, 8);
2755 $string = self::_readUnicodeString(substr($recordData, 14), $nlen);
2758 $offset = 14 + $string[
'size'];
2759 $formulaStructure = pack(
'v', $flen) . substr($recordData, $offset);
2767 $this->_definedname[] =
array(
2768 'isBuiltInName' => $isBuiltInName,
2769 'name' => $string[
'value'],
2770 'formula' => $formula,
2782 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2786 $recordData = $splicedRecordData[
'recordData'];
2788 $this->_drawingGroupData .= $recordData;
2811 $recordData = $splicedRecordData[
'recordData'];
2812 $spliceOffsets = $splicedRecordData[
'spliceOffsets'];
2818 $nm = self::_GetInt4d($recordData, 4);
2822 for ($i = 0; $i < $nm; ++$i) {
2825 $numChars = self::_GetInt2d($recordData, $pos);
2829 $optionFlags = ord($recordData{$pos});
2833 $isCompressed = (($optionFlags & 0x01) == 0) ;
2836 $hasAsian = (($optionFlags & 0x04) != 0);
2839 $hasRichText = (($optionFlags & 0x08) != 0);
2843 $formattingRuns = self::_GetInt2d($recordData, $pos);
2849 $extendedRunLength = self::_GetInt4d($recordData, $pos);
2854 $len = ($isCompressed) ? $numChars : $numChars * 2;
2857 foreach ($spliceOffsets as $spliceOffset) {
2860 if ($pos <= $spliceOffset) {
2861 $limitpos = $spliceOffset;
2866 if ($pos + $len <= $limitpos) {
2869 $retstr = substr($recordData, $pos, $len);
2876 $retstr = substr($recordData, $pos, $limitpos - $pos);
2878 $bytesRead = $limitpos - $pos;
2881 $charsLeft = $numChars - (($isCompressed) ? $bytesRead : ($bytesRead / 2));
2886 while ($charsLeft > 0) {
2889 foreach ($spliceOffsets as $spliceOffset) {
2890 if ($pos < $spliceOffset) {
2891 $limitpos = $spliceOffset;
2898 $option = ord($recordData{$pos});
2901 if ($isCompressed && ($option == 0)) {
2904 $len = min($charsLeft, $limitpos - $pos);
2905 $retstr .= substr($recordData, $pos, $len);
2907 $isCompressed =
true;
2909 } elseif (!$isCompressed && ($option != 0)) {
2912 $len = min($charsLeft * 2, $limitpos - $pos);
2913 $retstr .= substr($recordData, $pos, $len);
2914 $charsLeft -= $len / 2;
2915 $isCompressed =
false;
2917 } elseif (!$isCompressed && ($option == 0)) {
2920 $len = min($charsLeft, $limitpos - $pos);
2921 for ($j = 0; $j < $len; ++$j) {
2922 $retstr .= $recordData{$pos + $j} . chr(0);
2925 $isCompressed =
false;
2931 for ($j = 0; $j < strlen($retstr); ++$j) {
2932 $newstr .= $retstr[$j] . chr(0);
2935 $len = min($charsLeft * 2, $limitpos - $pos);
2936 $retstr .= substr($recordData, $pos, $len);
2937 $charsLeft -= $len / 2;
2938 $isCompressed =
false;
2946 $retstr = self::_encodeUTF16($retstr, $isCompressed);
2952 for ($j = 0; $j < $formattingRuns; ++$j) {
2954 $charPos = self::_GetInt2d($recordData, $pos + $j * 4);
2957 $fontIndex = self::_GetInt2d($recordData, $pos + 2 + $j * 4);
2960 'charPos' => $charPos,
2961 'fontIndex' => $fontIndex,
2964 $pos += 4 * $formattingRuns;
2970 $pos += $extendedRunLength;
2974 $this->_sst[] =
array(
2976 'fmtRuns' => $fmtRuns,
2989 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
2990 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
2993 $this->_pos += 4 + $length;
2995 if ($this->_version == self::XLS_BIFF8 && !$this->_readDataOnly) {
2997 $printGridlines = (bool) self::_GetInt2d($recordData, 0);
2998 $this->_phpSheet->setPrintGridlines($printGridlines);
3008 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3009 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3012 $this->_pos += 4 + $length;
3016 $height = self::_GetInt2d($recordData, 2);
3017 $this->_phpSheet->getDefaultRowDimension()->setRowHeight($height / 20);
3026 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3027 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3030 $this->_pos += 4 + $length;
3035 $isSummaryBelow = (0x0040 & self::_GetInt2d($recordData, 0)) >> 6;
3036 $this->_phpSheet->setShowSummaryBelow($isSummaryBelow);
3039 $isSummaryRight = (0x0080 & self::_GetInt2d($recordData, 0)) >> 7;
3040 $this->_phpSheet->setShowSummaryRight($isSummaryRight);
3044 $this->_isFitToPages = (bool) ((0x0100 & self::_GetInt2d($recordData, 0)) >> 8);
3053 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3054 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3057 $this->_pos += 4 + $length;
3059 if ($this->_version == self::XLS_BIFF8 && !$this->_readDataOnly) {
3062 $nm = self::_GetInt2d($recordData, 0);
3065 for ($i = 0; $i < $nm; ++$i) {
3066 $r = self::_GetInt2d($recordData, 2 + 6 * $i);
3067 $cf = self::_GetInt2d($recordData, 2 + 6 * $i + 2);
3068 $cl = self::_GetInt2d($recordData, 2 + 6 * $i + 4);
3082 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3083 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3086 $this->_pos += 4 + $length;
3088 if ($this->_version == self::XLS_BIFF8 && !$this->_readDataOnly) {
3090 $nm = self::_GetInt2d($recordData, 0);
3093 for ($i = 0; $i < $nm; ++$i) {
3094 $c = self::_GetInt2d($recordData, 2 + 6 * $i);
3095 $rf = self::_GetInt2d($recordData, 2 + 6 * $i + 2);
3096 $rl = self::_GetInt2d($recordData, 2 + 6 * $i + 4);
3110 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3111 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3114 $this->_pos += 4 + $length;
3116 if (!$this->_readDataOnly) {
3120 if ($this->_version == self::XLS_BIFF8) {
3121 $string = self::_readUnicodeStringLong($recordData);
3126 $this->_phpSheet->getHeaderFooter()->setOddHeader($string[
'value']);
3127 $this->_phpSheet->getHeaderFooter()->setEvenHeader($string[
'value']);
3138 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3139 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3142 $this->_pos += 4 + $length;
3144 if (!$this->_readDataOnly) {
3148 if ($this->_version == self::XLS_BIFF8) {
3149 $string = self::_readUnicodeStringLong($recordData);
3153 $this->_phpSheet->getHeaderFooter()->setOddFooter($string[
'value']);
3154 $this->_phpSheet->getHeaderFooter()->setEvenFooter($string[
'value']);
3165 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3166 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3169 $this->_pos += 4 + $length;
3171 if (!$this->_readDataOnly) {
3173 $isHorizontalCentered = (bool) self::_GetInt2d($recordData, 0);
3175 $this->_phpSheet->getPageSetup()->setHorizontalCentered($isHorizontalCentered);
3185 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3186 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3189 $this->_pos += 4 + $length;
3191 if (!$this->_readDataOnly) {
3193 $isVerticalCentered = (bool) self::_GetInt2d($recordData, 0);
3195 $this->_phpSheet->getPageSetup()->setVerticalCentered($isVerticalCentered);
3205 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3206 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3209 $this->_pos += 4 + $length;
3211 if (!$this->_readDataOnly) {
3213 $this->_phpSheet->getPageMargins()->setLeft(self::_extractNumber($recordData));
3223 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3224 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3227 $this->_pos += 4 + $length;
3229 if (!$this->_readDataOnly) {
3231 $this->_phpSheet->getPageMargins()->setRight(self::_extractNumber($recordData));
3241 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3242 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3245 $this->_pos += 4 + $length;
3247 if (!$this->_readDataOnly) {
3249 $this->_phpSheet->getPageMargins()->setTop(self::_extractNumber($recordData));
3259 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3260 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3263 $this->_pos += 4 + $length;
3265 if (!$this->_readDataOnly) {
3267 $this->_phpSheet->getPageMargins()->setBottom(self::_extractNumber($recordData));
3277 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3278 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3281 $this->_pos += 4 + $length;
3283 if (!$this->_readDataOnly) {
3285 $paperSize = self::_GetInt2d($recordData, 0);
3288 $scale = self::_GetInt2d($recordData, 2);
3291 $fitToWidth = self::_GetInt2d($recordData, 6);
3294 $fitToHeight = self::_GetInt2d($recordData, 8);
3299 $isPortrait = (0x0002 & self::_GetInt2d($recordData, 10)) >> 1;
3303 $isNotInit = (0x0004 & self::_GetInt2d($recordData, 10)) >> 2;
3306 $this->_phpSheet->getPageSetup()->setPaperSize($paperSize);
3307 switch ($isPortrait) {
3312 $this->_phpSheet->getPageSetup()->setScale($scale,
false);
3313 $this->_phpSheet->getPageSetup()->setFitToPage((
bool) $this->_isFitToPages);
3314 $this->_phpSheet->getPageSetup()->setFitToWidth($fitToWidth,
false);
3315 $this->_phpSheet->getPageSetup()->setFitToHeight($fitToHeight,
false);
3319 $marginHeader = self::_extractNumber(substr($recordData, 16, 8));
3320 $this->_phpSheet->getPageMargins()->setHeader($marginHeader);
3323 $marginFooter = self::_extractNumber(substr($recordData, 24, 8));
3324 $this->_phpSheet->getPageMargins()->setFooter($marginFooter);
3335 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3336 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3339 $this->_pos += 4 + $length;
3341 if ($this->_readDataOnly) {
3348 $bool = (0x01 & self::_GetInt2d($recordData, 0)) >> 0;
3349 $this->_phpSheet->getProtection()->setSheet((
bool)$bool);
3358 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3359 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3362 $this->_pos += 4 + $length;
3364 if ($this->_readDataOnly) {
3371 $bool = (0x01 & self::_GetInt2d($recordData, 0)) >> 0;
3373 $this->_phpSheet->getProtection()->setScenarios((
bool)$bool);
3382 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3383 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3386 $this->_pos += 4 + $length;
3388 if ($this->_readDataOnly) {
3395 $bool = (0x01 & self::_GetInt2d($recordData, 0)) >> 0;
3397 $this->_phpSheet->getProtection()->setObjects((
bool)$bool);
3406 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3407 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3410 $this->_pos += 4 + $length;
3412 if (!$this->_readDataOnly) {
3414 $password = strtoupper(dechex(self::_GetInt2d($recordData, 0)));
3415 $this->_phpSheet->getProtection()->setPassword($password,
true);
3425 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3426 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3429 $this->_pos += 4 + $length;
3432 $width = self::_GetInt2d($recordData, 0);
3434 $this->_phpSheet->getDefaultColumnDimension()->setWidth($width);
3444 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3445 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3448 $this->_pos += 4 + $length;
3450 if (!$this->_readDataOnly) {
3452 $fc = self::_GetInt2d($recordData, 0);
3455 $lc = self::_GetInt2d($recordData, 2);
3458 $width = self::_GetInt2d($recordData, 4);
3461 $xfIndex = self::_GetInt2d($recordData, 6);
3466 $isHidden = (0x0001 & self::_GetInt2d($recordData, 8)) >> 0;
3469 $level = (0x0700 & self::_GetInt2d($recordData, 8)) >> 8;
3472 $isCollapsed = (0x1000 & self::_GetInt2d($recordData, 8)) >> 12;
3476 for ($i = $fc; $i <= $lc; ++$i) {
3477 if ($lc == 255 || $lc == 256) {
3478 $this->_phpSheet->getDefaultColumnDimension()->setWidth($width / 256);
3481 $this->_phpSheet->getColumnDimensionByColumn($i)->setWidth($width / 256);
3482 $this->_phpSheet->getColumnDimensionByColumn($i)->setVisible(!$isHidden);
3483 $this->_phpSheet->getColumnDimensionByColumn($i)->setOutlineLevel($level);
3484 $this->_phpSheet->getColumnDimensionByColumn($i)->setCollapsed($isCollapsed);
3485 $this->_phpSheet->getColumnDimensionByColumn($i)->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3503 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3504 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3507 $this->_pos += 4 + $length;
3509 if (!$this->_readDataOnly) {
3511 $r = self::_GetInt2d($recordData, 0);
3520 $height = (0x7FFF & self::_GetInt2d($recordData, 6)) >> 0;
3523 $useDefaultHeight = (0x8000 & self::_GetInt2d($recordData, 6)) >> 15;
3525 if (!$useDefaultHeight) {
3526 $this->_phpSheet->getRowDimension(
$r + 1)->setRowHeight($height / 20);
3536 $level = (0x00000007 & self::_GetInt4d($recordData, 12)) >> 0;
3537 $this->_phpSheet->getRowDimension(
$r + 1)->setOutlineLevel($level);
3540 $isCollapsed = (0x00000010 & self::_GetInt4d($recordData, 12)) >> 4;
3541 $this->_phpSheet->getRowDimension(
$r + 1)->setCollapsed($isCollapsed);
3544 $isHidden = (0x00000020 & self::_GetInt4d($recordData, 12)) >> 5;
3545 $this->_phpSheet->getRowDimension(
$r + 1)->setVisible(!$isHidden);
3548 $hasExplicitFormat = (0x00000080 & self::_GetInt4d($recordData, 12)) >> 7;
3551 $xfIndex = (0x0FFF0000 & self::_GetInt4d($recordData, 12)) >> 16;
3553 if ($hasExplicitFormat) {
3554 $this->_phpSheet->getRowDimension(
$r + 1)->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3573 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3574 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3577 $this->_pos += 4 + $length;
3580 $row = self::_GetInt2d($recordData, 0);
3583 $column = self::_GetInt2d($recordData, 2);
3589 $xfIndex = self::_GetInt2d($recordData, 4);
3592 $rknum = self::_GetInt4d($recordData, 6);
3593 $numValue = self::_GetIEEE754($rknum);
3595 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3596 if (!$this->_readDataOnly) {
3598 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3618 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3619 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3622 $this->_pos += 4 + $length;
3625 $row = self::_GetInt2d($recordData, 0);
3628 $column = self::_GetInt2d($recordData, 2);
3634 $xfIndex = self::_GetInt2d($recordData, 4);
3637 $index = self::_GetInt4d($recordData, 6);
3640 if (($fmtRuns = $this->_sst[$index][
'fmtRuns']) && !$this->_readDataOnly) {
3644 $sstCount = count($this->_sst[$index][
'fmtRuns']);
3645 for ($i = 0; $i <= $sstCount; ++$i) {
3646 if (isset($fmtRuns[$i])) {
3648 $charPos = $fmtRuns[$i][
'charPos'];
3658 if (isset($fmtRuns[$i - 1])) {
3659 if ($fmtRuns[$i - 1][
'fontIndex'] < 4) {
3660 $fontIndex = $fmtRuns[$i - 1][
'fontIndex'];
3664 $fontIndex = $fmtRuns[$i - 1][
'fontIndex'] - 1;
3666 $textRun->setFont(clone $this->_objFonts[$fontIndex]);
3671 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3674 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3678 if (!$this->_readDataOnly) {
3680 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3696 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3697 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3700 $this->_pos += 4 + $length;
3703 $row = self::_GetInt2d($recordData, 0);
3706 $colFirst = self::_GetInt2d($recordData, 2);
3709 $colLast = self::_GetInt2d($recordData, $length - 2);
3710 $columns = $colLast - $colFirst + 1;
3715 for ($i = 0; $i <
$columns; ++$i) {
3722 $xfIndex = self::_GetInt2d($recordData, $offset);
3725 $numValue = self::_GetIEEE754(self::_GetInt4d($recordData, $offset + 2));
3726 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3727 if (!$this->_readDataOnly) {
3729 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3751 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3752 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3755 $this->_pos += 4 + $length;
3758 $row = self::_GetInt2d($recordData, 0);
3761 $column = self::_GetInt2d($recordData, 2);
3767 $xfIndex = self::_GetInt2d($recordData, 4);
3769 $numValue = self::_extractNumber(substr($recordData, 6, 8));
3771 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3772 if (!$this->_readDataOnly) {
3774 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3793 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3794 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3797 $this->_pos += 4 + $length;
3800 $row = self::_GetInt2d($recordData, 0);
3803 $column = self::_GetInt2d($recordData, 2);
3807 $formulaStructure = substr($recordData, 20);
3810 $options = self::_GetInt2d($recordData, 14);
3815 $isPartOfSharedFormula = (bool) (0x0008 &
$options);
3821 $isPartOfSharedFormula = $isPartOfSharedFormula && ord($formulaStructure{2}) == 0x01;
3823 if ($isPartOfSharedFormula) {
3826 $baseRow = self::_GetInt2d($formulaStructure, 3);
3827 $baseCol = self::_GetInt2d($formulaStructure, 5);
3834 if ($isPartOfSharedFormula) {
3836 $this->_sharedFormulaParts[$columnString . (
$row + 1)] = $this->_baseCell;
3842 $xfIndex = self::_GetInt2d($recordData, 4);
3845 if ( (ord($recordData{6}) == 0)
3846 && (ord($recordData{12}) == 255)
3847 && (ord($recordData{13}) == 255) ) {
3853 $code = self::_GetInt2d($this->_data, $this->_pos);
3854 if (
$code == self::XLS_Type_SHAREDFMLA) {
3861 } elseif ((ord($recordData{6}) == 1)
3862 && (ord($recordData{12}) == 255)
3863 && (ord($recordData{13}) == 255)) {
3867 $value = (bool) ord($recordData{8});
3869 } elseif ((ord($recordData{6}) == 2)
3870 && (ord($recordData{12}) == 255)
3871 && (ord($recordData{13}) == 255)) {
3875 $value = self::_mapErrorCode(ord($recordData{8}));
3877 } elseif ((ord($recordData{6}) == 3)
3878 && (ord($recordData{12}) == 255)
3879 && (ord($recordData{13}) == 255)) {
3889 $value = self::_extractNumber(substr($recordData, 6, 8));
3893 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
3894 if (!$this->_readDataOnly) {
3896 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
3900 if (!$isPartOfSharedFormula) {
3904 if ($this->_version != self::XLS_BIFF8) {
3911 $cell->setValueExplicit($value, $dataType);
3914 if ($this->_version == self::XLS_BIFF8) {
3917 $cell->setValueExplicit($value, $dataType);
3922 $cell->setCalculatedValue($value);
3934 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3935 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3938 $this->_pos += 4 + $length;
3941 $cellRange = substr($recordData, 0, 6);
3947 $no = ord($recordData{7});
3950 $formula = substr($recordData, 8);
3953 $this->_sharedFormulas[$this->_baseCell] = $formula;
3967 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3968 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3971 $this->_pos += 4 + $length;
3973 if ($this->_version == self::XLS_BIFF8) {
3974 $string = self::_readUnicodeStringLong($recordData);
3975 $value = $string[
'value'];
3978 $value = $string[
'value'];
3995 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
3996 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
3999 $this->_pos += 4 + $length;
4002 $row = self::_GetInt2d($recordData, 0);
4005 $column = self::_GetInt2d($recordData, 2);
4011 $xfIndex = self::_GetInt2d($recordData, 4);
4014 $boolErr = ord($recordData{6});
4017 $isError = ord($recordData{7});
4019 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
4022 $value = (bool) $boolErr;
4029 $value = self::_mapErrorCode($boolErr);
4036 if (!$this->_readDataOnly) {
4038 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
4054 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4055 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4058 $this->_pos += 4 + $length;
4061 $row = self::_GetInt2d($recordData, 0);
4064 $fc = self::_GetInt2d($recordData, 2);
4068 if (!$this->_readDataOnly) {
4069 for ($i = 0; $i < $length / 2 - 3; ++$i) {
4074 $xfIndex = self::_GetInt2d($recordData, 4 + 2 * $i);
4075 $this->_phpSheet->getCell($columnString . (
$row + 1))->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
4096 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4097 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4100 $this->_pos += 4 + $length;
4103 $row = self::_GetInt2d($recordData, 0);
4106 $column = self::_GetInt2d($recordData, 2);
4112 $xfIndex = self::_GetInt2d($recordData, 4);
4116 if ($this->_version == self::XLS_BIFF8) {
4117 $string = self::_readUnicodeStringLong(substr($recordData, 6));
4118 $value = $string[
'value'];
4121 $value = $string[
'value'];
4123 $cell = $this->_phpSheet->getCell($columnString . (
$row + 1));
4126 if (!$this->_readDataOnly) {
4128 $cell->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
4139 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4140 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4143 $this->_pos += 4 + $length;
4146 $row = self::_GetInt2d($recordData, 0);
4149 $col = self::_GetInt2d($recordData, 2);
4155 $xfIndex = self::_GetInt2d($recordData, 4);
4158 if (!$this->_readDataOnly) {
4159 $this->_phpSheet->getCell($columnString . (
$row + 1))->setXfIndex($this->_mapCellXfIndex[$xfIndex]);
4171 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4175 $recordData = $splicedRecordData[
'recordData'];
4177 $this->_drawingData .= $recordData;
4186 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4187 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4190 $this->_pos += 4 + $length;
4192 if ($this->_readDataOnly || $this->_version != self::XLS_BIFF8) {
4205 $ftCmoType = self::_GetInt2d($recordData, 0);
4206 $cbCmoSize = self::_GetInt2d($recordData, 2);
4207 $otObjType = self::_GetInt2d($recordData, 4);
4208 $idObjID = self::_GetInt2d($recordData, 6);
4209 $grbitOpts = self::_GetInt2d($recordData, 6);
4211 $this->_objs[] =
array(
4212 'ftCmoType' => $ftCmoType,
4213 'cbCmoSize' => $cbCmoSize,
4214 'otObjType' => $otObjType,
4215 'idObjID' => $idObjID,
4216 'grbitOpts' => $grbitOpts
4218 $this->textObjRef = $idObjID;
4231 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4232 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4235 $this->_pos += 4 + $length;
4238 $options = self::_GetInt2d($recordData, 0);
4241 $firstVisibleRow = self::_GetInt2d($recordData, 2);
4244 $firstVisibleColumn = self::_GetInt2d($recordData, 4);
4245 if ($this->_version === self::XLS_BIFF8) {
4250 $zoomscaleInPageBreakPreview = self::_GetInt2d($recordData, 10);
4251 if ($zoomscaleInPageBreakPreview === 0) $zoomscaleInPageBreakPreview = 60;
4252 $zoomscaleInNormalView = self::_GetInt2d($recordData, 12);
4253 if ($zoomscaleInNormalView === 0) $zoomscaleInNormalView = 100;
4257 $showGridlines = (bool) ((0x0002 &
$options) >> 1);
4258 $this->_phpSheet->setShowGridlines($showGridlines);
4261 $showRowColHeaders = (bool) ((0x0004 & $options) >> 2);
4262 $this->_phpSheet->setShowRowColHeaders($showRowColHeaders);
4265 $this->_frozen = (bool) ((0x0008 & $options) >> 3);
4268 $this->_phpSheet->setRightToLeft((
bool)((0x0040 & $options) >> 6));
4271 $isActive = (bool) ((0x0400 & $options) >> 10);
4273 $this->_phpExcel->setActiveSheetIndex($this->_phpExcel->getIndex($this->_phpSheet));
4277 $isPageBreakPreview = (bool) ((0x0800 & $options) >> 11);
4285 $this->_phpSheet->getSheetView()->setView($view);
4286 if ($this->_version === self::XLS_BIFF8) {
4287 $zoomScale = $isPageBreakPreview? $zoomscaleInPageBreakPreview : $zoomscaleInNormalView;
4288 $this->_phpSheet->getSheetView()->setZoomScale($zoomScale);
4289 $this->_phpSheet->getSheetView()->setZoomScaleNormal($zoomscaleInNormalView);
4298 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4299 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4302 $this->_pos += 4 + $length;
4308 $rt = self::_GetInt2d($recordData, 0);
4311 $grbitFrt = self::_GetInt2d($recordData, 2);
4316 $wScalePLV = self::_GetInt2d($recordData, 12);
4318 $grbit = self::_GetInt2d($recordData, 14);
4321 $fPageLayoutView = $grbit & 0x01;
4322 $fRulerVisible = ($grbit >> 1) & 0x01;
4323 $fWhitespaceHidden = ($grbit >> 3) & 0x01;
4325 if ($fPageLayoutView === 1) {
4327 $this->_phpSheet->getSheetView()->setZoomScale($wScalePLV);
4337 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4338 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4341 $this->_pos += 4 + $length;
4344 $numerator = self::_GetInt2d($recordData, 0);
4347 $denumerator = self::_GetInt2d($recordData, 2);
4350 $this->_phpSheet->getSheetView()->setZoomScale($numerator * 100 / $denumerator);
4359 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4360 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4363 $this->_pos += 4 + $length;
4365 if (!$this->_readDataOnly) {
4367 $px = self::_GetInt2d($recordData, 0);
4370 $py = self::_GetInt2d($recordData, 2);
4372 if ($this->_frozen) {
4387 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4388 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4391 $this->_pos += 4 + $length;
4393 if (!$this->_readDataOnly) {
4395 $paneId = ord($recordData{0});
4398 $r = self::_GetInt2d($recordData, 1);
4401 $c = self::_GetInt2d($recordData, 3);
4405 $index = self::_GetInt2d($recordData, 5);
4408 $data = substr($recordData, 7);
4411 $selectedCells = $cellRangeAddressList[
'cellRangeAddresses'][0];
4414 if (preg_match(
'/^([A-Z]+1\:[A-Z]+)16384$/', $selectedCells)) {
4415 $selectedCells = preg_replace(
'/^([A-Z]+1\:[A-Z]+)16384$/',
'${1}1048576', $selectedCells);
4419 if (preg_match(
'/^([A-Z]+1\:[A-Z]+)65536$/', $selectedCells)) {
4420 $selectedCells = preg_replace(
'/^([A-Z]+1\:[A-Z]+)65536$/',
'${1}1048576', $selectedCells);
4424 if (preg_match(
'/^(A[0-9]+\:)IV([0-9]+)$/', $selectedCells)) {
4425 $selectedCells = preg_replace(
'/^(A[0-9]+\:)IV([0-9]+)$/',
'${1}XFD${2}', $selectedCells);
4428 $this->_phpSheet->setSelectedCells($selectedCells);
4435 $includeCellRange =
true;
4437 $includeCellRange =
false;
4439 $rangeBoundaries[1][0]++;
4440 for (
$row = $rangeBoundaries[0][1];
$row <= $rangeBoundaries[1][1];
$row++) {
4443 $includeCellRange =
true;
4449 return $includeCellRange;
4464 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4465 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4468 $this->_pos += 4 + $length;
4470 if ($this->_version == self::XLS_BIFF8 && !$this->_readDataOnly) {
4472 foreach ($cellRangeAddressList[
'cellRangeAddresses'] as $cellRangeAddress) {
4473 if ((strpos($cellRangeAddress,
':') !== FALSE) &&
4475 $this->_phpSheet->mergeCells($cellRangeAddress);
4487 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4488 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4491 $this->_pos += 4 + $length;
4493 if (!$this->_readDataOnly) {
4508 $isFileLinkOrUrl = (0x00000001 & self::_GetInt2d($recordData, 28)) >> 0;
4511 $isAbsPathOrUrl = (0x00000001 & self::_GetInt2d($recordData, 28)) >> 1;
4514 $hasDesc = (0x00000014 & self::_GetInt2d($recordData, 28)) >> 2;
4517 $hasText = (0x00000008 & self::_GetInt2d($recordData, 28)) >> 3;
4520 $hasFrame = (0x00000080 & self::_GetInt2d($recordData, 28)) >> 7;
4523 $isUNC = (0x00000100 & self::_GetInt2d($recordData, 28)) >> 8;
4530 $dl = self::_GetInt4d($recordData, 32);
4532 $desc = self::_encodeUTF16(substr($recordData, 36, 2 * ($dl - 1)),
false);
4533 $offset += 4 + 2 * $dl;
4536 $fl = self::_GetInt4d($recordData, $offset);
4537 $offset += 4 + 2 * $fl;
4541 $hyperlinkType = null;
4544 $hyperlinkType =
'UNC';
4545 }
else if (!$isFileLinkOrUrl) {
4546 $hyperlinkType =
'workbook';
4547 }
else if (ord($recordData{$offset}) == 0x03) {
4548 $hyperlinkType =
'local';
4549 }
else if (ord($recordData{$offset}) == 0xE0) {
4550 $hyperlinkType =
'URL';
4553 switch ($hyperlinkType) {
4561 $us = self::_GetInt4d($recordData, $offset);
4564 $url = self::_encodeUTF16(substr($recordData, $offset, $us - 2),
false);
4565 $nullOffset = strpos(
$url, 0x00);
4568 $url .= $hasText ?
'#' :
'';
4582 $upLevelCount = self::_GetInt2d($recordData, $offset);
4586 $sl = self::_GetInt4d($recordData, $offset);
4590 $shortenedFilePath = substr($recordData, $offset, $sl);
4591 $shortenedFilePath = self::_encodeUTF16($shortenedFilePath,
true);
4592 $shortenedFilePath = substr($shortenedFilePath, 0, -1);
4601 $sz = self::_GetInt4d($recordData, $offset);
4607 $xl = self::_GetInt4d($recordData, $offset);
4614 $extendedFilePath = substr($recordData, $offset, $xl);
4615 $extendedFilePath = self::_encodeUTF16($extendedFilePath,
false);
4620 $url = str_repeat(
'..\\', $upLevelCount);
4622 $extendedFilePath : $shortenedFilePath;
4623 $url .= $hasText ?
'#' :
'';
4646 $tl = self::_GetInt4d($recordData, $offset);
4649 $text = self::_encodeUTF16(substr($recordData, $offset, 2 * ($tl - 1)),
false);
4655 $this->_phpSheet->getCell($coordinate)->getHyperLink()->setUrl(
$url);
4666 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4667 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4670 $this->_pos += 4 + $length;
4679 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4680 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4683 $this->_pos += 4 + $length;
4685 if ($this->_readDataOnly) {
4690 $options = self::_GetInt4d($recordData, 0);
4693 $type = (0x0000000F &
$options) >> 0;
4706 $errorStyle = (0x00000070 &
$options) >> 4;
4707 switch ($errorStyle) {
4715 $explicitFormula = (0x00000080 &
$options) >> 7;
4718 $allowBlank = (0x00000100 &
$options) >> 8;
4721 $suppressDropDown = (0x00000200 &
$options) >> 9;
4724 $showInputMessage = (0x00040000 &
$options) >> 18;
4727 $showErrorMessage = (0x00080000 &
$options) >> 19;
4730 $operator = (0x00F00000 &
$options) >> 20;
4731 switch ($operator) {
4744 $string = self::_readUnicodeStringLong(substr($recordData, $offset));
4745 $promptTitle = $string[
'value'] !== chr(0) ?
4746 $string[
'value'] :
'';
4747 $offset += $string[
'size'];
4750 $string = self::_readUnicodeStringLong(substr($recordData, $offset));
4751 $errorTitle = $string[
'value'] !== chr(0) ?
4752 $string[
'value'] :
'';
4753 $offset += $string[
'size'];
4756 $string = self::_readUnicodeStringLong(substr($recordData, $offset));
4757 $prompt = $string[
'value'] !== chr(0) ?
4758 $string[
'value'] :
'';
4759 $offset += $string[
'size'];
4762 $string = self::_readUnicodeStringLong(substr($recordData, $offset));
4763 $error = $string[
'value'] !== chr(0) ?
4764 $string[
'value'] :
'';
4765 $offset += $string[
'size'];
4768 $sz1 = self::_GetInt2d($recordData, $offset);
4775 $formula1 = substr($recordData, $offset, $sz1);
4776 $formula1 = pack(
'v', $sz1) . $formula1;
4782 $formula1 = str_replace(chr(0),
',', $formula1);
4790 $sz2 = self::_GetInt2d($recordData, $offset);
4797 $formula2 = substr($recordData, $offset, $sz2);
4798 $formula2 = pack(
'v', $sz2) . $formula2;
4808 $cellRangeAddresses = $cellRangeAddressList[
'cellRangeAddresses'];
4810 foreach ($cellRangeAddresses as $cellRange) {
4811 $stRange = $this->_phpSheet->shrinkRangeToFit($cellRange);
4813 foreach ($stRange as $coordinate) {
4814 $objValidation = $this->_phpSheet->getCell($coordinate)->getDataValidation();
4839 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4840 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4843 $this->_pos += 4 + $length;
4848 if (!$this->_readDataOnly) {
4855 $sz = self::_GetInt4d($recordData, 12);
4860 $colorIndex = self::_GetInt2d($recordData, 16);
4861 $color = self::_readColor($colorIndex,$this->_palette,$this->_version);
4862 $this->_phpSheet->getTabColor()->setRGB($color[
'rgb']);
4879 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4880 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4883 $this->_pos += 4 + $length;
4885 if ($this->_readDataOnly) {
4896 $isf = self::_GetInt2d($recordData, 12);
4907 $options = self::_GetInt2d($recordData, 19);
4911 $this->_phpSheet->getProtection()->setObjects(!$bool);
4915 $this->_phpSheet->getProtection()->setScenarios(!$bool);
4919 $this->_phpSheet->getProtection()->setFormatCells(!$bool);
4923 $this->_phpSheet->getProtection()->setFormatColumns(!$bool);
4927 $this->_phpSheet->getProtection()->setFormatRows(!$bool);
4931 $this->_phpSheet->getProtection()->setInsertColumns(!$bool);
4935 $this->_phpSheet->getProtection()->setInsertRows(!$bool);
4939 $this->_phpSheet->getProtection()->setInsertHyperlinks(!$bool);
4943 $this->_phpSheet->getProtection()->setDeleteColumns(!$bool);
4947 $this->_phpSheet->getProtection()->setDeleteRows(!$bool);
4951 $this->_phpSheet->getProtection()->setSelectLockedCells(!$bool);
4955 $this->_phpSheet->getProtection()->setSort(!$bool);
4959 $this->_phpSheet->getProtection()->setAutoFilter(!$bool);
4963 $this->_phpSheet->getProtection()->setPivotTables(!$bool);
4967 $this->_phpSheet->getProtection()->setSelectUnlockedCells(!$bool);
4980 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
4981 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
4984 $this->_pos += 4 + $length;
4989 if (!$this->_readDataOnly) {
4993 $isf = self::_GetInt2d($recordData, 12);
5003 $cref = self::_GetInt2d($recordData, 19);
5009 $cellRanges =
array();
5010 for ($i = 0; $i < $cref; ++$i) {
5016 $cellRanges[] = $cellRange;
5021 $rgbFeat = substr($recordData, $offset);
5025 $wPassword = self::_GetInt4d($recordData, $offset);
5030 $this->_phpSheet->protectCells(implode(
' ', $cellRanges), strtoupper(dechex($wPassword)),
true);
5041 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
5045 $recordData = $splicedRecordData[
'recordData'];
5050 $cf = self::_GetInt2d($recordData, 0);
5053 $env = self::_GetInt2d($recordData, 2);
5056 $lcb = self::_GetInt4d($recordData, 4);
5059 $iData = substr($recordData, 8);
5066 $bcSize = self::_GetInt4d($iData, 0);
5070 $bcWidth = self::_GetInt2d($iData, 4);
5074 $bcHeight = self::_GetInt2d($iData, 6);
5076 $ih = imagecreatetruecolor($bcWidth, $bcHeight);
5081 $bcBitCount = self::_GetInt2d($iData, 10);
5084 $rgbString = substr($iData, 12);
5085 $rgbTriples =
array();
5086 while (strlen($rgbString) > 0) {
5087 $rgbTriples[] = unpack(
'Cb/Cg/Cr', $rgbString);
5088 $rgbString = substr($rgbString, 3);
5092 foreach ($rgbTriples as $i => $rgbTriple) {
5093 $color = imagecolorallocate($ih, $rgbTriple[
'r'], $rgbTriple[
'g'], $rgbTriple[
'b']);
5094 imagesetpixel($ih,
$x, $bcHeight - 1 -
$y, $color);
5095 $x = (
$x + 1) % $bcWidth;
5096 $y =
$y + floor((
$x + 1) / $bcWidth);
5102 $drawing->setWorksheet($this->_phpSheet);
5124 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
5125 $recordData = $this->
_readRecordData($this->_data, $this->_pos + 4, $length);
5129 if ($this->_drawingData ==
'') {
5131 $this->_pos += 4 + $length;
5139 $this->_pos += 4 + $length;
5150 $validSplitPoints =
array(0xF003, 0xF004, 0xF00D);
5152 $splitPoint = self::_GetInt2d($recordData, 2);
5153 if (in_array($splitPoint, $validSplitPoints)) {
5156 $this->_drawingData .= $splicedRecordData[
'recordData'];
5162 $this->_pos += 4 + $length;
5178 $spliceOffsets =
array();
5181 $spliceOffsets[0] = 0;
5187 $identifier = self::_GetInt2d($this->_data, $this->_pos);
5189 $length = self::_GetInt2d($this->_data, $this->_pos + 2);
5192 $spliceOffsets[$i] = $spliceOffsets[$i - 1] + $length;
5194 $this->_pos += 4 + $length;
5195 $nextIdentifier = self::_GetInt2d($this->_data, $this->_pos);
5197 while ($nextIdentifier == self::XLS_Type_CONTINUE);
5199 $splicedData =
array(
5200 'recordData' =>
$data,
5201 'spliceOffsets' => $spliceOffsets,
5204 return $splicedData;
5219 $sz = self::_GetInt2d($formulaStructure, 0);
5222 $formulaData = substr($formulaStructure, 2, $sz);
5232 if (strlen($formulaStructure) > 2 + $sz) {
5233 $additionalData = substr($formulaStructure, 2 + $sz);
5241 $additionalData =
'';
5261 while (strlen($formulaData) > 0
and $token = $this->
_getNextToken($formulaData, $baseCell)) {
5263 $formulaData = substr($formulaData, $token[
'size']);
5271 return $formulaString;
5286 if (empty($tokens)) {
5290 $formulaStrings =
array();
5291 foreach ($tokens as $token) {
5293 $space0 = isset($space0) ? $space0 :
'';
5294 $space1 = isset($space1) ? $space1 :
'';
5295 $space2 = isset($space2) ? $space2 :
'';
5296 $space3 = isset($space3) ? $space3 :
'';
5297 $space4 = isset($space4) ? $space4 :
'';
5298 $space5 = isset($space5) ? $space5 :
'';
5300 switch ($token[
'name']) {
5316 $op2 = array_pop($formulaStrings);
5317 $op1 = array_pop($formulaStrings);
5318 $formulaStrings[] =
"$op1$space1$space0{$token['data']}$op2";
5319 unset($space0, $space1);
5323 $op = array_pop($formulaStrings);
5324 $formulaStrings[] =
"$space1$space0{$token['data']}$op";
5325 unset($space0, $space1);
5328 $op = array_pop($formulaStrings);
5329 $formulaStrings[] =
"$op$space1$space0{$token['data']}";
5330 unset($space0, $space1);
5332 case 'tAttrVolatile':
5341 switch ($token[
'data'][
'spacetype']) {
5343 $space0 = str_repeat(
' ', $token[
'data'][
'spacecount']);
5346 $space1 = str_repeat(
"\n", $token[
'data'][
'spacecount']);
5349 $space2 = str_repeat(
' ', $token[
'data'][
'spacecount']);
5352 $space3 = str_repeat(
"\n", $token[
'data'][
'spacecount']);
5355 $space4 = str_repeat(
' ', $token[
'data'][
'spacecount']);
5358 $space5 = str_repeat(
"\n", $token[
'data'][
'spacecount']);
5363 $op = array_pop($formulaStrings);
5364 $formulaStrings[] =
"{$space1}{$space0}SUM($op)";
5365 unset($space0, $space1);
5369 if ($token[
'data'][
'function'] !=
'') {
5372 for ($i = 0; $i < $token[
'data'][
'args']; ++$i) {
5373 $ops[] = array_pop($formulaStrings);
5375 $ops = array_reverse($ops);
5376 $formulaStrings[] =
"$space1$space0{$token['data']['function']}(" . implode(
',', $ops) .
")";
5377 unset($space0, $space1);
5381 for ($i = 0; $i < $token[
'data'][
'args'] - 1; ++$i) {
5382 $ops[] = array_pop($formulaStrings);
5384 $ops = array_reverse($ops);
5385 $function = array_pop($formulaStrings);
5386 $formulaStrings[] =
"$space1$space0$function(" . implode(
',', $ops) .
")";
5387 unset($space0, $space1);
5391 $expression = array_pop($formulaStrings);
5392 $formulaStrings[] =
"$space3$space2($expression$space5$space4)";
5393 unset($space2, $space3, $space4, $space5);
5396 $constantArray = self::_readBIFF8ConstantArray($additionalData);
5397 $formulaStrings[] = $space1 . $space0 . $constantArray[
'value'];
5398 $additionalData = substr($additionalData, $constantArray[
'size']);
5399 unset($space0, $space1);
5404 $additionalData = substr($additionalData, $cellRangeAddressList[
'size']);
5405 $formulaStrings[] =
"$space1$space0{$token['data']}";
5406 unset($space0, $space1);
5424 $formulaStrings[] =
"$space1$space0{$token['data']}";
5425 unset($space0, $space1);
5429 $formulaString = $formulaStrings[0];
5435 return $formulaString;
5450 $id = ord($formulaData[0]);
5454 case 0x03: $name =
'tAdd';
$size = 1;
$data =
'+';
break;
5455 case 0x04: $name =
'tSub';
$size = 1;
$data =
'-';
break;
5456 case 0x05: $name =
'tMul';
$size = 1;
$data =
'*';
break;
5457 case 0x06: $name =
'tDiv';
$size = 1;
$data =
'/';
break;
5458 case 0x07: $name =
'tPower';
$size = 1;
$data =
'^';
break;
5459 case 0x08: $name =
'tConcat';
$size = 1;
$data =
'&';
break;
5460 case 0x09: $name =
'tLT';
$size = 1;
$data =
'<';
break;
5461 case 0x0A: $name =
'tLE';
$size = 1;
$data =
'<=';
break;
5462 case 0x0B: $name =
'tEQ';
$size = 1;
$data =
'=';
break;
5463 case 0x0C: $name =
'tGE';
$size = 1;
$data =
'>=';
break;
5464 case 0x0D: $name =
'tGT';
$size = 1;
$data =
'>';
break;
5465 case 0x0E: $name =
'tNE';
$size = 1;
$data =
'<>';
break;
5466 case 0x0F: $name =
'tIsect';
$size = 1;
$data =
' ';
break;
5467 case 0x10: $name =
'tList';
$size = 1;
$data =
',';
break;
5468 case 0x11: $name =
'tRange';
$size = 1;
$data =
':';
break;
5469 case 0x12: $name =
'tUplus';
$size = 1;
$data =
'+';
break;
5470 case 0x13: $name =
'tUminus';
$size = 1;
$data =
'-';
break;
5471 case 0x14: $name =
'tPercent';
$size = 1;
$data =
'%';
break;
5485 $string = self::_readUnicodeStringShort(substr($formulaData, 1));
5486 $size = 1 + $string[
'size'];
5487 $data = self::_UTF8toExcelDoubleQuoted($string[
'value']);
5491 switch (ord($formulaData[1])) {
5493 $name =
'tAttrVolatile';
5503 $name =
'tAttrChoose';
5505 $nc = self::_GetInt2d($formulaData, 2);
5508 $size = 2 * $nc + 6;
5512 $name =
'tAttrSkip';
5523 $name =
'tAttrSpace';
5526 switch (ord($formulaData[2])) {
5528 $spacetype =
'type0';
5531 $spacetype =
'type1';
5534 $spacetype =
'type2';
5537 $spacetype =
'type3';
5540 $spacetype =
'type4';
5543 $spacetype =
'type5';
5550 $spacecount = ord($formulaData[3]);
5552 $data =
array(
'spacetype' => $spacetype,
'spacecount' => $spacecount);
5563 $data = self::_mapErrorCode(ord($formulaData[1]));
5569 $data = ord($formulaData[1]) ?
'TRUE' :
'FALSE';
5575 $data = self::_GetInt2d($formulaData, 1);
5581 $data = self::_extractNumber(substr($formulaData, 1));
5582 $data = str_replace(
',',
'.', (
string)
$data);
5598 switch (self::_GetInt2d($formulaData, 1)) {
5599 case 2: $function =
'ISNA'; $args = 1;
break;
5600 case 3: $function =
'ISERROR'; $args = 1;
break;
5601 case 10: $function =
'NA'; $args = 0;
break;
5602 case 15: $function =
'SIN'; $args = 1;
break;
5603 case 16: $function =
'COS'; $args = 1;
break;
5604 case 17: $function =
'TAN'; $args = 1;
break;
5605 case 18: $function =
'ATAN'; $args = 1;
break;
5606 case 19: $function =
'PI'; $args = 0;
break;
5607 case 20: $function =
'SQRT'; $args = 1;
break;
5608 case 21: $function =
'EXP'; $args = 1;
break;
5609 case 22: $function =
'LN'; $args = 1;
break;
5610 case 23: $function =
'LOG10'; $args = 1;
break;
5611 case 24: $function =
'ABS'; $args = 1;
break;
5612 case 25: $function =
'INT'; $args = 1;
break;
5613 case 26: $function =
'SIGN'; $args = 1;
break;
5614 case 27: $function =
'ROUND'; $args = 2;
break;
5615 case 30: $function =
'REPT'; $args = 2;
break;
5616 case 31: $function =
'MID'; $args = 3;
break;
5617 case 32: $function =
'LEN'; $args = 1;
break;
5618 case 33: $function =
'VALUE'; $args = 1;
break;
5619 case 34: $function =
'TRUE'; $args = 0;
break;
5620 case 35: $function =
'FALSE'; $args = 0;
break;
5621 case 38: $function =
'NOT'; $args = 1;
break;
5622 case 39: $function =
'MOD'; $args = 2;
break;
5623 case 40: $function =
'DCOUNT'; $args = 3;
break;
5624 case 41: $function =
'DSUM'; $args = 3;
break;
5625 case 42: $function =
'DAVERAGE'; $args = 3;
break;
5626 case 43: $function =
'DMIN'; $args = 3;
break;
5627 case 44: $function =
'DMAX'; $args = 3;
break;
5628 case 45: $function =
'DSTDEV'; $args = 3;
break;
5629 case 48: $function =
'TEXT'; $args = 2;
break;
5630 case 61: $function =
'MIRR'; $args = 3;
break;
5631 case 63: $function =
'RAND'; $args = 0;
break;
5632 case 65: $function =
'DATE'; $args = 3;
break;
5633 case 66: $function =
'TIME'; $args = 3;
break;
5634 case 67: $function =
'DAY'; $args = 1;
break;
5635 case 68: $function =
'MONTH'; $args = 1;
break;
5636 case 69: $function =
'YEAR'; $args = 1;
break;
5637 case 71: $function =
'HOUR'; $args = 1;
break;
5638 case 72: $function =
'MINUTE'; $args = 1;
break;
5639 case 73: $function =
'SECOND'; $args = 1;
break;
5640 case 74: $function =
'NOW'; $args = 0;
break;
5641 case 75: $function =
'AREAS'; $args = 1;
break;
5642 case 76: $function =
'ROWS'; $args = 1;
break;
5643 case 77: $function =
'COLUMNS'; $args = 1;
break;
5644 case 83: $function =
'TRANSPOSE'; $args = 1;
break;
5645 case 86: $function =
'TYPE'; $args = 1;
break;
5646 case 97: $function =
'ATAN2'; $args = 2;
break;
5647 case 98: $function =
'ASIN'; $args = 1;
break;
5648 case 99: $function =
'ACOS'; $args = 1;
break;
5649 case 105: $function =
'ISREF'; $args = 1;
break;
5650 case 111: $function =
'CHAR'; $args = 1;
break;
5651 case 112: $function =
'LOWER'; $args = 1;
break;
5652 case 113: $function =
'UPPER'; $args = 1;
break;
5653 case 114: $function =
'PROPER'; $args = 1;
break;
5654 case 117: $function =
'EXACT'; $args = 2;
break;
5655 case 118: $function =
'TRIM'; $args = 1;
break;
5656 case 119: $function =
'REPLACE'; $args = 4;
break;
5657 case 121: $function =
'CODE'; $args = 1;
break;
5658 case 126: $function =
'ISERR'; $args = 1;
break;
5659 case 127: $function =
'ISTEXT'; $args = 1;
break;
5660 case 128: $function =
'ISNUMBER'; $args = 1;
break;
5661 case 129: $function =
'ISBLANK'; $args = 1;
break;
5662 case 130: $function =
'T'; $args = 1;
break;
5663 case 131: $function =
'N'; $args = 1;
break;
5664 case 140: $function =
'DATEVALUE'; $args = 1;
break;
5665 case 141: $function =
'TIMEVALUE'; $args = 1;
break;
5666 case 142: $function =
'SLN'; $args = 3;
break;
5667 case 143: $function =
'SYD'; $args = 4;
break;
5668 case 162: $function =
'CLEAN'; $args = 1;
break;
5669 case 163: $function =
'MDETERM'; $args = 1;
break;
5670 case 164: $function =
'MINVERSE'; $args = 1;
break;
5671 case 165: $function =
'MMULT'; $args = 2;
break;
5672 case 184: $function =
'FACT'; $args = 1;
break;
5673 case 189: $function =
'DPRODUCT'; $args = 3;
break;
5674 case 190: $function =
'ISNONTEXT'; $args = 1;
break;
5675 case 195: $function =
'DSTDEVP'; $args = 3;
break;
5676 case 196: $function =
'DVARP'; $args = 3;
break;
5677 case 198: $function =
'ISLOGICAL'; $args = 1;
break;
5678 case 199: $function =
'DCOUNTA'; $args = 3;
break;
5679 case 207: $function =
'REPLACEB'; $args = 4;
break;
5680 case 210: $function =
'MIDB'; $args = 3;
break;
5681 case 211: $function =
'LENB'; $args = 1;
break;
5682 case 212: $function =
'ROUNDUP'; $args = 2;
break;
5683 case 213: $function =
'ROUNDDOWN'; $args = 2;
break;
5684 case 214: $function =
'ASC'; $args = 1;
break;
5685 case 215: $function =
'DBCS'; $args = 1;
break;
5686 case 221: $function =
'TODAY'; $args = 0;
break;
5687 case 229: $function =
'SINH'; $args = 1;
break;
5688 case 230: $function =
'COSH'; $args = 1;
break;
5689 case 231: $function =
'TANH'; $args = 1;
break;
5690 case 232: $function =
'ASINH'; $args = 1;
break;
5691 case 233: $function =
'ACOSH'; $args = 1;
break;
5692 case 234: $function =
'ATANH'; $args = 1;
break;
5693 case 235: $function =
'DGET'; $args = 3;
break;
5694 case 244: $function =
'INFO'; $args = 1;
break;
5695 case 252: $function =
'FREQUENCY'; $args = 2;
break;
5696 case 261: $function =
'ERROR.TYPE'; $args = 1;
break;
5697 case 271: $function =
'GAMMALN'; $args = 1;
break;
5698 case 273: $function =
'BINOMDIST'; $args = 4;
break;
5699 case 274: $function =
'CHIDIST'; $args = 2;
break;
5700 case 275: $function =
'CHIINV'; $args = 2;
break;
5701 case 276: $function =
'COMBIN'; $args = 2;
break;
5702 case 277: $function =
'CONFIDENCE'; $args = 3;
break;
5703 case 278: $function =
'CRITBINOM'; $args = 3;
break;
5704 case 279: $function =
'EVEN'; $args = 1;
break;
5705 case 280: $function =
'EXPONDIST'; $args = 3;
break;
5706 case 281: $function =
'FDIST'; $args = 3;
break;
5707 case 282: $function =
'FINV'; $args = 3;
break;
5708 case 283: $function =
'FISHER'; $args = 1;
break;
5709 case 284: $function =
'FISHERINV'; $args = 1;
break;
5710 case 285: $function =
'FLOOR'; $args = 2;
break;
5711 case 286: $function =
'GAMMADIST'; $args = 4;
break;
5712 case 287: $function =
'GAMMAINV'; $args = 3;
break;
5713 case 288: $function =
'CEILING'; $args = 2;
break;
5714 case 289: $function =
'HYPGEOMDIST'; $args = 4;
break;
5715 case 290: $function =
'LOGNORMDIST'; $args = 3;
break;
5716 case 291: $function =
'LOGINV'; $args = 3;
break;
5717 case 292: $function =
'NEGBINOMDIST'; $args = 3;
break;
5718 case 293: $function =
'NORMDIST'; $args = 4;
break;
5719 case 294: $function =
'NORMSDIST'; $args = 1;
break;
5720 case 295: $function =
'NORMINV'; $args = 3;
break;
5721 case 296: $function =
'NORMSINV'; $args = 1;
break;
5722 case 297: $function =
'STANDARDIZE'; $args = 3;
break;
5723 case 298: $function =
'ODD'; $args = 1;
break;
5724 case 299: $function =
'PERMUT'; $args = 2;
break;
5725 case 300: $function =
'POISSON'; $args = 3;
break;
5726 case 301: $function =
'TDIST'; $args = 3;
break;
5727 case 302: $function =
'WEIBULL'; $args = 4;
break;
5728 case 303: $function =
'SUMXMY2'; $args = 2;
break;
5729 case 304: $function =
'SUMX2MY2'; $args = 2;
break;
5730 case 305: $function =
'SUMX2PY2'; $args = 2;
break;
5731 case 306: $function =
'CHITEST'; $args = 2;
break;
5732 case 307: $function =
'CORREL'; $args = 2;
break;
5733 case 308: $function =
'COVAR'; $args = 2;
break;
5734 case 309: $function =
'FORECAST'; $args = 3;
break;
5735 case 310: $function =
'FTEST'; $args = 2;
break;
5736 case 311: $function =
'INTERCEPT'; $args = 2;
break;
5737 case 312: $function =
'PEARSON'; $args = 2;
break;
5738 case 313: $function =
'RSQ'; $args = 2;
break;
5739 case 314: $function =
'STEYX'; $args = 2;
break;
5740 case 315: $function =
'SLOPE'; $args = 2;
break;
5741 case 316: $function =
'TTEST'; $args = 4;
break;
5742 case 325: $function =
'LARGE'; $args = 2;
break;
5743 case 326: $function =
'SMALL'; $args = 2;
break;
5744 case 327: $function =
'QUARTILE'; $args = 2;
break;
5745 case 328: $function =
'PERCENTILE'; $args = 2;
break;
5746 case 331: $function =
'TRIMMEAN'; $args = 2;
break;
5747 case 332: $function =
'TINV'; $args = 2;
break;
5748 case 337: $function =
'POWER'; $args = 2;
break;
5749 case 342: $function =
'RADIANS'; $args = 1;
break;
5750 case 343: $function =
'DEGREES'; $args = 1;
break;
5751 case 346: $function =
'COUNTIF'; $args = 2;
break;
5752 case 347: $function =
'COUNTBLANK'; $args = 1;
break;
5753 case 350: $function =
'ISPMT'; $args = 4;
break;
5754 case 351: $function =
'DATEDIF'; $args = 3;
break;
5755 case 352: $function =
'DATESTRING'; $args = 1;
break;
5756 case 353: $function =
'NUMBERSTRING'; $args = 2;
break;
5757 case 360: $function =
'PHONETIC'; $args = 1;
break;
5758 case 368: $function =
'BAHTTEXT'; $args = 1;
break;
5763 $data =
array(
'function' => $function,
'args' => $args);
5771 $args = ord($formulaData[1]);
5773 $index = self::_GetInt2d($formulaData, 2);
5775 case 0: $function =
'COUNT';
break;
5776 case 1: $function =
'IF';
break;
5777 case 4: $function =
'SUM';
break;
5778 case 5: $function =
'AVERAGE';
break;
5779 case 6: $function =
'MIN';
break;
5780 case 7: $function =
'MAX';
break;
5781 case 8: $function =
'ROW';
break;
5782 case 9: $function =
'COLUMN';
break;
5783 case 11: $function =
'NPV';
break;
5784 case 12: $function =
'STDEV';
break;
5785 case 13: $function =
'DOLLAR';
break;
5786 case 14: $function =
'FIXED';
break;
5787 case 28: $function =
'LOOKUP';
break;
5788 case 29: $function =
'INDEX';
break;
5789 case 36: $function =
'AND';
break;
5790 case 37: $function =
'OR';
break;
5791 case 46: $function =
'VAR';
break;
5792 case 49: $function =
'LINEST';
break;
5793 case 50: $function =
'TREND';
break;
5794 case 51: $function =
'LOGEST';
break;
5795 case 52: $function =
'GROWTH';
break;
5796 case 56: $function =
'PV';
break;
5797 case 57: $function =
'FV';
break;
5798 case 58: $function =
'NPER';
break;
5799 case 59: $function =
'PMT';
break;
5800 case 60: $function =
'RATE';
break;
5801 case 62: $function =
'IRR';
break;
5802 case 64: $function =
'MATCH';
break;
5803 case 70: $function =
'WEEKDAY';
break;
5804 case 78: $function =
'OFFSET';
break;
5805 case 82: $function =
'SEARCH';
break;
5806 case 100: $function =
'CHOOSE';
break;
5807 case 101: $function =
'HLOOKUP';
break;
5808 case 102: $function =
'VLOOKUP';
break;
5809 case 109: $function =
'LOG';
break;
5810 case 115: $function =
'LEFT';
break;
5811 case 116: $function =
'RIGHT';
break;
5812 case 120: $function =
'SUBSTITUTE';
break;
5813 case 124: $function =
'FIND';
break;
5814 case 125: $function =
'CELL';
break;
5815 case 144: $function =
'DDB';
break;
5816 case 148: $function =
'INDIRECT';
break;
5817 case 167: $function =
'IPMT';
break;
5818 case 168: $function =
'PPMT';
break;
5819 case 169: $function =
'COUNTA';
break;
5820 case 183: $function =
'PRODUCT';
break;
5821 case 193: $function =
'STDEVP';
break;
5822 case 194: $function =
'VARP';
break;
5823 case 197: $function =
'TRUNC';
break;
5824 case 204: $function =
'USDOLLAR';
break;
5825 case 205: $function =
'FINDB';
break;
5826 case 206: $function =
'SEARCHB';
break;
5827 case 208: $function =
'LEFTB';
break;
5828 case 209: $function =
'RIGHTB';
break;
5829 case 216: $function =
'RANK';
break;
5830 case 219: $function =
'ADDRESS';
break;
5831 case 220: $function =
'DAYS360';
break;
5832 case 222: $function =
'VDB';
break;
5833 case 227: $function =
'MEDIAN';
break;
5834 case 228: $function =
'SUMPRODUCT';
break;
5835 case 247: $function =
'DB';
break;
5836 case 255: $function =
'';
break;
5837 case 269: $function =
'AVEDEV';
break;
5838 case 270: $function =
'BETADIST';
break;
5839 case 272: $function =
'BETAINV';
break;
5840 case 317: $function =
'PROB';
break;
5841 case 318: $function =
'DEVSQ';
break;
5842 case 319: $function =
'GEOMEAN';
break;
5843 case 320: $function =
'HARMEAN';
break;
5844 case 321: $function =
'SUMSQ';
break;
5845 case 322: $function =
'KURT';
break;
5846 case 323: $function =
'SKEW';
break;
5847 case 324: $function =
'ZTEST';
break;
5848 case 329: $function =
'PERCENTRANK';
break;
5849 case 330: $function =
'MODE';
break;
5850 case 336: $function =
'CONCATENATE';
break;
5851 case 344: $function =
'SUBTOTAL';
break;
5852 case 345: $function =
'SUMIF';
break;
5853 case 354: $function =
'ROMAN';
break;
5854 case 358: $function =
'GETPIVOTDATA';
break;
5855 case 359: $function =
'HYPERLINK';
break;
5856 case 361: $function =
'AVERAGEA';
break;
5857 case 362: $function =
'MAXA';
break;
5858 case 363: $function =
'MINA';
break;
5859 case 364: $function =
'STDEVPA';
break;
5860 case 365: $function =
'VARPA';
break;
5861 case 366: $function =
'STDEVA';
break;
5862 case 367: $function =
'VARA';
break;
5867 $data =
array(
'function' => $function,
'args' => $args);
5875 $definedNameIndex = self::_GetInt2d($formulaData, 1) - 1;
5877 $data = $this->_definedname[$definedNameIndex][
'name'];
5899 $subSize = self::_GetInt2d($formulaData, 5);
5900 $size = 7 + $subSize;
5909 $subSize = self::_GetInt2d($formulaData, 5);
5910 $size = 7 + $subSize;
5918 $subSize = self::_GetInt2d($formulaData, 1);
5919 $size = 3 + $subSize;
5946 $index = self::_GetInt2d($formulaData, 3);
5948 $data = $this->_externalNames[$index - 1][
'name'];
5964 $data =
"$sheetRange!$cellAddress";
5983 $data =
"$sheetRange!$cellRangeAddress";
6015 $row = self::_GetInt2d($cellAddressStructure, 0) + 1;
6023 if (!(0x4000 & self::_GetInt2d($cellAddressStructure, 2))) {
6027 if (!(0x8000 & self::_GetInt2d($cellAddressStructure, 2))) {
6050 $rowIndex = self::_GetInt2d($cellAddressStructure, 0);
6051 $row = self::_GetInt2d($cellAddressStructure, 0) + 1;
6056 $colIndex = 0x00FF & self::_GetInt2d($cellAddressStructure, 2);
6059 if (!(0x4000 & self::_GetInt2d($cellAddressStructure, 2))) {
6063 $colIndex = ($colIndex <= 127) ? $colIndex : $colIndex - 256;
6068 if (!(0x8000 & self::_GetInt2d($cellAddressStructure, 2))) {
6071 $rowIndex = ($rowIndex <= 32767) ? $rowIndex : $rowIndex - 65536;
6091 $fr = self::_GetInt2d($subData, 0) + 1;
6094 $lr = self::_GetInt2d($subData, 2) + 1;
6097 $fc = ord($subData{4});
6100 $lc = ord($subData{5});
6103 if ($fr > $lr || $fc > $lc) {
6111 if ($fr == $lr
and $fc == $lc) {
6114 return "$fc$fr:$lc$lr";
6130 $fr = self::_GetInt2d($subData, 0) + 1;
6133 $lr = self::_GetInt2d($subData, 2) + 1;
6136 $fc = self::_GetInt2d($subData, 4);
6139 $lc = self::_GetInt2d($subData, 6);
6142 if ($fr > $lr || $fc > $lc) {
6150 if ($fr == $lr
and $fc == $lc) {
6153 return "$fc$fr:$lc$lr";
6171 $fr = self::_GetInt2d($subData, 0) + 1;
6174 $lr = self::_GetInt2d($subData, 2) + 1;
6182 if (!(0x4000 & self::_GetInt2d($subData, 4))) {
6187 if (!(0x8000 & self::_GetInt2d($subData, 4))) {
6197 if (!(0x4000 & self::_GetInt2d($subData, 6))) {
6202 if (!(0x8000 & self::_GetInt2d($subData, 6))) {
6206 return "$fc$fr:$lc$lr";
6228 $frIndex = self::_GetInt2d($subData, 0);
6231 $lrIndex = self::_GetInt2d($subData, 2);
6236 $fcIndex = 0x00FF & self::_GetInt2d($subData, 4);
6239 if (!(0x4000 & self::_GetInt2d($subData, 4))) {
6245 $fcIndex = ($fcIndex <= 127) ? $fcIndex : $fcIndex - 256;
6250 if (!(0x8000 & self::_GetInt2d($subData, 4))) {
6256 $frIndex = ($frIndex <= 32767) ? $frIndex : $frIndex - 65536;
6263 $lcIndex = 0x00FF & self::_GetInt2d($subData, 6);
6264 $lcIndex = ($lcIndex <= 127) ? $lcIndex : $lcIndex - 256;
6268 if (!(0x4000 & self::_GetInt2d($subData, 6))) {
6274 $lcIndex = ($lcIndex <= 127) ? $lcIndex : $lcIndex - 256;
6279 if (!(0x8000 & self::_GetInt2d($subData, 6))) {
6285 $lrIndex = ($lrIndex <= 32767) ? $lrIndex : $lrIndex - 65536;
6289 return "$fc$fr:$lc$lr";
6302 $cellRangeAddresses =
array();
6305 $nm = self::_GetInt2d($subData, 0);
6309 for ($i = 0; $i < $nm; ++$i) {
6315 'size' => 2 + 8 * $nm,
6316 'cellRangeAddresses' => $cellRangeAddresses,
6330 $cellRangeAddresses =
array();
6333 $nm = self::_GetInt2d($subData, 0);
6337 for ($i = 0; $i < $nm; ++$i) {
6343 'size' => 2 + 6 * $nm,
6344 'cellRangeAddresses' => $cellRangeAddresses,
6361 if (isset($this->_ref[$index])) {
6363 $type = $this->_externalBooks[$this->_ref[$index][
'externalBookIndex']][
'type'];
6368 if ($this->_ref[$index][
'firstSheetIndex'] == 0xFFFF
or $this->_ref[$index][
'lastSheetIndex'] == 0xFFFF) {
6373 $firstSheetName = $this->_sheets[$this->_ref[$index][
'firstSheetIndex']][
'name'];
6374 $lastSheetName = $this->_sheets[$this->_ref[$index][
'lastSheetIndex']][
'name'];
6376 if ($firstSheetName == $lastSheetName) {
6378 $sheetRange = $firstSheetName;
6380 $sheetRange =
"$firstSheetName:$lastSheetName";
6384 $sheetRange = str_replace(
"'",
"''", $sheetRange);
6390 if (preg_match(
"/[ !\"@#£$%&{()}<>=+'|^,;-]/", $sheetRange)) {
6391 $sheetRange =
"'$sheetRange'";
6418 $nc = ord($arrayData[0]);
6421 $nr = self::_GetInt2d($arrayData, 1);
6423 $arrayData = substr($arrayData, 3);
6426 $matrixChunks =
array();
6427 for (
$r = 1;
$r <= $nr + 1; ++
$r) {
6429 for ($c = 1; $c <= $nc + 1; ++$c) {
6430 $constant = self::_readBIFF8Constant($arrayData);
6431 $items[] = $constant[
'value'];
6432 $arrayData = substr($arrayData, $constant[
'size']);
6433 $size += $constant[
'size'];
6435 $matrixChunks[] = implode(
',', $items);
6437 $matrix =
'{' . implode(
';', $matrixChunks) .
'}';
6457 $identifier = ord($valueData[0]);
6459 switch ($identifier) {
6466 $value = self::_extractNumber(substr($valueData, 1, 8));
6471 $string = self::_readUnicodeStringLong(substr($valueData, 1));
6472 $value =
'"' . $string[
'value'] .
'"';
6473 $size = 1 + $string[
'size'];
6477 if (ord($valueData[1])) {
6486 $value = self::_mapErrorCode(ord($valueData[1]));
6516 $rgb = sprintf(
'%02X%02X%02X',
$r, $g, $b);
6518 return array(
'rgb' => $rgb);
6532 $ln = ord($subData[0]);
6554 $ln = self::_GetInt2d($subData, 0);
6580 $characterCount = ord($subData[0]);
6582 $string = self::_readUnicodeString(substr($subData, 1), $characterCount);
6585 $string[
'size'] += 1;
6604 $characterCount = self::_GetInt2d($subData, 0);
6606 $string = self::_readUnicodeString(substr($subData, 2), $characterCount);
6609 $string[
'size'] += 2;
6631 $isCompressed = !((0x01 & ord($subData[0])) >> 0);
6634 $hasAsian = (0x04) & ord($subData[0]) >> 2;
6637 $hasRichText = (0x08) & ord($subData[0]) >> 3;
6642 $value = self::_encodeUTF16(substr($subData, 1, $isCompressed ? $characterCount : 2 * $characterCount), $isCompressed);
6646 'size' => $isCompressed ? 1 + $characterCount : 1 + 2 * $characterCount,
6660 return '"' . str_replace(
'"',
'""', $value) .
'"';
6672 $rknumhigh = self::_GetInt4d(
$data, 4);
6673 $rknumlow = self::_GetInt4d(
$data, 0);
6674 $sign = ($rknumhigh & 0x80000000) >> 31;
6675 $exp = (($rknumhigh & 0x7ff00000) >> 20) - 1023;
6676 $mantissa = (0x100000 | ($rknumhigh & 0x000fffff));
6677 $mantissalow1 = ($rknumlow & 0x80000000) >> 31;
6678 $mantissalow2 = ($rknumlow & 0x7fffffff);
6679 $value = $mantissa / pow( 2 , (20 - $exp));
6681 if ($mantissalow1 != 0) {
6682 $value += 1 / pow (2 , (21 - $exp));
6685 $value += $mantissalow2 / pow (2 , (52 - $exp));
6696 if (($rknum & 0x02) != 0) {
6697 $value = $rknum >> 2;
6704 $sign = ($rknum & 0x80000000) >> 31;
6705 $exp = ($rknum & 0x7ff00000) >> 20;
6706 $mantissa = (0x100000 | ($rknum & 0x000ffffc));
6707 $value = $mantissa / pow( 2 , (20- ($exp - 1023)));
6709 $value = -1 * $value;
6713 if (($rknum & 0x01) != 0) {
6730 $string = self::_uncompressByteString($string);
6745 $uncompressedString =
'';
6746 $strLen = strlen($string);
6747 for ($i = 0; $i < $strLen; ++$i) {
6748 $uncompressedString .= $string[$i] .
"\0";
6751 return $uncompressedString;
6776 return ord(
$data[$pos]) | (ord(
$data[$pos+1]) << 8);
6792 $_or_24 = ord(
$data[$pos + 3]);
6793 if ($_or_24 >= 128) {
6795 $_ord_24 = -abs((256 - $_or_24) << 24);
6797 $_ord_24 = ($_or_24 & 127) << 24;
6799 return ord(
$data[$pos]) | (ord(
$data[$pos+1]) << 8) | (ord(
$data[$pos+2]) << 16) | $_ord_24;
6812 if ($color <= 0x07 || $color >= 0x40) {
6814 return self::_mapBuiltInColor($color);
6815 } elseif (isset($palette) && isset($palette[$color - 8])) {
6817 return $palette[$color - 8];
6821 return self::_mapColor($color);
6824 return self::_mapColorBIFF5($color);
6904 case 0x00:
return '#NULL!';
break;
6905 case 0x07:
return '#DIV/0!';
break;
6906 case 0x0F:
return '#VALUE!';
break;
6907 case 0x17:
return '#REF!';
break;
6908 case 0x1D:
return '#NAME?';
break;
6909 case 0x24:
return '#NUM!';
break;
6910 case 0x2A:
return '#N/A';
break;
6911 default:
return false;
6925 case 0x00:
return array(
'rgb' =>
'000000');
6926 case 0x01:
return array(
'rgb' =>
'FFFFFF');
6927 case 0x02:
return array(
'rgb' =>
'FF0000');
6928 case 0x03:
return array(
'rgb' =>
'00FF00');
6929 case 0x04:
return array(
'rgb' =>
'0000FF');
6930 case 0x05:
return array(
'rgb' =>
'FFFF00');
6931 case 0x06:
return array(
'rgb' =>
'FF00FF');
6932 case 0x07:
return array(
'rgb' =>
'00FFFF');
6933 case 0x40:
return array(
'rgb' =>
'000000');
6934 case 0x41:
return array(
'rgb' =>
'FFFFFF');
6935 default:
return array(
'rgb' =>
'000000');
6949 case 0x08:
return array(
'rgb' =>
'000000');
6950 case 0x09:
return array(
'rgb' =>
'FFFFFF');
6951 case 0x0A:
return array(
'rgb' =>
'FF0000');
6952 case 0x0B:
return array(
'rgb' =>
'00FF00');
6953 case 0x0C:
return array(
'rgb' =>
'0000FF');
6954 case 0x0D:
return array(
'rgb' =>
'FFFF00');
6955 case 0x0E:
return array(
'rgb' =>
'FF00FF');
6956 case 0x0F:
return array(
'rgb' =>
'00FFFF');
6957 case 0x10:
return array(
'rgb' =>
'800000');
6958 case 0x11:
return array(
'rgb' =>
'008000');
6959 case 0x12:
return array(
'rgb' =>
'000080');
6960 case 0x13:
return array(
'rgb' =>
'808000');
6961 case 0x14:
return array(
'rgb' =>
'800080');
6962 case 0x15:
return array(
'rgb' =>
'008080');
6963 case 0x16:
return array(
'rgb' =>
'C0C0C0');
6964 case 0x17:
return array(
'rgb' =>
'808080');
6965 case 0x18:
return array(
'rgb' =>
'8080FF');
6966 case 0x19:
return array(
'rgb' =>
'802060');
6967 case 0x1A:
return array(
'rgb' =>
'FFFFC0');
6968 case 0x1B:
return array(
'rgb' =>
'A0E0F0');
6969 case 0x1C:
return array(
'rgb' =>
'600080');
6970 case 0x1D:
return array(
'rgb' =>
'FF8080');
6971 case 0x1E:
return array(
'rgb' =>
'0080C0');
6972 case 0x1F:
return array(
'rgb' =>
'C0C0FF');
6973 case 0x20:
return array(
'rgb' =>
'000080');
6974 case 0x21:
return array(
'rgb' =>
'FF00FF');
6975 case 0x22:
return array(
'rgb' =>
'FFFF00');
6976 case 0x23:
return array(
'rgb' =>
'00FFFF');
6977 case 0x24:
return array(
'rgb' =>
'800080');
6978 case 0x25:
return array(
'rgb' =>
'800000');
6979 case 0x26:
return array(
'rgb' =>
'008080');
6980 case 0x27:
return array(
'rgb' =>
'0000FF');
6981 case 0x28:
return array(
'rgb' =>
'00CFFF');
6982 case 0x29:
return array(
'rgb' =>
'69FFFF');
6983 case 0x2A:
return array(
'rgb' =>
'E0FFE0');
6984 case 0x2B:
return array(
'rgb' =>
'FFFF80');
6985 case 0x2C:
return array(
'rgb' =>
'A6CAF0');
6986 case 0x2D:
return array(
'rgb' =>
'DD9CB3');
6987 case 0x2E:
return array(
'rgb' =>
'B38FEE');
6988 case 0x2F:
return array(
'rgb' =>
'E3E3E3');
6989 case 0x30:
return array(
'rgb' =>
'2A6FF9');
6990 case 0x31:
return array(
'rgb' =>
'3FB8CD');
6991 case 0x32:
return array(
'rgb' =>
'488436');
6992 case 0x33:
return array(
'rgb' =>
'958C41');
6993 case 0x34:
return array(
'rgb' =>
'8E5E42');
6994 case 0x35:
return array(
'rgb' =>
'A0627A');
6995 case 0x36:
return array(
'rgb' =>
'624FAC');
6996 case 0x37:
return array(
'rgb' =>
'969696');
6997 case 0x38:
return array(
'rgb' =>
'1D2FBE');
6998 case 0x39:
return array(
'rgb' =>
'286676');
6999 case 0x3A:
return array(
'rgb' =>
'004500');
7000 case 0x3B:
return array(
'rgb' =>
'453E01');
7001 case 0x3C:
return array(
'rgb' =>
'6A2813');
7002 case 0x3D:
return array(
'rgb' =>
'85396A');
7003 case 0x3E:
return array(
'rgb' =>
'4A3285');
7004 case 0x3F:
return array(
'rgb' =>
'424242');
7005 default:
return array(
'rgb' =>
'000000');
7019 case 0x08:
return array(
'rgb' =>
'000000');
7020 case 0x09:
return array(
'rgb' =>
'FFFFFF');
7021 case 0x0A:
return array(
'rgb' =>
'FF0000');
7022 case 0x0B:
return array(
'rgb' =>
'00FF00');
7023 case 0x0C:
return array(
'rgb' =>
'0000FF');
7024 case 0x0D:
return array(
'rgb' =>
'FFFF00');
7025 case 0x0E:
return array(
'rgb' =>
'FF00FF');
7026 case 0x0F:
return array(
'rgb' =>
'00FFFF');
7027 case 0x10:
return array(
'rgb' =>
'800000');
7028 case 0x11:
return array(
'rgb' =>
'008000');
7029 case 0x12:
return array(
'rgb' =>
'000080');
7030 case 0x13:
return array(
'rgb' =>
'808000');
7031 case 0x14:
return array(
'rgb' =>
'800080');
7032 case 0x15:
return array(
'rgb' =>
'008080');
7033 case 0x16:
return array(
'rgb' =>
'C0C0C0');
7034 case 0x17:
return array(
'rgb' =>
'808080');
7035 case 0x18:
return array(
'rgb' =>
'9999FF');
7036 case 0x19:
return array(
'rgb' =>
'993366');
7037 case 0x1A:
return array(
'rgb' =>
'FFFFCC');
7038 case 0x1B:
return array(
'rgb' =>
'CCFFFF');
7039 case 0x1C:
return array(
'rgb' =>
'660066');
7040 case 0x1D:
return array(
'rgb' =>
'FF8080');
7041 case 0x1E:
return array(
'rgb' =>
'0066CC');
7042 case 0x1F:
return array(
'rgb' =>
'CCCCFF');
7043 case 0x20:
return array(
'rgb' =>
'000080');
7044 case 0x21:
return array(
'rgb' =>
'FF00FF');
7045 case 0x22:
return array(
'rgb' =>
'FFFF00');
7046 case 0x23:
return array(
'rgb' =>
'00FFFF');
7047 case 0x24:
return array(
'rgb' =>
'800080');
7048 case 0x25:
return array(
'rgb' =>
'800000');
7049 case 0x26:
return array(
'rgb' =>
'008080');
7050 case 0x27:
return array(
'rgb' =>
'0000FF');
7051 case 0x28:
return array(
'rgb' =>
'00CCFF');
7052 case 0x29:
return array(
'rgb' =>
'CCFFFF');
7053 case 0x2A:
return array(
'rgb' =>
'CCFFCC');
7054 case 0x2B:
return array(
'rgb' =>
'FFFF99');
7055 case 0x2C:
return array(
'rgb' =>
'99CCFF');
7056 case 0x2D:
return array(
'rgb' =>
'FF99CC');
7057 case 0x2E:
return array(
'rgb' =>
'CC99FF');
7058 case 0x2F:
return array(
'rgb' =>
'FFCC99');
7059 case 0x30:
return array(
'rgb' =>
'3366FF');
7060 case 0x31:
return array(
'rgb' =>
'33CCCC');
7061 case 0x32:
return array(
'rgb' =>
'99CC00');
7062 case 0x33:
return array(
'rgb' =>
'FFCC00');
7063 case 0x34:
return array(
'rgb' =>
'FF9900');
7064 case 0x35:
return array(
'rgb' =>
'FF6600');
7065 case 0x36:
return array(
'rgb' =>
'666699');
7066 case 0x37:
return array(
'rgb' =>
'969696');
7067 case 0x38:
return array(
'rgb' =>
'003366');
7068 case 0x39:
return array(
'rgb' =>
'339966');
7069 case 0x3A:
return array(
'rgb' =>
'003300');
7070 case 0x3B:
return array(
'rgb' =>
'333300');
7071 case 0x3C:
return array(
'rgb' =>
'993300');
7072 case 0x3D:
return array(
'rgb' =>
'993366');
7073 case 0x3E:
return array(
'rgb' =>
'333399');
7074 case 0x3F:
return array(
'rgb' =>
'333333');
7075 default:
return array(
'rgb' =>
'000000');
7083 $value->createText($is);
_readImData()
Read IMDATA record.
const FILL_PATTERN_LIGHTHORIZONTAL
_readFont()
Read a FONT record.
_readExternalBook()
Read EXTERNALBOOK record.
static _readRGB($rgb)
Extract RGB color OpenOffice.org's Documentation of the Microsoft Excel File Format, section 2.5.4.
_readBoolErr()
Read BOOLERR record This record represents a Boolean value or error value cell.
static _readBIFF8Constant($valueData)
read BIFF8 constant value which may be 'Empty Value', 'Number', 'String Value', 'Boolean Value'...
_readByteStringShort($subData)
Read byte string (8-bit string length) OpenOffice documentation: 2.5.2.
_readWindow2()
Read WINDOW2 record.
const FILL_PATTERN_LIGHTGRAY
_readBIFF8CellRangeAddress($subData)
Reads a cell range address in BIFF8 e.g.
static getDistanceX(PHPExcel_Worksheet $sheet, $startColumn='A', $startOffsetX=0, $endColumn='A', $endOffsetX=0)
Get the horizontal distance in pixels between two anchors The distanceX is found as sum of all the sp...
static coordinateFromString($pCoordinateString='A1')
Coordinate from string.
_readSst()
SST - Shared String Table.
const FILL_PATTERN_DARKGRID
static _mapBorderStyle($index)
Map border style OpenOffice documentation: 2.5.11.
_readFormula()
Read FORMULA record + perhaps a following STRING record if formula result is a string This record con...
_readFooter()
Read FOOTER record.
const FILL_PATTERN_DARKHORIZONTAL
canRead($pFilename)
Can the current PHPExcel_Reader_IReader read the file?
static _readUnicodeStringShort($subData)
Extracts an Excel Unicode short string (8-bit string length) OpenOffice documentation: 2...
_readProtect()
PROTECT - Sheet protection (BIFF2 through BIFF8) if this record is omitted, then it also means no she...
_readSharedFmla()
Read a SHAREDFMLA record.
static ConvertEncoding($value, $to, $from)
Convert string from one encoding to another.
static _mapBuiltInColor($color)
Map built-in color to RGB value.
_readPane()
Read PANE record.
_readLabelSst()
Read LABELSST record This record represents a cell that contains a string.
const BORDER_MEDIUMDASHDOT
static _readUnicodeStringLong($subData)
Extracts an Excel Unicode long string (16-bit string length) OpenOffice documentation: 2...
_createFormulaFromTokens($tokens, $additionalData)
Take array of tokens together with additional data for formula and return human readable formula...
__construct()
Create a new PHPExcel_Reader_Excel5 instance.
_readBIFF8CellRangeAddressFixed($subData)
Reads a cell range address in BIFF8 e.g.
const XLS_Type_DATAVALIDATIONS
const XLS_Type_PAGELAYOUTVIEW
static setExcelCalendar($baseDate)
Set the Excel calendar (Windows 1900 or Mac 1904)
_readHeader()
Read HEADER record.
_getSplicedRecordData()
Reads a record from current position in data stream and continues reading data as long as CONTINUE re...
_readExternName()
Read EXTERNNAME record.
_readExternSheet()
Read EXTERNSHEET record.
listWorksheetNames($pFilename)
Reads names of the worksheets from a file, without parsing the whole file to a PHPExcel object...
const SHEETSTATE_VERYHIDDEN
const XLS_Type_EXTERNSHEET
_getNextToken($formulaData, $baseCell='A1')
Fetch next token from binary formula data.
_includeCellRangeFiltered($cellRangeAddress)
_readBIFF8CellAddress($cellAddressStructure)
Reads a cell address in BIFF8 e.g.
static _readUnicodeString($subData, $characterCount)
Read Unicode string with no string length field, but with known character count this function is unde...
const XLS_Type_DEFCOLWIDTH
_readBlank()
Read BLANK record.
_readBIFF8CellRangeAddressB($subData, $baseCell='A1')
Reads a cell range address in BIFF8 for shared formulas.
_makeKey($block, $valContext)
static _mapFillPattern($index)
Get fill pattern from index OpenOffice documentation: 2.5.12.
_readHorizontalPageBreaks()
Read HORIZONTALPAGEBREAKS record.
static _mapErrorCode($subData)
Map error code, e.g.
_getFormulaFromData($formulaData, $additionalData='', $baseCell='A1')
Take formula data and additional data for formula and return human readable formula.
const XLS_Type_DEFINEDNAME
_decodeCodepage($string)
Convert string to UTF-8.
const XLS_Type_MSODRAWING
_readHcenter()
Read HCENTER record.
_readSheetRangeByRefIndex($index)
Get a sheet range like Sheet1:Sheet3 from REF index Note: If there is only one sheet in the range...
const XLS_Type_SHAREDFMLA
_readXf()
XF - Extended Format.
const XLS_Type_EXTERNNAME
const FILL_PATTERN_LIGHTTRELLIS
const XLS_Type_BOTTOMMARGIN
static _readBIFF8ConstantArray($arrayData)
read BIFF8 constant value array from array data returns e.g.
_readColInfo()
Read COLINFO record.
const XLS_Type_PRINTGRIDLINES
static sizeCol($sheet, $col='A')
Get the width of a column in pixels.
_readObj()
Read OBJ record.
const XLS_Type_OBJECTPROTECT
const PROTECTION_UNPROTECTED
static _mapColorBIFF5($subData)
Map color array from BIFF5 built-in color index.
_readBIFF8CellAddressB($cellAddressStructure, $baseCell='A1')
Reads a cell address in BIFF8 for shared formulas.
_readDefaultRowHeight()
Read DEFAULTROWHEIGHT record.
const ORIENTATION_LANDSCAPE
_readScenProtect()
SCENPROTECT.
const XLS_Type_RANGEPROTECTION
_readContinue()
Read a free CONTINUE record.
const XLS_Type_HORIZONTALPAGEBREAKS
_readDefColWidth()
Read DEFCOLWIDTH record.
const XLS_Type_SCENPROTECT
const XLS_Type_LEFTMARGIN
const OPERATOR_GREATERTHAN
if(!is_array($argv)) $options
_readNumber()
Read NUMBER record This record represents a cell that contains a floating-point value.
const UNDERLINE_DOUBLEACCOUNTING
const HORIZONTAL_CENTER_CONTINUOUS
const FILL_PATTERN_LIGHTDOWN
const OPERATOR_NOTBETWEEN
_readVcenter()
Read VCENTER record.
const FILL_PATTERN_MEDIUMGRAY
_readStyle()
Read STYLE record.
const XLS_Type_VERTICALPAGEBREAKS
static _GetInt2d($data, $pos)
Read 16-bit unsigned integer.
const XLS_Type_DATAVALIDATION
const PROTECTION_INHERIT
Protection styles.
_readVerticalPageBreaks()
Read VERTICALPAGEBREAKS record.
const XLS_Type_SHEETPROTECTION
foreach( $_REQUEST as $var) foreach(array('_POST'=> 'HTTP_POST_VARS', '_GET'=> 'HTTP_GET_VARS', '_COOKIE'=> 'HTTP_COOKIE_VARS', '_SERVER'=> 'HTTP_SERVER_VARS', '_ENV'=> 'HTTP_ENV_VARS', '_FILES'=> 'HTTP_POST_FILES') as $array=> $other) $step
_readPrintGridlines()
Read PRINTGRIDLINES record.
_readDefault()
Reads a general type of BIFF record.
const FILL_PATTERN_DARKDOWN
const MS_BIFF_CRYPTO_NONE
_readBIFF5CellRangeAddressFixed($subData)
Reads a cell range address in BIFF5 e.g.
_readPageSetup()
Read PAGESETUP record.
static _mapColor($subData)
Map color array from BIFF8 built-in color index.
_readRightMargin()
Read RIGHTMARGIN record.
static OLE2LocalDate($string)
Returns a timestamp from an OLE container's date.
const FILL_PATTERN_GRAY125
const FILL_PATTERN_DARKTRELLIS
_loadOLE($pFilename)
Use OLE reader to extract the relevant data streams from the OLE file.
_getFormulaFromStructure($formulaStructure, $baseCell='A1')
Convert formula structure into human readable Excel formula like 'A3+A5*5'.
const FILL_PATTERN_LIGHTVERTICAL
_readSheetProtection()
Read SHEETPROTECTION record (FEATHEADR)
const UNDERLINE_SINGLEACCOUNTING
const BORDER_MEDIUMDASHDOTDOT
_readString()
Read a STRING record from current stream position and advance the stream pointer to next record This ...
_readPageLayoutView()
Read PLV Record(Created by Excel2007 or upper)
Create styles array
The data for the language used.
const SHEETVIEW_PAGE_LAYOUT
_readLabel()
Read LABEL record This record represents a cell that contains a string.
_readPalette()
Read PALETTE record.
_readHyperLink()
Read HYPERLINK record.
static sizeRow($sheet, $row=1)
Convert the height of a cell from user's units to pixels.
_readTextObject()
The TEXT Object record contains the text associated with a cell annotation.
static Substring($pValue='', $pStart=0, $pLength=0)
Get a substring of a UTF-8 encoded string.
listWorksheetInfo($pFilename)
Return worksheet info (Name, Last Column Letter, Last Column Index, Total Rows, Total Columns) ...
const PROTECTION_PROTECTED
const FILL_PATTERN_GRAY0625
_readRk()
Read RK record This record represents a cell that contains an RK value (encoded integer or floating-p...
_readBottomMargin()
Read BOTTOMMARGIN record.
getReadFilter()
Read filter.
static _extractNumber($data)
Reads first 8 bytes of a string and return IEEE 754 float.
_readSheetLayout()
Read SHEETLAYOUT record.
const XLS_Type_SHEETLAYOUT
const FILL_PATTERN_LIGHTGRID
static extractAllCellReferencesInRange($pRange='A1')
Extract all cell references in range.
static columnIndexFromString($pString='A')
Column index from string.
const OPERATOR_GREATERTHANOREQUAL
_verifyPassword($password, $docid, $salt_data, $hashedsalt_data, &$valContext)
static getRangeBoundaries($pRange='A1:A1')
Calculate range boundaries.
const XLS_Type_MERGEDCELLS
const XLS_Type_RIGHTMARGIN
const BORDER_SLANTDASHDOT
const OPERATOR_LESSTHANOREQUAL
static _UTF8toExcelDoubleQuoted($value)
Convert UTF-8 string to string surounded by double quotes.
load($pFilename)
Loads PHPExcel from file.
const FILL_PATTERN_DARKVERTICAL
const SHEETVIEW_PAGE_BREAK_PREVIEW
_readMergedCells()
MERGEDCELLS.
static getDistanceY(PHPExcel_Worksheet $sheet, $startRow=1, $startOffsetY=0, $endRow=1, $endOffsetY=0)
Get the vertical distance in pixels between two anchors The distanceY is found as sum of all the span...
_readObjectProtect()
OBJECTPROTECT.
static NumberToName($codePage=1252)
Convert Microsoft Code Page Identifier to Code Page Name which iconv and mbstring understands...
_readMulRk()
Read MULRK record This record represents a cell range containing RK value cells.
_readLeftMargin()
Read LEFTMARGIN record.
static stringFromColumnIndex($pColumnIndex=0)
String from columnindex.
_readDataValidations()
Read DATAVALIDATIONS record.
const ORIENTATION_PORTRAIT
const FILL_PATTERN_DARKGRAY
_readBIFF5CellRangeAddressList($subData)
Read BIFF5 cell range address list section 2.5.15.
const XLS_WorkbookGlobals
_readMsoDrawingGroup()
Read MSODRAWINGGROUP record.
_readRecordData($data, $pos, $len)
Read record data from stream, decrypting as required.
static _uncompressByteString($string)
Convert UTF-16 string in compressed notation to uncompressed form.
_readScl()
Read SCL record.
_readPassword()
PASSWORD - Sheet protection (hashed) password (BIFF2 through BIFF8)
static _encodeUTF16($string, $compressed='')
Get UTF-8 string from (compressed or uncompressed) UTF-16 string.
const CALENDAR_WINDOWS_1900
constants
const FILL_PATTERN_LIGHTUP
_readBIFF8CellRangeAddressList($subData)
Read BIFF8 cell range address list section 2.5.15.
_readRangeProtection()
Read RANGEPROTECTION record Reading of this record is based on Microsoft Office Excel 97-2000 Binary ...
$_documentSummaryInformation
defined( 'APPLICATION_ENV')||define( 'APPLICATION_ENV'
_readMsoDrawing()
Read MSODRAWING record.
_readNote()
The NOTE record specifies a comment associated with a particular cell.
_readByteStringLong($subData)
Read byte string (16-bit string length) OpenOffice documentation: 2.5.2.
_readSummaryInformation()
Read summary information.
_readMulBlank()
Read MULBLANK record This record represents a cell range of empty cells.
static _GetInt4d($data, $pos)
Read 32-bit signed integer.
static _GetIEEE754($rknum)
const XLS_Type_DEFAULTROWHEIGHT
const XLS_Type_EXTERNALBOOK
const FILL_PATTERN_DARKUP
const BORDER_MEDIUMDASHED
static CountCharacters($value, $enc='UTF-8')
Get character count.
_readSelection()
Read SELECTION record.
_readSheetPr()
Read SHEETPR record.
_readDocumentSummaryInformation()
Read additional document summary information.
static _readColor($color, $palette, $version)
Read color.
const XLS_Type_MSODRAWINGGROUP
_readDefinedName()
DEFINEDNAME.
_readTopMargin()
Read TOPMARGIN record.
_readDataValidation()
Read DATAVALIDATION record.