Skip to content

Commit 9aa1708

Browse files
authored
Some Fixes for Scatter Charts (#2828)
* Some Fixes for Scatter Charts Chart issues have been pouring in recently. This is a partial response to issue #2762. It implements "no joins" for scatter charts, as well as having the reader and writer handle "point size", "line width", and "color" for markers. A new boolean property `scatterLines`, with setter and getter, is added to DataSeriesValues to handle joins (default is true which means scatter plot points *are* joined by lines). Some, but not yet all, default font properties for the chart title are handled (color and, surprisingly, font name present challenges). With these changes, sample 32readwriteScatterChart1.xlsx now looks closer to its source. There are still some differences (x-axis changes), but I think this change is already large enough. I can work on the other problems later. The code for reading charts has not yet been converted to be namespace aware. Having a tiny island of aware code in a sea of unaware makes no sense to me, so some of the new code is likewise unaware. I hope to be able to get to it eventually, but, among other considerations, it is difficult to generate suitable test cases. * Add Formal Tests Essentially the same as the corresponding Samples, but with formal assertions. * Clean Up Some Code in Reader/Xlsx/Chart Having added code to support default font attributes as well as element-specific font attributes for chart captions, there was duplicated code between the default and specific sections. I hope that this PR makes the code easier to follow. * Add Support for Font Name and Color to XLSX Chart Titles XML layout for these in new files differs from what program was expecting. Not sure if program expectations were wrong, or if this is a change to Excel since initial development. * Minor Improvement Handle theoretical case where Chart title has text but no font information. * Support Bezier Curve and Scaling of X-Axis on Scatter Plot For Bezier, need to specify `<c:smooth>` tag in addition to already supplied `<c:scatterStyle val="smoothMarker">` For X-Axis, scatter needs to supply both X and y axis as `<c:valAx>` rather than `<c:catAx>` for X.
1 parent 4df236a commit 9aa1708

File tree

9 files changed

+613
-195
lines changed

9 files changed

+613
-195
lines changed

phpstan-baseline.neon

Lines changed: 5 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -1215,26 +1215,6 @@ parameters:
12151215
count: 2
12161216
path: src/PhpSpreadsheet/Chart/DataSeries.php
12171217

1218-
-
1219-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\DataSeriesValues\\:\\:refresh\\(\\) has parameter \\$flatten with no type specified\\.$#"
1220-
count: 1
1221-
path: src/PhpSpreadsheet/Chart/DataSeriesValues.php
1222-
1223-
-
1224-
message: "#^Property PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\DataSeriesValues\\:\\:\\$dataSource \\(string\\) does not accept string\\|null\\.$#"
1225-
count: 1
1226-
path: src/PhpSpreadsheet/Chart/DataSeriesValues.php
1227-
1228-
-
1229-
message: "#^Property PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\DataSeriesValues\\:\\:\\$dataTypeValues has no type specified\\.$#"
1230-
count: 1
1231-
path: src/PhpSpreadsheet/Chart/DataSeriesValues.php
1232-
1233-
-
1234-
message: "#^Property PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\DataSeriesValues\\:\\:\\$fillColor \\(array\\<string\\>\\|string\\) does not accept array\\<string\\>\\|string\\|null\\.$#"
1235-
count: 1
1236-
path: src/PhpSpreadsheet/Chart/DataSeriesValues.php
1237-
12381218
-
12391219
message: "#^Parameter \\#1 \\$angle of method PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\GridLines\\:\\:setShadowAngle\\(\\) expects int, int\\|null given\\.$#"
12401220
count: 1
@@ -2560,56 +2540,6 @@ parameters:
25602540
count: 1
25612541
path: src/PhpSpreadsheet/Reader/Xlsx/BaseParserClass.php
25622542

2563-
-
2564-
message: "#^Cannot call method getFont\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\RichText\\\\Run\\|null\\.$#"
2565-
count: 12
2566-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2567-
2568-
-
2569-
message: "#^Cannot call method setBold\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2570-
count: 1
2571-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2572-
2573-
-
2574-
message: "#^Cannot call method setColor\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2575-
count: 1
2576-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2577-
2578-
-
2579-
message: "#^Cannot call method setItalic\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2580-
count: 1
2581-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2582-
2583-
-
2584-
message: "#^Cannot call method setName\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2585-
count: 1
2586-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2587-
2588-
-
2589-
message: "#^Cannot call method setSize\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2590-
count: 1
2591-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2592-
2593-
-
2594-
message: "#^Cannot call method setStrikethrough\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2595-
count: 2
2596-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2597-
2598-
-
2599-
message: "#^Cannot call method setSubscript\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2600-
count: 1
2601-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2602-
2603-
-
2604-
message: "#^Cannot call method setSuperscript\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2605-
count: 1
2606-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2607-
2608-
-
2609-
message: "#^Cannot call method setUnderline\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
2610-
count: 3
2611-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2612-
26132543
-
26142544
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:chartDataSeries\\(\\) has no return type specified\\.$#"
26152545
count: 1
@@ -2635,11 +2565,6 @@ parameters:
26352565
count: 1
26362566
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
26372567

2638-
-
2639-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:chartDataSeriesValueSet\\(\\) has parameter \\$marker with no type specified\\.$#"
2640-
count: 1
2641-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2642-
26432568
-
26442569
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:chartDataSeriesValueSet\\(\\) has parameter \\$namespacesChartMeta with no type specified\\.$#"
26452570
count: 1
@@ -2715,21 +2640,6 @@ parameters:
27152640
count: 1
27162641
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
27172642

2718-
-
2719-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:readColor\\(\\) has no return type specified\\.$#"
2720-
count: 1
2721-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2722-
2723-
-
2724-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:readColor\\(\\) has parameter \\$background with no type specified\\.$#"
2725-
count: 1
2726-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2727-
2728-
-
2729-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Reader\\\\Xlsx\\\\Chart\\:\\:readColor\\(\\) has parameter \\$color with no type specified\\.$#"
2730-
count: 1
2731-
path: src/PhpSpreadsheet/Reader/Xlsx/Chart.php
2732-
27332643
-
27342644
message: "#^Parameter \\#1 \\$position of class PhpOffice\\\\PhpSpreadsheet\\\\Chart\\\\Legend constructor expects string, bool\\|float\\|int\\|string\\|null given\\.$#"
27352645
count: 1
@@ -4997,7 +4907,7 @@ parameters:
49974907

49984908
-
49994909
message: "#^Cannot call method getBold\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
5000-
count: 2
4910+
count: 1
50014911
path: src/PhpSpreadsheet/Writer/Xlsx/StringTable.php
50024912

50034913
-
@@ -5007,12 +4917,12 @@ parameters:
50074917

50084918
-
50094919
message: "#^Cannot call method getItalic\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
5010-
count: 2
4920+
count: 1
50114921
path: src/PhpSpreadsheet/Writer/Xlsx/StringTable.php
50124922

50134923
-
50144924
message: "#^Cannot call method getName\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
5015-
count: 2
4925+
count: 1
50164926
path: src/PhpSpreadsheet/Writer/Xlsx/StringTable.php
50174927

50184928
-
@@ -5022,7 +4932,7 @@ parameters:
50224932

50234933
-
50244934
message: "#^Cannot call method getStrikethrough\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
5025-
count: 2
4935+
count: 1
50264936
path: src/PhpSpreadsheet/Writer/Xlsx/StringTable.php
50274937

50284938
-
@@ -5037,7 +4947,7 @@ parameters:
50374947

50384948
-
50394949
message: "#^Cannot call method getUnderline\\(\\) on PhpOffice\\\\PhpSpreadsheet\\\\Style\\\\Font\\|null\\.$#"
5040-
count: 2
4950+
count: 1
50414951
path: src/PhpSpreadsheet/Writer/Xlsx/StringTable.php
50424952

50434953
-
30.9 KB
Binary file not shown.

src/PhpSpreadsheet/Chart/DataSeriesValues.php

Lines changed: 30 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ class DataSeriesValues
1212
const DATASERIES_TYPE_STRING = 'String';
1313
const DATASERIES_TYPE_NUMBER = 'Number';
1414

15-
private static $dataTypeValues = [
15+
private const DATA_TYPE_VALUES = [
1616
self::DATASERIES_TYPE_STRING,
1717
self::DATASERIES_TYPE_NUMBER,
1818
];
@@ -27,7 +27,7 @@ class DataSeriesValues
2727
/**
2828
* Series Data Source.
2929
*
30-
* @var string
30+
* @var ?string
3131
*/
3232
private $dataSource;
3333

@@ -69,7 +69,7 @@ class DataSeriesValues
6969
/**
7070
* Fill color (can be array with colors if dataseries have custom colors).
7171
*
72-
* @var string|string[]
72+
* @var null|string|string[]
7373
*/
7474
private $fillColor;
7575

@@ -80,6 +80,9 @@ class DataSeriesValues
8080
*/
8181
private $lineWidth = 12700;
8282

83+
/** @var bool */
84+
private $scatterLines = true;
85+
8386
/**
8487
* Create a new DataSeriesValues object.
8588
*
@@ -90,8 +93,9 @@ class DataSeriesValues
9093
* @param mixed $dataValues
9194
* @param null|mixed $marker
9295
* @param null|string|string[] $fillColor
96+
* @param string $pointSize
9397
*/
94-
public function __construct($dataType = self::DATASERIES_TYPE_NUMBER, $dataSource = null, $formatCode = null, $pointCount = 0, $dataValues = [], $marker = null, $fillColor = null)
98+
public function __construct($dataType = self::DATASERIES_TYPE_NUMBER, $dataSource = null, $formatCode = null, $pointCount = 0, $dataValues = [], $marker = null, $fillColor = null, $pointSize = '3')
9599
{
96100
$this->setDataType($dataType);
97101
$this->dataSource = $dataSource;
@@ -100,6 +104,9 @@ public function __construct($dataType = self::DATASERIES_TYPE_NUMBER, $dataSourc
100104
$this->dataValues = $dataValues;
101105
$this->pointMarker = $marker;
102106
$this->fillColor = $fillColor;
107+
if (is_numeric($pointSize)) {
108+
$this->pointSize = (int) $pointSize;
109+
}
103110
}
104111

105112
/**
@@ -126,7 +133,7 @@ public function getDataType()
126133
*/
127134
public function setDataType($dataType)
128135
{
129-
if (!in_array($dataType, self::$dataTypeValues)) {
136+
if (!in_array($dataType, self::DATA_TYPE_VALUES)) {
130137
throw new Exception('Invalid datatype for chart data series values');
131138
}
132139
$this->dataType = $dataType;
@@ -137,7 +144,7 @@ public function setDataType($dataType)
137144
/**
138145
* Get Series Data Source (formula).
139146
*
140-
* @return string
147+
* @return ?string
141148
*/
142149
public function getDataSource()
143150
{
@@ -147,7 +154,7 @@ public function getDataSource()
147154
/**
148155
* Set Series Data Source (formula).
149156
*
150-
* @param string $dataSource
157+
* @param ?string $dataSource
151158
*
152159
* @return $this
153160
*/
@@ -239,7 +246,7 @@ public function getPointCount()
239246
/**
240247
* Get fill color.
241248
*
242-
* @return string|string[] HEX color or array with HEX colors
249+
* @return null|string|string[] HEX color or array with HEX colors
243250
*/
244251
public function getFillColor()
245252
{
@@ -249,7 +256,7 @@ public function getFillColor()
249256
/**
250257
* Set fill color for series.
251258
*
252-
* @param string|string[] $color HEX color or array with HEX colors
259+
* @param null|string|string[] $color HEX color or array with HEX colors
253260
*
254261
* @return DataSeriesValues
255262
*/
@@ -260,7 +267,7 @@ public function setFillColor($color)
260267
$this->validateColor($colorValue);
261268
}
262269
} else {
263-
$this->validateColor($color);
270+
$this->validateColor("$color");
264271
}
265272
$this->fillColor = $color;
266273

@@ -379,7 +386,7 @@ public function setDataValues($dataValues)
379386
return $this;
380387
}
381388

382-
public function refresh(Worksheet $worksheet, $flatten = true): void
389+
public function refresh(Worksheet $worksheet, bool $flatten = true): void
383390
{
384391
if ($this->dataSource !== null) {
385392
$calcEngine = Calculation::getInstance($worksheet->getParent());
@@ -421,4 +428,16 @@ public function refresh(Worksheet $worksheet, $flatten = true): void
421428
$this->pointCount = count($this->dataValues);
422429
}
423430
}
431+
432+
public function getScatterLines(): bool
433+
{
434+
return $this->scatterLines;
435+
}
436+
437+
public function setScatterLines(bool $scatterLines): self
438+
{
439+
$this->scatterLines = $scatterLines;
440+
441+
return $this;
442+
}
424443
}

0 commit comments

Comments
 (0)