コード例 #1
0
ファイル: Excel5.php プロジェクト: bestgoodz/toko-baju
 /**
  * Loads PHPExcel from file
  *
  * @param 	string 		$pFilename
  * @return 	PHPExcel
  * @throws 	Exception
  */
 public function load($pFilename)
 {
     // Read the OLE file
     $this->_loadOLE($pFilename);
     // Initialisations
     $this->_phpExcel = new PHPExcel();
     $this->_phpExcel->removeSheetByIndex(0);
     // remove 1st sheet
     if (!$this->_readDataOnly) {
         $this->_phpExcel->removeCellStyleXfByIndex(0);
         // remove the default style
         $this->_phpExcel->removeCellXfByIndex(0);
         // remove the default style
     }
     // Read the summary information stream (containing meta data)
     $this->_readSummaryInformation();
     // total byte size of Excel data (workbook global substream + sheet substreams)
     $this->_dataSize = strlen($this->_data);
     // initialize
     $this->_pos = 0;
     $this->_codepage = 'CP1252';
     $this->_formats = array();
     $this->_objFonts = array();
     $this->_palette = array();
     $this->_sheets = array();
     $this->_externalBooks = array();
     $this->_ref = array();
     $this->_definedname = array();
     $this->_sst = array();
     $this->_drawingGroupData = '';
     $this->_xfIndex = '';
     $this->_mapCellXfIndex = array();
     $this->_mapCellStyleXfIndex = array();
     // Parse Workbook Global Substream
     while ($this->_pos < $this->_dataSize) {
         $code = $this->_GetInt2d($this->_data, $this->_pos);
         switch ($code) {
             case self::XLS_Type_BOF:
                 $this->_readBof();
                 break;
             case self::XLS_Type_FILEPASS:
                 $this->_readFilepass();
                 break;
             case self::XLS_Type_CODEPAGE:
                 $this->_readCodepage();
                 break;
             case self::XLS_Type_DATEMODE:
                 $this->_readDateMode();
                 break;
             case self::XLS_Type_FONT:
                 $this->_readFont();
                 break;
             case self::XLS_Type_FORMAT:
                 $this->_readFormat();
                 break;
             case self::XLS_Type_XF:
                 $this->_readXf();
                 break;
             case self::XLS_Type_XFEXT:
                 $this->_readXfExt();
                 break;
             case self::XLS_Type_STYLE:
                 $this->_readStyle();
                 break;
             case self::XLS_Type_PALETTE:
                 $this->_readPalette();
                 break;
             case self::XLS_Type_SHEET:
                 $this->_readSheet();
                 break;
             case self::XLS_Type_EXTERNALBOOK:
                 $this->_readExternalBook();
                 break;
             case self::XLS_Type_EXTERNNAME:
                 $this->_readExternName();
                 break;
             case self::XLS_Type_EXTERNSHEET:
                 $this->_readExternSheet();
                 break;
             case self::XLS_Type_DEFINEDNAME:
                 $this->_readDefinedName();
                 break;
             case self::XLS_Type_MSODRAWINGGROUP:
                 $this->_readMsoDrawingGroup();
                 break;
             case self::XLS_Type_SST:
                 $this->_readSst();
                 break;
             case self::XLS_Type_EOF:
                 $this->_readDefault();
                 break 2;
             default:
                 $this->_readDefault();
                 break;
         }
     }
     // Resolve indexed colors for font, fill, and border colors
     // Cannot be resolved already in XF record, because PALETTE record comes afterwards
     if (!$this->_readDataOnly) {
         foreach ($this->_objFonts as $objFont) {
             if (isset($objFont->colorIndex)) {
                 $color = $this->_readColor($objFont->colorIndex);
                 $objFont->getColor()->setRGB($color['rgb']);
             }
         }
         foreach ($this->_phpExcel->getCellXfCollection() as $objStyle) {
             // fill start and end color
             $fill = $objStyle->getFill();
             if (isset($fill->startcolorIndex)) {
                 $startColor = $this->_readColor($fill->startcolorIndex);
                 $fill->getStartColor()->setRGB($startColor['rgb']);
             }
             if (isset($fill->endcolorIndex)) {
                 $endColor = $this->_readColor($fill->endcolorIndex);
                 $fill->getEndColor()->setRGB($endColor['rgb']);
             }
             // border colors
             $top = $objStyle->getBorders()->getTop();
             $right = $objStyle->getBorders()->getRight();
             $bottom = $objStyle->getBorders()->getBottom();
             $left = $objStyle->getBorders()->getLeft();
             $diagonal = $objStyle->getBorders()->getDiagonal();
             if (isset($top->colorIndex)) {
                 $borderTopColor = $this->_readColor($top->colorIndex);
                 $top->getColor()->setRGB($borderTopColor['rgb']);
             }
             if (isset($right->colorIndex)) {
                 $borderRightColor = $this->_readColor($right->colorIndex);
                 $right->getColor()->setRGB($borderRightColor['rgb']);
             }
             if (isset($bottom->colorIndex)) {
                 $borderBottomColor = $this->_readColor($bottom->colorIndex);
                 $bottom->getColor()->setRGB($borderBottomColor['rgb']);
             }
             if (isset($left->colorIndex)) {
                 $borderLeftColor = $this->_readColor($left->colorIndex);
                 $left->getColor()->setRGB($borderLeftColor['rgb']);
             }
             if (isset($diagonal->colorIndex)) {
                 $borderDiagonalColor = $this->_readColor($diagonal->colorIndex);
                 $diagonal->getColor()->setRGB($borderDiagonalColor['rgb']);
             }
         }
     }
     // treat MSODRAWINGGROUP records, workbook-level Escher
     if (!$this->_readDataOnly && $this->_drawingGroupData) {
         $escherWorkbook = new Shared_Escher();
         $reader = new Reader_Excel5_Escher($escherWorkbook);
         $escherWorkbook = $reader->load($this->_drawingGroupData);
         // debug Escher stream
         //$debug = new Debug_Escher(new Shared_Escher());
         //$debug->load($this->_drawingGroupData);
     }
     // Parse the individual sheets
     foreach ($this->_sheets as $sheet) {
         if ($sheet['sheetType'] != 0x0) {
             // 0x00: Worksheet, 0x02: Chart, 0x06: Visual Basic module
             continue;
         }
         // check if sheet should be skipped
         if (isset($this->_loadSheetsOnly) && !in_array($sheet['name'], $this->_loadSheetsOnly)) {
             continue;
         }
         // add sheet to PHPExcel object
         $this->_phpSheet = $this->_phpExcel->createSheet();
         $this->_phpSheet->setTitle($sheet['name']);
         $this->_phpSheet->setSheetState($sheet['sheetState']);
         $this->_pos = $sheet['offset'];
         // Initialize isFitToPages. May change after reading SHEETPR record.
         $this->_isFitToPages = false;
         // Initialize drawingData
         $this->_drawingData = '';
         // Initialize objs
         $this->_objs = array();
         // Initialize shared formula parts
         $this->_sharedFormulaParts = array();
         // Initialize shared formulas
         $this->_sharedFormulas = array();
         while ($this->_pos <= $this->_dataSize - 4) {
             $code = $this->_GetInt2d($this->_data, $this->_pos);
             switch ($code) {
                 case self::XLS_Type_BOF:
                     $this->_readBof();
                     break;
                 case self::XLS_Type_PRINTGRIDLINES:
                     $this->_readPrintGridlines();
                     break;
                 case self::XLS_Type_DEFAULTROWHEIGHT:
                     $this->_readDefaultRowHeight();
                     break;
                 case self::XLS_Type_SHEETPR:
                     $this->_readSheetPr();
                     break;
                 case self::XLS_Type_HORIZONTALPAGEBREAKS:
                     $this->_readHorizontalPageBreaks();
                     break;
                 case self::XLS_Type_VERTICALPAGEBREAKS:
                     $this->_readVerticalPageBreaks();
                     break;
                 case self::XLS_Type_HEADER:
                     $this->_readHeader();
                     break;
                 case self::XLS_Type_FOOTER:
                     $this->_readFooter();
                     break;
                 case self::XLS_Type_HCENTER:
                     $this->_readHcenter();
                     break;
                 case self::XLS_Type_VCENTER:
                     $this->_readVcenter();
                     break;
                 case self::XLS_Type_LEFTMARGIN:
                     $this->_readLeftMargin();
                     break;
                 case self::XLS_Type_RIGHTMARGIN:
                     $this->_readRightMargin();
                     break;
                 case self::XLS_Type_TOPMARGIN:
                     $this->_readTopMargin();
                     break;
                 case self::XLS_Type_BOTTOMMARGIN:
                     $this->_readBottomMargin();
                     break;
                 case self::XLS_Type_PAGESETUP:
                     $this->_readPageSetup();
                     break;
                 case self::XLS_Type_PROTECT:
                     $this->_readProtect();
                     break;
                 case self::XLS_Type_SCENPROTECT:
                     $this->_readScenProtect();
                     break;
                 case self::XLS_Type_OBJECTPROTECT:
                     $this->_readObjectProtect();
                     break;
                 case self::XLS_Type_PASSWORD:
                     $this->_readPassword();
                     break;
                 case self::XLS_Type_DEFCOLWIDTH:
                     $this->_readDefColWidth();
                     break;
                 case self::XLS_Type_COLINFO:
                     $this->_readColInfo();
                     break;
                 case self::XLS_Type_DIMENSION:
                     $this->_readDefault();
                     break;
                 case self::XLS_Type_ROW:
                     $this->_readRow();
                     break;
                 case self::XLS_Type_DBCELL:
                     $this->_readDefault();
                     break;
                 case self::XLS_Type_RK:
                     $this->_readRk();
                     break;
                 case self::XLS_Type_LABELSST:
                     $this->_readLabelSst();
                     break;
                 case self::XLS_Type_MULRK:
                     $this->_readMulRk();
                     break;
                 case self::XLS_Type_NUMBER:
                     $this->_readNumber();
                     break;
                 case self::XLS_Type_FORMULA:
                     $this->_readFormula();
                     break;
                 case self::XLS_Type_SHAREDFMLA:
                     $this->_readSharedFmla();
                     break;
                 case self::XLS_Type_BOOLERR:
                     $this->_readBoolErr();
                     break;
                 case self::XLS_Type_MULBLANK:
                     $this->_readMulBlank();
                     break;
                 case self::XLS_Type_LABEL:
                     $this->_readLabel();
                     break;
                 case self::XLS_Type_BLANK:
                     $this->_readBlank();
                     break;
                 case self::XLS_Type_MSODRAWING:
                     $this->_readMsoDrawing();
                     break;
                 case self::XLS_Type_OBJ:
                     $this->_readObj();
                     break;
                 case self::XLS_Type_WINDOW2:
                     $this->_readWindow2();
                     break;
                 case self::XLS_Type_SCL:
                     $this->_readScl();
                     break;
                 case self::XLS_Type_PANE:
                     $this->_readPane();
                     break;
                 case self::XLS_Type_SELECTION:
                     $this->_readSelection();
                     break;
                 case self::XLS_Type_MERGEDCELLS:
                     $this->_readMergedCells();
                     break;
                 case self::XLS_Type_HYPERLINK:
                     $this->_readHyperLink();
                     break;
                 case self::XLS_Type_DATAVALIDATIONS:
                     $this->_readDataValidations();
                     break;
                 case self::XLS_Type_DATAVALIDATION:
                     $this->_readDataValidation();
                     break;
                 case self::XLS_Type_SHEETLAYOUT:
                     $this->_readSheetLayout();
                     break;
                 case self::XLS_Type_SHEETPROTECTION:
                     $this->_readSheetProtection();
                     break;
                 case self::XLS_Type_RANGEPROTECTION:
                     $this->_readRangeProtection();
                     break;
                     //case self::XLS_Type_IMDATA:				$this->_readImData();					break;
                 //case self::XLS_Type_IMDATA:				$this->_readImData();					break;
                 case self::XLS_Type_CONTINUE:
                     $this->_readContinue();
                     break;
                 case self::XLS_Type_EOF:
                     $this->_readDefault();
                     break 2;
                 default:
                     $this->_readDefault();
                     break;
             }
         }
         // treat MSODRAWING records, sheet-level Escher
         if (!$this->_readDataOnly && $this->_drawingData) {
             $escherWorksheet = new Shared_Escher();
             $reader = new Reader_Excel5_Escher($escherWorksheet);
             $escherWorksheet = $reader->load($this->_drawingData);
             // debug Escher stream
             //$debug = new Debug_Escher(new Shared_Escher());
             //$debug->load($this->_drawingData);
             // get all spContainers in one long array, so they can be mapped to OBJ records
             $allSpContainers = $escherWorksheet->getDgContainer()->getSpgrContainer()->getAllSpContainers();
         }
         // treat OBJ records
         foreach ($this->_objs as $n => $obj) {
             // the first shape container never has a corresponding OBJ record, hence $n + 1
             $spContainer = $allSpContainers[$n + 1];
             // we skip all spContainers that are a part of a group shape since we cannot yet handle those
             if ($spContainer->getNestingLevel() > 1) {
                 continue;
             }
             // calculate the width and height of the shape
             list($startColumn, $startRow) = Cell::coordinateFromString($spContainer->getStartCoordinates());
             list($endColumn, $endRow) = Cell::coordinateFromString($spContainer->getEndCoordinates());
             $startOffsetX = $spContainer->getStartOffsetX();
             $startOffsetY = $spContainer->getStartOffsetY();
             $endOffsetX = $spContainer->getEndOffsetX();
             $endOffsetY = $spContainer->getEndOffsetY();
             $width = Shared_Excel5::getDistanceX($this->_phpSheet, $startColumn, $startOffsetX, $endColumn, $endOffsetX);
             $height = Shared_Excel5::getDistanceY($this->_phpSheet, $startRow, $startOffsetY, $endRow, $endOffsetY);
             // calculate offsetX and offsetY of the shape
             $offsetX = $startOffsetX * Shared_Excel5::sizeCol($this->_phpSheet, $startColumn) / 1024;
             $offsetY = $startOffsetY * Shared_Excel5::sizeRow($this->_phpSheet, $startRow) / 256;
             switch ($obj['type']) {
                 case 0x8:
                     // picture
                     // get index to BSE entry (1-based)
                     $BSEindex = $spContainer->getOPT(0x104);
                     $BSECollection = $escherWorkbook->getDggContainer()->getBstoreContainer()->getBSECollection();
                     $BSE = $BSECollection[$BSEindex - 1];
                     $blipType = $BSE->getBlipType();
                     // need check because some blip types are not supported by Escher reader such as EMF
                     if ($blip = $BSE->getBlip()) {
                         $ih = imagecreatefromstring($blip->getData());
                         $drawing = new Worksheet_MemoryDrawing();
                         $drawing->setImageResource($ih);
                         // width, height, offsetX, offsetY
                         $drawing->setResizeProportional(false);
                         $drawing->setWidth($width);
                         $drawing->setHeight($height);
                         $drawing->setOffsetX($offsetX);
                         $drawing->setOffsetY($offsetY);
                         switch ($blipType) {
                             case Shared_Escher_DggContainer_BstoreContainer_BSE::BLIPTYPE_JPEG:
                                 $drawing->setRenderingFunction(Worksheet_MemoryDrawing::RENDERING_JPEG);
                                 $drawing->setMimeType(Worksheet_MemoryDrawing::MIMETYPE_JPEG);
                                 break;
                             case Shared_Escher_DggContainer_BstoreContainer_BSE::BLIPTYPE_PNG:
                                 $drawing->setRenderingFunction(Worksheet_MemoryDrawing::RENDERING_PNG);
                                 $drawing->setMimeType(Worksheet_MemoryDrawing::MIMETYPE_PNG);
                                 break;
                         }
                         $drawing->setWorksheet($this->_phpSheet);
                         $drawing->setCoordinates($spContainer->getStartCoordinates());
                     }
                     break;
                 default:
                     // other object type
                     break;
             }
         }
         // treat SHAREDFMLA records
         if ($this->_version == self::XLS_BIFF8) {
             foreach ($this->_sharedFormulaParts as $cell => $baseCell) {
                 $formula = $this->_getFormulaFromStructure($this->_sharedFormulas[$baseCell], $cell);
                 $this->_phpSheet->getCell($cell)->setValueExplicit('=' . $formula, Cell_DataType::TYPE_FORMULA);
             }
         }
     }
     // add the named ranges (defined names)
     foreach ($this->_definedname as $definedName) {
         if ($definedName['isBuiltInName']) {
             switch ($definedName['name']) {
                 case pack('C', 0x6):
                     // print area
                     //	in general, formula looks like this: Foo!$C$7:$J$66,Bar!$A$1:$IV$2
                     $ranges = explode(',', $definedName['formula']);
                     // FIXME: what if sheetname contains comma?
                     $extractedRanges = array();
                     foreach ($ranges as $range) {
                         // $range should look like one of these
                         //		Foo!$C$7:$J$66
                         //		Bar!$A$1:$IV$2
                         $explodes = explode('!', $range);
                         $sheetName = $explodes[0];
                         if (count($explodes) == 2) {
                             $extractedRanges[] = str_replace('$', '', $explodes[1]);
                             // C7:J66
                         }
                     }
                     if ($docSheet = $this->_phpExcel->getSheetByName($sheetName)) {
                         $docSheet->getPageSetup()->setPrintArea(implode(',', $extractedRanges));
                         // C7:J66,A1:IV2
                     }
                     break;
                 case pack('C', 0x7):
                     // print titles (repeating rows)
                     // Assuming BIFF8, there are 3 cases
                     // 1. repeating rows
                     //		formula looks like this: Sheet!$A$1:$IV$2
                     //		rows 1-2 repeat
                     // 2. repeating columns
                     //		formula looks like this: Sheet!$A$1:$B$65536
                     //		columns A-B repeat
                     // 3. both repeating rows and repeating columns
                     //		formula looks like this: Sheet!$A$1:$B$65536,Sheet!$A$1:$IV$2
                     $ranges = explode(',', $definedName['formula']);
                     // FIXME: what if sheetname contains comma?
                     foreach ($ranges as $range) {
                         // $range should look like this one of these
                         //		Sheet!$A$1:$B$65536
                         //		Sheet!$A$1:$IV$2
                         $explodes = explode('!', $range);
                         if (count($explodes) == 2) {
                             if ($docSheet = $this->_phpExcel->getSheetByName($explodes[0])) {
                                 $extractedRange = $explodes[1];
                                 $extractedRange = str_replace('$', '', $extractedRange);
                                 $coordinateStrings = explode(':', $extractedRange);
                                 if (count($coordinateStrings) == 2) {
                                     list($firstColumn, $firstRow) = Cell::coordinateFromString($coordinateStrings[0]);
                                     list($lastColumn, $lastRow) = Cell::coordinateFromString($coordinateStrings[1]);
                                     if ($firstColumn == 'A' and $lastColumn == 'IV') {
                                         // then we have repeating rows
                                         $docSheet->getPageSetup()->setRowsToRepeatAtTop(array($firstRow, $lastRow));
                                     } elseif ($firstRow == 1 and $lastRow == 65536) {
                                         // then we have repeating columns
                                         $docSheet->getPageSetup()->setColumnsToRepeatAtLeft(array($firstColumn, $lastColumn));
                                     }
                                 }
                             }
                         }
                     }
                     break;
             }
         } else {
             // Extract range
             $explodes = explode('!', $definedName['formula']);
             if (count($explodes) == 2) {
                 if ($docSheet = $this->_phpExcel->getSheetByName($explodes[0])) {
                     $extractedRange = $explodes[1];
                     $extractedRange = str_replace('$', '', $extractedRange);
                     $localOnly = $definedName['scope'] == 0 ? false : true;
                     $scope = $definedName['scope'] == 0 ? null : $this->_phpExcel->getSheetByName($this->_sheets[$definedName['scope'] - 1]['name']);
                     $this->_phpExcel->addNamedRange(new NamedRange((string) $definedName['name'], $docSheet, $extractedRange, $localOnly, $scope));
                 }
             }
         }
     }
     return $this->_phpExcel;
 }
コード例 #2
0
ファイル: Worksheet.php プロジェクト: bestgoodz/toko-baju
 /**
  * Write MSODRAWING record
  */
 private function _writeMsoDrawing()
 {
     // check if there are any shapes for this sheet
     if (count($this->_phpSheet->getDrawingCollection()) == 0) {
         return;
     }
     // create intermediate Escher object
     $escher = new Shared_Escher();
     // dgContainer
     $dgContainer = new Shared_Escher_DgContainer();
     // set the drawing index (we use sheet index + 1)
     $dgContainer->setDgId($this->_phpSheet->getParent()->getIndex($this->_phpSheet) + 1);
     $escher->setDgContainer($dgContainer);
     // spgrContainer
     $spgrContainer = new Shared_Escher_DgContainer_SpgrContainer();
     $dgContainer->setSpgrContainer($spgrContainer);
     // add one shape which is the group shape
     $spContainer = new Shared_Escher_DgContainer_SpgrContainer_SpContainer();
     $spContainer->setSpgr(true);
     $spContainer->setSpType(0);
     $spContainer->setSpId($this->_phpSheet->getParent()->getIndex($this->_phpSheet) + 1 << 10);
     $spgrContainer->addChild($spContainer);
     // add the shapes
     // outer loop is for determining BSE index
     $blipIndex = 0;
     // 1-based index to BstoreContainer
     $countShapes = 0;
     // count number of shapes (minus group shape), in this sheet
     foreach ($this->_phpSheet->getParent()->getAllsheets() as $sheet) {
         foreach ($sheet->getDrawingCollection() as $drawing) {
             ++$blipIndex;
             if ($sheet === $this->_phpSheet) {
                 ++$countShapes;
                 // add the shape
                 $spContainer = new Shared_Escher_DgContainer_SpgrContainer_SpContainer();
                 // set the shape type
                 $spContainer->setSpType(0x4b);
                 // set the shape index (we combine 1-based sheet index and $countShapes to create unique shape index)
                 $spId = $countShapes | $this->_phpSheet->getParent()->getIndex($this->_phpSheet) + 1 << 10;
                 $spContainer->setSpId($spId);
                 // keep track of last spId
                 $lastSpId = $spId;
                 // set the BLIP index
                 $spContainer->setOPT(0x4104, $blipIndex);
                 // set coordinates and offsets, client anchor
                 $coordinates = $drawing->getCoordinates();
                 $offsetX = $drawing->getOffsetX();
                 $offsetY = $drawing->getOffsetY();
                 $width = $drawing->getWidth();
                 $height = $drawing->getHeight();
                 $twoAnchor = Shared_Excel5::oneAnchor2twoAnchor($this->_phpSheet, $coordinates, $offsetX, $offsetY, $width, $height);
                 $spContainer->setStartCoordinates($twoAnchor['startCoordinates']);
                 $spContainer->setStartOffsetX($twoAnchor['startOffsetX']);
                 $spContainer->setStartOffsetY($twoAnchor['startOffsetY']);
                 $spContainer->setEndCoordinates($twoAnchor['endCoordinates']);
                 $spContainer->setEndOffsetX($twoAnchor['endOffsetX']);
                 $spContainer->setEndOffsetY($twoAnchor['endOffsetY']);
                 $spgrContainer->addChild($spContainer);
             }
         }
     }
     // set last shape index
     $dgContainer->setLastSpId($lastSpId);
     // write the Escher stream
     $writer = new Writer_Excel5_Escher($escher);
     $data = $writer->close();
     $spOffsets = $writer->getSpOffsets();
     // write the neccesary MSODRAWING, OBJ records
     // split the Escher stream
     $spOffsets[0] = 0;
     $nm = count($spOffsets) - 1;
     // number of shapes excluding first shape
     for ($i = 1; $i <= $nm; ++$i) {
         // MSODRAWING record
         $record = 0xec;
         // Record identifier
         // chunk of Escher stream for one shape
         $dataChunk = substr($data, $spOffsets[$i - 1], $spOffsets[$i] - $spOffsets[$i - 1]);
         $length = strlen($dataChunk);
         $header = pack("vv", $record, $length);
         $this->_append($header . $dataChunk);
         // OBJ record
         $record = 0x5d;
         // record identifier
         $objData = '';
         // ftCmo
         $objData .= pack('vvvvvVVV', 0x15, 0x12, 0x8, $i, 0x6011, 0, 0, 0);
         // ftEnd
         $objData .= pack('vv', 0x0, 0x0);
         $length = strlen($objData);
         $header = pack('vv', $record, $length);
         $this->_append($header . $objData);
     }
 }