33namespace PhpOffice \PhpSpreadsheet \Reader \Xlsx ;
44
55use PhpOffice \PhpSpreadsheet \Reader \Xlsx \Styles as StyleReader ;
6+ use PhpOffice \PhpSpreadsheet \Style \Color ;
67use PhpOffice \PhpSpreadsheet \Style \Conditional ;
8+ use PhpOffice \PhpSpreadsheet \Style \ConditionalFormatting \ConditionalColorScale ;
79use PhpOffice \PhpSpreadsheet \Style \ConditionalFormatting \ConditionalDataBar ;
810use PhpOffice \PhpSpreadsheet \Style \ConditionalFormatting \ConditionalFormattingRuleExtension ;
911use PhpOffice \PhpSpreadsheet \Style \ConditionalFormatting \ConditionalFormatValueObject ;
@@ -25,11 +27,14 @@ class ConditionalStyles
2527
2628 private array $ dxfs ;
2729
28- public function __construct (Worksheet $ workSheet , SimpleXMLElement $ worksheetXml , array $ dxfs = [])
30+ private StyleReader $ styleReader ;
31+
32+ public function __construct (Worksheet $ workSheet , SimpleXMLElement $ worksheetXml , array $ dxfs , StyleReader $ styleReader )
2933 {
3034 $ this ->worksheet = $ workSheet ;
3135 $ this ->worksheetXml = $ worksheetXml ;
3236 $ this ->dxfs = $ dxfs ;
37+ $ this ->styleReader = $ styleReader ;
3338 }
3439
3540 public function load (): void
@@ -45,13 +50,13 @@ public function load(): void
4550 $ this ->worksheet ->setSelectedCells ($ selectedCells );
4651 }
4752
48- public function loadFromExt (StyleReader $ styleReader ): void
53+ public function loadFromExt (): void
4954 {
5055 $ selectedCells = $ this ->worksheet ->getSelectedCells ();
5156
5257 $ this ->ns = $ this ->worksheetXml ->getNamespaces (true );
5358 $ this ->setConditionalsFromExt (
54- $ this ->readConditionalsFromExt ($ this ->worksheetXml ->extLst , $ styleReader )
59+ $ this ->readConditionalsFromExt ($ this ->worksheetXml ->extLst )
5560 );
5661
5762 $ this ->worksheet ->setSelectedCells ($ selectedCells );
@@ -68,7 +73,7 @@ private function setConditionalsFromExt(array $conditionals): void
6873 }
6974 }
7075
71- private function readConditionalsFromExt (SimpleXMLElement $ extLst, StyleReader $ styleReader ): array
76+ private function readConditionalsFromExt (SimpleXMLElement $ extLst ): array
7277 {
7378 $ conditionals = [];
7479 if (!isset ($ extLst ->ext )) {
@@ -110,7 +115,7 @@ private function readConditionalsFromExt(SimpleXMLElement $extLst, StyleReader $
110115 $ priority = (int ) $ attributes ->priority ;
111116
112117 $ conditional = $ this ->readConditionalRuleFromExt ($ extCfRuleXml , $ attributes );
113- $ cfStyle = $ this ->readStyleFromExt ($ extCfRuleXml, $ styleReader );
118+ $ cfStyle = $ this ->readStyleFromExt ($ extCfRuleXml );
114119 $ conditional ->setStyle ($ cfStyle );
115120 $ conditionals [$ sqref ][$ priority ] = $ conditional ;
116121 }
@@ -146,17 +151,17 @@ private function readConditionalRuleFromExt(SimpleXMLElement $cfRuleXml, SimpleX
146151 return $ conditional ;
147152 }
148153
149- private function readStyleFromExt (SimpleXMLElement $ extCfRuleXml, StyleReader $ styleReader ): Style
154+ private function readStyleFromExt (SimpleXMLElement $ extCfRuleXml ): Style
150155 {
151156 $ cfStyle = new Style (false , true );
152157 if ($ extCfRuleXml ->dxf ) {
153158 $ styleXML = $ extCfRuleXml ->dxf ->children ();
154159
155160 if ($ styleXML ->borders ) {
156- $ styleReader ->readBorderStyle ($ cfStyle ->getBorders (), $ styleXML ->borders );
161+ $ this -> styleReader ->readBorderStyle ($ cfStyle ->getBorders (), $ styleXML ->borders );
157162 }
158163 if ($ styleXML ->fill ) {
159- $ styleReader ->readFillStyle ($ cfStyle ->getFill (), $ styleXML ->fill );
164+ $ this -> styleReader ->readFillStyle ($ cfStyle ->getFill (), $ styleXML ->fill );
160165 }
161166 }
162167
@@ -198,6 +203,7 @@ private function readStyleRules(array $cfRules, SimpleXMLElement $extLst): array
198203 $ conditionalFormattingRuleExtensions = ConditionalFormattingRuleExtension::parseExtLstXml ($ extLst );
199204 $ conditionalStyles = [];
200205
206+ /** @var SimpleXMLElement $cfRule */
201207 foreach ($ cfRules as $ cfRule ) {
202208 $ objConditional = new Conditional ();
203209 $ objConditional ->setConditionType ((string ) $ cfRule ['type ' ]);
@@ -231,7 +237,11 @@ private function readStyleRules(array $cfRules, SimpleXMLElement $extLst): array
231237
232238 if (isset ($ cfRule ->dataBar )) {
233239 $ objConditional ->setDataBar (
234- $ this ->readDataBarOfConditionalRule ($ cfRule , $ conditionalFormattingRuleExtensions ) // @phpstan-ignore-line
240+ $ this ->readDataBarOfConditionalRule ($ cfRule , $ conditionalFormattingRuleExtensions )
241+ );
242+ } elseif (isset ($ cfRule ->colorScale )) {
243+ $ objConditional ->setColorScale (
244+ $ this ->readColorScale ($ cfRule )
235245 );
236246 } elseif (isset ($ cfRule ['dxfId ' ])) {
237247 $ objConditional ->setStyle (clone $ this ->dxfs [(int ) ($ cfRule ['dxfId ' ])]);
@@ -270,14 +280,48 @@ private function readDataBarOfConditionalRule($cfRule, array $conditionalFormatt
270280
271281 //color
272282 if (isset ($ cfRule ->dataBar ->color )) {
273- $ dataBar ->setColor (( string ) $ cfRule ->dataBar ->color [ ' rgb ' ] );
283+ $ dataBar ->setColor ($ this -> styleReader -> readColor ( $ cfRule ->dataBar ->color ) );
274284 }
275285 //extLst
276286 $ this ->readDataBarExtLstOfConditionalRule ($ dataBar , $ cfRule , $ conditionalFormattingRuleExtensions );
277287
278288 return $ dataBar ;
279289 }
280290
291+ private function readColorScale (simpleXMLElement |stdClass $ cfRule ): ConditionalColorScale
292+ {
293+ $ colorScale = new ConditionalColorScale ();
294+ $ types = [];
295+ foreach ($ cfRule ->colorScale ->cfvo as $ cfvoXml ) {
296+ $ attr = $ cfvoXml ->attributes () ?? [];
297+ $ type = (string ) ($ attr ['type ' ] ?? '' );
298+ $ types [] = $ type ;
299+ $ val = $ attr ['val ' ] ?? null ;
300+ if ($ type === 'min ' ) {
301+ $ colorScale ->setMinimumConditionalFormatValueObject (new ConditionalFormatValueObject ($ type , $ val ));
302+ } elseif ($ type === 'percentile ' ) {
303+ $ colorScale ->setMidpointConditionalFormatValueObject (new ConditionalFormatValueObject ($ type , $ val ));
304+ } elseif ($ type === 'max ' ) {
305+ $ colorScale ->setMaximumConditionalFormatValueObject (new ConditionalFormatValueObject ($ type , $ val ));
306+ }
307+ }
308+ $ idx = 0 ;
309+ foreach ($ cfRule ->colorScale ->color as $ color ) {
310+ $ type = $ types [$ idx ];
311+ $ rgb = $ this ->styleReader ->readColor ($ color );
312+ if ($ type === 'min ' ) {
313+ $ colorScale ->setMinimumColor (new Color ($ rgb ));
314+ } elseif ($ type === 'percentile ' ) {
315+ $ colorScale ->setMidpointColor (new Color ($ rgb ));
316+ } elseif ($ type === 'max ' ) {
317+ $ colorScale ->setMaximumColor (new Color ($ rgb ));
318+ }
319+ ++$ idx ;
320+ }
321+
322+ return $ colorScale ;
323+ }
324+
281325 /**
282326 * @param SimpleXMLElement|stdClass $cfRule
283327 */
0 commit comments