Refactory Writer Styles to match new code organization (#433)
Decomposed old StyleHelper into StyleManager, StyleRegistry and StyleMerger.
This commit is contained in:
1 parent
238756ab6e
commit
cc9a0b526b
34 files changed
+1005
-762
No files matched your search
@@ -0,0 +1,92 @@
|
||||
<?php
|
||||
|
||||
namespace Box\Spout\Writer\Common\Manager\Style;
|
||||
|
||||
use Box\Spout\Writer\Common\Entity\Style\Style;
|
||||
|
||||
/**
|
||||
* Class StyleManager
|
||||
* Manages styles to be applied to a cell
|
||||
*
|
||||
* @package Box\Spout\Writer\Common\Manager\Style
|
||||
*/
|
||||
class StyleManager implements StyleManagerInterface
|
||||
{
|
||||
/** @var StyleRegistry Registry for all used styles */
|
||||
protected $styleRegistry;
|
||||
|
||||
/**
|
||||
* @param StyleRegistry $styleRegistry
|
||||
*/
|
||||
public function __construct(StyleRegistry $styleRegistry)
|
||||
{
|
||||
$this->styleRegistry = $styleRegistry;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the default style
|
||||
*
|
||||
* @return Style Default style
|
||||
*/
|
||||
protected function getDefaultStyle()
|
||||
{
|
||||
// By construction, the default style has ID 0
|
||||
return $this->styleRegistry->getRegisteredStyles()[0];
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the given style as a used style.
|
||||
* Duplicate styles won't be registered more than once.
|
||||
*
|
||||
* @param Style $style The style to be registered
|
||||
* @return Style The registered style, updated with an internal ID.
|
||||
*/
|
||||
public function registerStyle($style)
|
||||
{
|
||||
return $this->styleRegistry->registerStyle($style);
|
||||
}
|
||||
|
||||
/**
|
||||
* Apply additional styles if the given row needs it.
|
||||
* Typically, set "wrap text" if a cell contains a new line.
|
||||
*
|
||||
* @param Style $style The original style
|
||||
* @param array $dataRow The row the style will be applied to
|
||||
* @return Style The updated style
|
||||
*/
|
||||
public function applyExtraStylesIfNeeded($style, $dataRow)
|
||||
{
|
||||
$updatedStyle = $this->applyWrapTextIfCellContainsNewLine($style, $dataRow);
|
||||
return $updatedStyle;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the "wrap text" option if a cell of the given row contains a new line.
|
||||
*
|
||||
* @NOTE: There is a bug on the Mac version of Excel (2011 and below) where new lines
|
||||
* are ignored even when the "wrap text" option is set. This only occurs with
|
||||
* inline strings (shared strings do work fine).
|
||||
* A workaround would be to encode "\n" as "_x000D_" but it does not work
|
||||
* on the Windows version of Excel...
|
||||
*
|
||||
* @param Style $style The original style
|
||||
* @param array $dataRow The row the style will be applied to
|
||||
* @return Style The eventually updated style
|
||||
*/
|
||||
protected function applyWrapTextIfCellContainsNewLine($style, $dataRow)
|
||||
{
|
||||
// if the "wrap text" option is already set, no-op
|
||||
if ($style->hasSetWrapText()) {
|
||||
return $style;
|
||||
}
|
||||
|
||||
foreach ($dataRow as $cell) {
|
||||
if (is_string($cell) && strpos($cell, "\n") !== false) {
|
||||
$style->setShouldWrapText();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return $style;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
<?php
|
||||
|
||||
namespace Box\Spout\Writer\Common\Manager\Style;
|
||||
|
||||
use Box\Spout\Writer\Common\Entity\Style\Style;
|
||||
|
||||
/**
|
||||
* Interface StyleHManagernterface
|
||||
*
|
||||
* @package Box\Spout\Writer\Common\Manager\Style
|
||||
*/
|
||||
interface StyleManagerInterface
|
||||
{
|
||||
/**
|
||||
* Registers the given style as a used style.
|
||||
* Duplicate styles won't be registered more than once.
|
||||
*
|
||||
* @param Style $style The style to be registered
|
||||
* @return Style The registered style, updated with an internal ID.
|
||||
*/
|
||||
public function registerStyle($style);
|
||||
|
||||
/**
|
||||
* Apply additional styles if the given row needs it.
|
||||
* Typically, set "wrap text" if a cell contains a new line.
|
||||
*
|
||||
* @param Style $style The original style
|
||||
* @param array $dataRow The row the style will be applied to
|
||||
* @return Style The updated style
|
||||
*/
|
||||
public function applyExtraStylesIfNeeded($style, $dataRow);
|
||||
}
|
||||
+6
-25
@@ -1,38 +1,19 @@
|
||||
<?php
|
||||
|
||||
namespace Box\Spout\Writer\Common\Manager;
|
||||
namespace Box\Spout\Writer\Common\Manager\Style;
|
||||
|
||||
use Box\Spout\Writer\Common\Entity\Style\Color;
|
||||
use Box\Spout\Writer\Common\Entity\Style\Style;
|
||||
use Box\Spout\Writer\XLSX\Helper\BorderHelper;
|
||||
|
||||
/**
|
||||
* Class StyleManager
|
||||
* Manages styles to be applied to a cell
|
||||
* Class StyleMerger
|
||||
* Takes care of merging styles together
|
||||
*
|
||||
* @package Box\Spout\Writer\Common\Manager\Style
|
||||
*/
|
||||
class StyleManager
|
||||
class StyleMerger
|
||||
{
|
||||
/**
|
||||
* Serializes the style for future comparison with other styles.
|
||||
* The ID is excluded from the comparison, as we only care about
|
||||
* actual style properties.
|
||||
*
|
||||
* @param Style $style
|
||||
* @return string The serialized style
|
||||
*/
|
||||
public function serialize(Style $style)
|
||||
{
|
||||
// In order to be able to properly compare style, set static ID value
|
||||
$currentId = $style->getId();
|
||||
$style->setId(0);
|
||||
|
||||
$serializedStyle = serialize($style);
|
||||
|
||||
$style->setId($currentId);
|
||||
|
||||
return $serializedStyle;
|
||||
}
|
||||
|
||||
/**
|
||||
* Merges the current style with the given style, using the given style as a base. This means that:
|
||||
* - if current style and base style both have property A set, use current style property's value
|
||||
@@ -0,0 +1,115 @@
|
||||
<?php
|
||||
|
||||
namespace Box\Spout\Writer\Common\Manager\Style;
|
||||
|
||||
use Box\Spout\Writer\Common\Entity\Style\Style;
|
||||
|
||||
/**
|
||||
* Class StyleRegistry
|
||||
* Registry for all used styles
|
||||
*
|
||||
* @package Box\Spout\Writer\Common\Manager\Style
|
||||
*/
|
||||
class StyleRegistry
|
||||
{
|
||||
/** @var array [SERIALIZED_STYLE] => [STYLE_ID] mapping table, keeping track of the registered styles */
|
||||
protected $serializedStyleToStyleIdMappingTable = [];
|
||||
|
||||
/** @var array [STYLE_ID] => [STYLE] mapping table, keeping track of the registered styles */
|
||||
protected $styleIdToStyleMappingTable = [];
|
||||
|
||||
/**
|
||||
* @param Style $defaultStyle
|
||||
*/
|
||||
public function __construct(Style $defaultStyle)
|
||||
{
|
||||
// This ensures that the default style is the first one to be registered
|
||||
$this->registerStyle($defaultStyle);
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers the given style as a used style.
|
||||
* Duplicate styles won't be registered more than once.
|
||||
*
|
||||
* @param Style $style The style to be registered
|
||||
* @return Style The registered style, updated with an internal ID.
|
||||
*/
|
||||
public function registerStyle(Style $style)
|
||||
{
|
||||
$serializedStyle = $this->serialize($style);
|
||||
|
||||
if (!$this->hasStyleAlreadyBeenRegistered($style)) {
|
||||
$nextStyleId = count($this->serializedStyleToStyleIdMappingTable);
|
||||
$style->setId($nextStyleId);
|
||||
|
||||
$this->serializedStyleToStyleIdMappingTable[$serializedStyle] = $nextStyleId;
|
||||
$this->styleIdToStyleMappingTable[$nextStyleId] = $style;
|
||||
}
|
||||
|
||||
return $this->getStyleFromSerializedStyle($serializedStyle);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether the given style has already been registered.
|
||||
*
|
||||
* @param Style $style
|
||||
* @return bool
|
||||
*/
|
||||
protected function hasStyleAlreadyBeenRegistered(Style $style)
|
||||
{
|
||||
$serializedStyle = $this->serialize($style);
|
||||
|
||||
// Using isset here because it is way faster than array_key_exists...
|
||||
return isset($this->serializedStyleToStyleIdMappingTable[$serializedStyle]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the registered style associated to the given serialization.
|
||||
*
|
||||
* @param string $serializedStyle The serialized style from which the actual style should be fetched from
|
||||
* @return Style
|
||||
*/
|
||||
protected function getStyleFromSerializedStyle($serializedStyle)
|
||||
{
|
||||
$styleId = $this->serializedStyleToStyleIdMappingTable[$serializedStyle];
|
||||
return $this->styleIdToStyleMappingTable[$styleId];
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Style[] List of registered styles
|
||||
*/
|
||||
public function getRegisteredStyles()
|
||||
{
|
||||
return array_values($this->styleIdToStyleMappingTable);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int $styleId
|
||||
* @return Style
|
||||
*/
|
||||
public function getStyleFromStyleId($styleId)
|
||||
{
|
||||
return $this->styleIdToStyleMappingTable[$styleId];
|
||||
}
|
||||
|
||||
/**
|
||||
* Serializes the style for future comparison with other styles.
|
||||
* The ID is excluded from the comparison, as we only care about
|
||||
* actual style properties.
|
||||
*
|
||||
* @param Style $style
|
||||
* @return string The serialized style
|
||||
*/
|
||||
public function serialize(Style $style)
|
||||
{
|
||||
// In order to be able to properly compare style, set static ID value
|
||||
$currentId = $style->getId();
|
||||
$style->setId(0);
|
||||
|
||||
$serializedStyle = serialize($style);
|
||||
|
||||
$style->setId($currentId);
|
||||
|
||||
return $serializedStyle;
|
||||
}
|
||||
}
|
||||
@@ -4,8 +4,8 @@ namespace Box\Spout\Writer\Common\Manager;
|
||||
|
||||
use Box\Spout\Common\Exception\IOException;
|
||||
use Box\Spout\Writer\Common\Helper\FileSystemWithRootFolderHelperInterface;
|
||||
use Box\Spout\Writer\Common\Helper\StyleHelperInterface;
|
||||
use Box\Spout\Writer\Common\Entity\Options;
|
||||
use Box\Spout\Writer\Common\Manager\Style\StyleManagerInterface;
|
||||
use Box\Spout\Writer\Common\Sheet;
|
||||
use Box\Spout\Writer\Common\Entity\Workbook;
|
||||
use Box\Spout\Writer\Common\Entity\Worksheet;
|
||||
@@ -31,14 +31,14 @@ abstract class WorkbookManagerAbstract implements WorkbookManagerInterface
|
||||
/** @var WorksheetManagerInterface */
|
||||
protected $worksheetManager;
|
||||
|
||||
/** @var StyleHelperInterface */
|
||||
protected $styleHelper;
|
||||
/** @var StyleManagerInterface Manages styles */
|
||||
protected $styleManager;
|
||||
|
||||
/** @var FileSystemWithRootFolderHelperInterface Helper to perform file system operations */
|
||||
protected $fileSystemHelper;
|
||||
|
||||
/** @var EntityFactory Factory to create entities */
|
||||
private $entityFactory;
|
||||
protected $entityFactory;
|
||||
|
||||
/** @var Worksheet The worksheet where data will be written to */
|
||||
protected $currentWorksheet;
|
||||
@@ -48,7 +48,7 @@ abstract class WorkbookManagerAbstract implements WorkbookManagerInterface
|
||||
* @param Workbook $workbook
|
||||
* @param OptionsManagerInterface $optionsManager
|
||||
* @param WorksheetManagerInterface $worksheetManager
|
||||
* @param StyleHelperInterface $styleHelper
|
||||
* @param StyleManagerInterface $styleManager
|
||||
* @param FileSystemWithRootFolderHelperInterface $fileSystemHelper
|
||||
* @param EntityFactory $entityFactory
|
||||
*/
|
||||
@@ -56,14 +56,14 @@ abstract class WorkbookManagerAbstract implements WorkbookManagerInterface
|
||||
Workbook $workbook,
|
||||
OptionsManagerInterface $optionsManager,
|
||||
WorksheetManagerInterface $worksheetManager,
|
||||
StyleHelperInterface $styleHelper,
|
||||
StyleManagerInterface $styleManager,
|
||||
FileSystemWithRootFolderHelperInterface $fileSystemHelper,
|
||||
EntityFactory $entityFactory)
|
||||
{
|
||||
$this->workbook = $workbook;
|
||||
$this->optionManager = $optionsManager;
|
||||
$this->worksheetManager = $worksheetManager;
|
||||
$this->styleHelper = $styleHelper;
|
||||
$this->styleManager = $styleManager;
|
||||
$this->fileSystemHelper = $fileSystemHelper;
|
||||
$this->entityFactory = $entityFactory;
|
||||
}
|
||||
@@ -244,8 +244,8 @@ abstract class WorkbookManagerAbstract implements WorkbookManagerInterface
|
||||
*/
|
||||
private function addRowWithStyleToWorksheet(Worksheet $worksheet, $dataRow, Style $style)
|
||||
{
|
||||
$updatedStyle = $this->styleHelper->applyExtraStylesIfNeeded($style, $dataRow);
|
||||
$registeredStyle = $this->styleHelper->registerStyle($updatedStyle);
|
||||
$updatedStyle = $this->styleManager->applyExtraStylesIfNeeded($style, $dataRow);
|
||||
$registeredStyle = $this->styleManager->registerStyle($updatedStyle);
|
||||
$this->worksheetManager->addRow($worksheet, $dataRow, $registeredStyle);
|
||||
|
||||
// update max num columns for the worksheet
|
||||
|
||||
Reference in new issue
Block a user