Charts - Add Support for Date Axis (#3018)

* Charts - Add Support for Date Axis

Fix #2967. Fix #2969 (which had already been fixed prior to opening the issue, but had added urgency for Date Axes). Add ability to set axis type to date axis, in addition to original possiblities of value axis and category axis.

* Update 33_Chart_create_line_dateaxis.php

No idea why php-cs-fixer is complaining. It didn't do so when I first uploaded. I can't duplicate problem on my own system. Not enough detail in error message for me to act. Grasping at straws, I have moved the function definition (which is the only use of braces in the entire script) from the end of the script to the beginning.

* Update 33_Chart_create_line_dateaxis.php

Some comments were mis-aligned. This may be related to the reasons behind PR #3025, which didn't take care of this because this script had not yet been merged.
This commit is contained in:
oleibman 2022-08-24 19:31:55 -07:00 committed by GitHub
parent e97428ba67
commit 3861f7e37e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 500 additions and 25 deletions

View File

@ -0,0 +1,375 @@
<?php
namespace PhpOffice\PhpSpreadsheet\Chart;
use DateTime;
use PhpOffice\PhpSpreadsheet\Chart\Legend as ChartLegend;
use PhpOffice\PhpSpreadsheet\IOFactory;
use PhpOffice\PhpSpreadsheet\Shared\Date as SharedDate;
use PhpOffice\PhpSpreadsheet\Spreadsheet;
require __DIR__ . '/../Header.php';
$spreadsheet = new Spreadsheet();
$dataSheet = $spreadsheet->getActiveSheet();
$dataSheet->setTitle('Data');
// changed data to simulate a trend chart - Xaxis are dates; Yaxis are 3 meausurements from each date
// Dates changed not to fall on exact quarter start
$dataSheet->fromArray(
[
['', 'date', 'metric1', 'metric2', 'metric3'],
['=DATEVALUE(B2)', '2021-01-10', 12.1, 15.1, 21.1],
['=DATEVALUE(B3)', '2021-04-21', 56.2, 73.2, 86.2],
['=DATEVALUE(B4)', '2021-07-31', 52.2, 61.2, 69.2],
['=DATEVALUE(B5)', '2021-10-11', 30.2, 22.2, 0.2],
['=DATEVALUE(B6)', '2022-01-21', 40.1, 38.1, 65.1],
['=DATEVALUE(B7)', '2022-04-11', 45.2, 44.2, 96.2],
['=DATEVALUE(B8)', '2022-07-01', 52.2, 51.2, 55.2],
['=DATEVALUE(B9)', '2022-10-31', 41.2, 72.2, 56.2],
]
);
$dataSheet->getStyle('A2:A9')->getNumberFormat()->setFormatCode(Properties::FORMAT_CODE_DATE_ISO8601);
$dataSheet->getColumnDimension('A')->setAutoSize(true);
$dataSheet->getColumnDimension('B')->setAutoSize(true);
$dataSheet->setSelectedCells('A1');
// Set the Labels for each data series we want to plot
// Datatype
// Cell reference for data
// Format Code
// Number of datapoints in series
$dataSeriesLabels = [
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_STRING, 'Data!$C$1', null, 1),
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_STRING, 'Data!$D$1', null, 1),
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_STRING, 'Data!$E$1', null, 1),
];
// Set the X-Axis Labels
// NUMBER, not STRING
// added x-axis values for each of the 3 metrics
// added FORMATE_CODE_NUMBER
// Number of datapoints in series
$xAxisTickValues = [
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_NUMBER, 'Data!$A$2:$A$9', Properties::FORMAT_CODE_DATE_ISO8601, 8),
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_NUMBER, 'Data!$A$2:$A$9', Properties::FORMAT_CODE_DATE_ISO8601, 8),
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_NUMBER, 'Data!$A$2:$A$9', Properties::FORMAT_CODE_DATE_ISO8601, 8),
];
// Set the Data values for each data series we want to plot
// Datatype
// Cell reference for data
// Format Code
// Number of datapoints in series
// Data values
// Data Marker
// Data Marker Color fill/[fill,Border]
// Data Marker size
// Color(s) added
// added FORMAT_CODE_NUMBER
$dataSeriesValues = [
new DataSeriesValues(
DataSeriesValues::DATASERIES_TYPE_NUMBER,
'Data!$C$2:$C$9',
Properties::FORMAT_CODE_NUMBER,
8,
null,
'diamond',
null,
5
),
new DataSeriesValues(
DataSeriesValues::DATASERIES_TYPE_NUMBER,
'Data!$D$2:$D$9',
Properties::FORMAT_CODE_NUMBER,
8,
null,
'square',
'*accent1',
6
),
new DataSeriesValues(
DataSeriesValues::DATASERIES_TYPE_NUMBER,
'Data!$E$2:$E$9',
Properties::FORMAT_CODE_NUMBER,
8,
null,
null,
null,
7
), // let Excel choose marker shape
];
// series 1 - metric1
// marker details
$dataSeriesValues[0]
->getMarkerFillColor()
->setColorProperties('0070C0', null, ChartColor::EXCEL_COLOR_TYPE_ARGB);
$dataSeriesValues[0]
->getMarkerBorderColor()
->setColorProperties('002060', null, ChartColor::EXCEL_COLOR_TYPE_ARGB);
// line details - dashed, smooth line (Bezier) with arrows, 40% transparent
$dataSeriesValues[0]
->setSmoothLine(true)
->setScatterLines(true)
->setLineColorProperties('accent1', 40, ChartColor::EXCEL_COLOR_TYPE_SCHEME); // value, alpha, type
$dataSeriesValues[0]->setLineStyleProperties(
2.5, // width in points
Properties::LINE_STYLE_COMPOUND_TRIPLE, // compound
Properties::LINE_STYLE_DASH_SQUARE_DOT, // dash
Properties::LINE_STYLE_CAP_SQUARE, // cap
Properties::LINE_STYLE_JOIN_MITER, // join
Properties::LINE_STYLE_ARROW_TYPE_OPEN, // head type
Properties::LINE_STYLE_ARROW_SIZE_4, // head size preset index
Properties::LINE_STYLE_ARROW_TYPE_ARROW, // end type
Properties::LINE_STYLE_ARROW_SIZE_6 // end size preset index
);
// series 2 - metric2, straight line - no special effects, connected
$dataSeriesValues[1] // square marker border color
->getMarkerBorderColor()
->setColorProperties('accent6', 3, ChartColor::EXCEL_COLOR_TYPE_SCHEME);
$dataSeriesValues[1] // square marker fill color
->getMarkerFillColor()
->setColorProperties('0FFF00', null, ChartColor::EXCEL_COLOR_TYPE_ARGB);
$dataSeriesValues[1]
->setScatterLines(true)
->setSmoothLine(false)
->setLineColorProperties('FF0000', 80, ChartColor::EXCEL_COLOR_TYPE_ARGB);
$dataSeriesValues[1]->setLineWidth(2.0);
// series 3 - metric3, markers, no line
$dataSeriesValues[2] // triangle? fill
//->setPointMarker('triangle') // let Excel choose shape, which is predicted to be a triangle
->getMarkerFillColor()
->setColorProperties('FFFF00', null, ChartColor::EXCEL_COLOR_TYPE_ARGB);
$dataSeriesValues[2] // triangle border
->getMarkerBorderColor()
->setColorProperties('accent4', null, ChartColor::EXCEL_COLOR_TYPE_SCHEME);
$dataSeriesValues[2]->setScatterLines(false); // points not connected
// Added so that Xaxis shows dates instead of Excel-equivalent-year1900-numbers
$xAxis = new Axis();
$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE_ISO8601);
// Build the dataseries
$series = new DataSeries(
DataSeries::TYPE_SCATTERCHART, // plotType
null, // plotGrouping (Scatter charts don't have grouping)
range(0, count($dataSeriesValues) - 1), // plotOrder
$dataSeriesLabels, // plotLabel
$xAxisTickValues, // plotCategory
$dataSeriesValues, // plotValues
null, // plotDirection
null, // smooth line
DataSeries::STYLE_SMOOTHMARKER // plotStyle
);
// Set the series in the plot area
$plotArea = new PlotArea(null, [$series]);
// Set the chart legend
$legend = new ChartLegend(ChartLegend::POSITION_TOPRIGHT, null, false);
$title = new Title('Test Scatter Chart');
$yAxisLabel = new Title('Value ($k)');
$yAxis = new Axis();
$yAxis->setMajorGridlines(new GridLines());
// Create the chart
$chart = new Chart(
'chart1', // name
$title, // title
$legend, // legend
$plotArea, // plotArea
true, // plotVisibleOnly
DataSeries::EMPTY_AS_GAP, // displayBlanksAs
null, // xAxisLabel
$yAxisLabel, // yAxisLabel
// added xAxis for correct date display
$xAxis, // xAxis
$yAxis, // yAxis
);
// Set the position of the chart in the chart sheet
$chart->setTopLeftPosition('A1');
$chart->setBottomRightPosition('P12');
// create a 'Chart' worksheet, add $chart to it
$spreadsheet->createSheet();
$chartSheet = $spreadsheet->getSheet(1);
$chartSheet->setTitle('Scatter+Line Chart');
$chartSheet = $spreadsheet->getSheetByName('Scatter+Line Chart');
// Add the chart to the worksheet
$chartSheet->addChart($chart);
// ------- Demonstrate Date Xaxis in Line Chart, not possible using Scatter Chart ------------
// Set the Labels (Column header) for each data series we want to plot
$dataSeriesLabels = [
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_STRING, 'Data!$E$1', null, 1),
];
// Set the X-Axis Labels - dates, N.B. 01/10/2021 === Jan 10, NOT Oct 1 !!
// x-axis values are the Excel numeric representation of the date - so set
// formatCode=General for the xAxis VALUES, but we want the labels to be
// DISPLAYED as 'yyyy-mm-dd' That is, read a number, display a date.
$xAxisTickValues = [
new DataSeriesValues(DataSeriesValues::DATASERIES_TYPE_NUMBER, 'Data!$A$2:$A$9', Properties::FORMAT_CODE_DATE_ISO8601, 8),
];
// X axis (date) settings
$xAxisLabel = new Title('Date');
$xAxis = new Axis();
$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE_ISO8601); // yyyy-mm-dd
// Set the Data values for each data series we want to plot
$dataSeriesValues = [
new DataSeriesValues(
DataSeriesValues::DATASERIES_TYPE_NUMBER,
'Data!$E$2:$E$9',
Properties::FORMAT_CODE_NUMBER,
8,
null,
'triangle',
null,
7
),
];
// series - metric3, markers, no line
$dataSeriesValues[0]
->setScatterlines(false); // disable connecting lines
$dataSeriesValues[0]
->getMarkerFillColor()
->setColorProperties('FFFF00', null, ChartColor::EXCEL_COLOR_TYPE_ARGB);
$dataSeriesValues[0]
->getMarkerBorderColor()
->setColorProperties('accent4', null, ChartColor::EXCEL_COLOR_TYPE_SCHEME);
// Build the dataseries
// must now use LineChart instead of ScatterChart, since ScatterChart does not
// support "dateAx" axis type.
$series = new DataSeries(
DataSeries::TYPE_LINECHART, // plotType
'standard', // plotGrouping
range(0, count($dataSeriesValues) - 1), // plotOrder
$dataSeriesLabels, // plotLabel
$xAxisTickValues, // plotCategory
$dataSeriesValues, // plotValues
null, // plotDirection
false, // smooth line
DataSeries::STYLE_LINEMARKER // plotStyle
// DataSeries::STYLE_SMOOTHMARKER // plotStyle
);
// Set the series in the plot area
$plotArea = new PlotArea(null, [$series]);
// Set the chart legend
$legend = new ChartLegend(ChartLegend::POSITION_RIGHT, null, false);
$title = new Title('Test Line-Chart with Date Axis - metric3 values');
// X axis (date) settings
$xAxisLabel = new Title('Game Date');
$xAxis = new Axis();
// date axis values are Excel numbers, not yyyy-mm-dd Date strings
$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE_ISO8601);
$xAxis->setAxisType('dateAx'); // dateAx available ONLY for LINECHART, not SCATTERCHART
// measure the time span in Quarters, of data.
$dateMinMax = dateRange(8, $spreadsheet); // array 'min'=>earliest date of first Q, 'max'=>latest date of final Q
// change xAxis tick marks to match Qtr boundaries
$nQtrs = sprintf('%3.2f', (($dateMinMax['max'] - $dateMinMax['min']) / 30.5) / 4);
$tickMarkInterval = ($nQtrs > 20) ? 6 : 3; // tick marks every ? months
$xAxis->setAxisOptionsProperties(
Properties::AXIS_LABELS_NEXT_TO, // axis_label pos
null, // horizontalCrossesValue
null, // horizontalCrosses
null, // axisOrientation
'in', // major_tick_mark
null, // minor_tick_mark
$dateMinMax['min'], // minimum calculate this from the earliest data: 'Data!$A$2'
$dateMinMax['max'], // maximum calculate this from the last data: 'Data!$A$'.($nrows+1)
$tickMarkInterval, // majorUnit determines tickmarks & Gridlines ?
null, // minorUnit
null, // textRotation
null, // hidden
'days', // baseTimeUnit
'months', // majorTimeUnit,
'months', // minorTimeUnit
);
$yAxisLabel = new Title('Value ($k)');
$yAxis = new Axis();
$yAxis->setMajorGridlines(new GridLines());
$xAxis->setMajorGridlines(new GridLines());
$minorGridLines = new GridLines();
$minorGridLines->activateObject();
$xAxis->setMinorGridlines($minorGridLines);
// Create the chart
$chart = new Chart(
'chart2', // name
$title, // title
$legend, // legend
$plotArea, // plotArea
true, // plotVisibleOnly
DataSeries::EMPTY_AS_GAP, // displayBlanksAs
null, // xAxisLabel
$yAxisLabel, // yAxisLabel
// added xAxis for correct date display
$xAxis, // xAxis
$yAxis, // yAxis
);
// Set the position of the chart in the chart sheet below the first chart
$chart->setTopLeftPosition('A13');
$chart->setBottomRightPosition('P25');
$chart->setRoundedCorners('true'); // Rounded corners in Chart Outline
// Add the chart to the worksheet $chartSheet
$chartSheet->addChart($chart);
$spreadsheet->setActiveSheetIndex(1);
// Save Excel 2007 file
$filename = $helper->getFilename(__FILE__);
$writer = IOFactory::createWriter($spreadsheet, 'Xlsx');
$writer->setIncludeCharts(true);
$callStartTime = microtime(true);
$writer->save($filename);
$helper->logWrite($writer, $filename, $callStartTime);
$spreadsheet->disconnectWorksheets();
function dateRange(int $nrows, Spreadsheet $wrkbk): array
{
$dataSheet = $wrkbk->getSheetByName('Data');
// start the xaxis at the beginning of the quarter of the first date
$startDateStr = $dataSheet->getCell('B2')->getValue(); // yyyy-mm-dd date string
$startDate = DateTime::createFromFormat('Y-m-d', $startDateStr); // php date obj
// get date of first day of the quarter of the start date
$startMonth = $startDate->format('n'); // suppress leading zero
$startYr = $startDate->format('Y');
$qtr = intdiv($startMonth, 3) + (($startMonth % 3 > 0) ? 1 : 0);
$qtrStartMonth = sprintf('%02d', 1 + (($qtr - 1) * 3));
$qtrStartStr = "$startYr-$qtrStartMonth-01";
$ExcelQtrStartDateVal = SharedDate::convertIsoDate($qtrStartStr);
// end the xaxis at the end of the quarter of the last date
$lastDateStr = $dataSheet->getCellByColumnAndRow(2, $nrows + 1)->getValue();
$lastDate = DateTime::createFromFormat('Y-m-d', $lastDateStr);
$lastMonth = $lastDate->format('n');
$lastYr = $lastDate->format('Y');
$qtr = intdiv($lastMonth, 3) + (($lastMonth % 3 > 0) ? 1 : 0);
$qtrEndMonth = 3 + (($qtr - 1) * 3);
$lastDOM = cal_days_in_month(CAL_GREGORIAN, $qtrEndMonth, $lastYr);
$qtrEndMonth = sprintf('%02d', $qtrEndMonth);
$qtrEndStr = "$lastYr-$qtrEndMonth-$lastDOM";
$ExcelQtrEndDateVal = SharedDate::convertIsoDate($qtrEndStr);
$minMaxDates = ['min' => $ExcelQtrStartDateVal, 'max' => $ExcelQtrEndDateVal];
return $minMaxDates;
}

View File

@ -263,6 +263,7 @@ $chart->setBottomRightPosition('P25');
// Add the chart to the worksheet $chartSheet
$chartSheet->addChart($chart);
$spreadsheet->setActiveSheetIndex(1);
// Save Excel 2007 file
$filename = $helper->getFilename(__FILE__);

Binary file not shown.

View File

@ -10,6 +10,14 @@ namespace PhpOffice\PhpSpreadsheet\Chart;
*/
class Axis extends Properties
{
const AXIS_TYPE_CATEGORY = 'catAx';
const AXIS_TYPE_DATE = 'dateAx';
const AXIS_TYPE_VALUE = 'valAx';
const TIME_UNIT_DAYS = 'days';
const TIME_UNIT_MONTHS = 'months';
const TIME_UNIT_YEARS = 'years';
public function __construct()
{
parent::__construct();
@ -62,6 +70,9 @@ class Axis extends Properties
'horizontal_crosses_value' => null,
'textRotation' => null,
'hidden' => null,
'majorTimeUnit' => self::TIME_UNIT_YEARS,
'minorTimeUnit' => self::TIME_UNIT_MONTHS,
'baseTimeUnit' => self::TIME_UNIT_DAYS,
];
/**
@ -74,6 +85,7 @@ class Axis extends Properties
private const NUMERIC_FORMAT = [
Properties::FORMAT_CODE_NUMBER,
Properties::FORMAT_CODE_DATE,
Properties::FORMAT_CODE_DATE_ISO8601,
];
/**
@ -115,12 +127,12 @@ class Axis extends Properties
public function getAxisIsNumericFormat(): bool
{
return (bool) $this->axisNumber['numeric'];
return $this->axisType === self::AXIS_TYPE_DATE || (bool) $this->axisNumber['numeric'];
}
public function setAxisOption(string $key, ?string $value): void
{
if (!empty($value)) {
if ($value !== null && $value !== '') {
$this->axisOptions[$key] = $value;
}
}
@ -140,7 +152,10 @@ class Axis extends Properties
?string $majorUnit = null,
?string $minorUnit = null,
?string $textRotation = null,
?string $hidden = null
?string $hidden = null,
?string $baseTimeUnit = null,
?string $majorTimeUnit = null,
?string $minorTimeUnit = null
): void {
$this->axisOptions['axis_labels'] = $axisLabels;
$this->setAxisOption('horizontal_crosses_value', $horizontalCrossesValue);
@ -154,6 +169,9 @@ class Axis extends Properties
$this->setAxisOption('minor_unit', $minorUnit);
$this->setAxisOption('textRotation', $textRotation);
$this->setAxisOption('hidden', $hidden);
$this->setAxisOption('baseTimeUnit', $baseTimeUnit);
$this->setAxisOption('majorTimeUnit', $majorTimeUnit);
$this->setAxisOption('minorTimeUnit', $minorTimeUnit);
}
/**
@ -185,7 +203,7 @@ class Axis extends Properties
public function setAxisType(string $type): self
{
if ($type === 'catAx' || $type === 'valAx') {
if ($type === self::AXIS_TYPE_CATEGORY || $type === self::AXIS_TYPE_VALUE || $type === self::AXIS_TYPE_DATE) {
$this->axisType = $type;
} else {
$this->axisType = '';

View File

@ -139,12 +139,13 @@ class Chart
$plotAreaLayout = $this->chartLayoutDetails($chartDetail);
break;
case 'catAx':
case Axis::AXIS_TYPE_CATEGORY:
case Axis::AXIS_TYPE_DATE:
$catAxRead = true;
if (isset($chartDetail->title)) {
$XaxisLabel = $this->chartTitle($chartDetail->title->children($this->cNamespace));
}
$xAxis->setAxisType('catAx');
$xAxis->setAxisType($chartDetailKey);
$this->readEffects($chartDetail, $xAxis);
if (isset($chartDetail->spPr)) {
$sppr = $chartDetail->spPr->children($this->aNamespace);
@ -173,13 +174,7 @@ class Chart
$this->setAxisProperties($chartDetail, $xAxis);
break;
case 'dateAx':
if (isset($chartDetail->title)) {
$XaxisLabel = $this->chartTitle($chartDetail->title->children($this->cNamespace));
}
break;
case 'valAx':
case Axis::AXIS_TYPE_VALUE:
$whichAxis = null;
$axPos = null;
if (isset($chartDetail->axPos)) {
@ -1375,6 +1370,15 @@ class Chart
if (isset($chartDetail->minorUnit)) {
$whichAxis->setAxisOption('minor_unit', (string) self::getAttribute($chartDetail->minorUnit, 'val', 'string'));
}
if (isset($chartDetail->baseTimeUnit)) {
$whichAxis->setAxisOption('baseTimeUnit', (string) self::getAttribute($chartDetail->baseTimeUnit, 'val', 'string'));
}
if (isset($chartDetail->majorTimeUnit)) {
$whichAxis->setAxisOption('majorTimeUnit', (string) self::getAttribute($chartDetail->majorTimeUnit, 'val', 'string'));
}
if (isset($chartDetail->minorTimeUnit)) {
$whichAxis->setAxisOption('minorTimeUnit', (string) self::getAttribute($chartDetail->minorTimeUnit, 'val', 'string'));
}
if (isset($chartDetail->txPr)) {
$children = $chartDetail->txPr->children($this->aNamespace);
if (isset($children->bodyPr)) {

View File

@ -490,13 +490,14 @@ class Chart extends WriterPart
private function writeCategoryAxis(XMLWriter $objWriter, ?Title $xAxisLabel, $id1, $id2, $isMultiLevelSeries, Axis $yAxis): void
{
// N.B. writeCategoryAxis may be invoked with the last parameter($yAxis) using $xAxis for ScatterChart, etc
// In that case, xAxis is NOT a category.
if ($yAxis->getAxisType() !== '') {
$objWriter->startElement('c:' . $yAxis->getAxisType());
// In that case, xAxis may contain values like the yAxis, or it may be a date axis (LINECHART).
$axisType = $yAxis->getAxisType();
if ($axisType !== '') {
$objWriter->startElement("c:$axisType");
} elseif ($yAxis->getAxisIsNumericFormat()) {
$objWriter->startElement('c:valAx');
$objWriter->startElement('c:' . Axis::AXIS_TYPE_VALUE);
} else {
$objWriter->startElement('c:catAx');
$objWriter->startElement('c:' . Axis::AXIS_TYPE_CATEGORY);
}
$majorGridlines = $yAxis->getMajorGridlines();
$minorGridlines = $yAxis->getMinorGridlines();
@ -654,7 +655,8 @@ class Chart extends WriterPart
}
$objWriter->startElement('c:auto');
$objWriter->writeAttribute('val', '1');
// LineChart with dateAx wants '0'
$objWriter->writeAttribute('val', ($axisType === Axis::AXIS_TYPE_DATE) ? '0' : '1');
$objWriter->endElement();
$objWriter->startElement('c:lblAlgn');
@ -665,6 +667,30 @@ class Chart extends WriterPart
$objWriter->writeAttribute('val', '100');
$objWriter->endElement();
if ($axisType === Axis::AXIS_TYPE_DATE) {
$property = 'baseTimeUnit';
$propertyVal = $yAxis->getAxisOptionsProperty($property);
if (!empty($propertyVal)) {
$objWriter->startElement("c:$property");
$objWriter->writeAttribute('val', $propertyVal);
$objWriter->endElement();
}
$property = 'majorTimeUnit';
$propertyVal = $yAxis->getAxisOptionsProperty($property);
if (!empty($propertyVal)) {
$objWriter->startElement("c:$property");
$objWriter->writeAttribute('val', $propertyVal);
$objWriter->endElement();
}
$property = 'minorTimeUnit';
$propertyVal = $yAxis->getAxisOptionsProperty($property);
if (!empty($propertyVal)) {
$objWriter->startElement("c:$property");
$objWriter->writeAttribute('val', $propertyVal);
$objWriter->endElement();
}
}
if ($isMultiLevelSeries) {
$objWriter->startElement('c:noMultiLvlLbl');
$objWriter->writeAttribute('val', '0');
@ -683,7 +709,7 @@ class Chart extends WriterPart
*/
private function writeValueAxis(XMLWriter $objWriter, ?Title $yAxisLabel, $groupType, $id1, $id2, $isMultiLevelSeries, Axis $xAxis): void
{
$objWriter->startElement('c:valAx');
$objWriter->startElement('c:' . Axis::AXIS_TYPE_VALUE);
$majorGridlines = $xAxis->getMajorGridlines();
$minorGridlines = $xAxis->getMinorGridlines();
@ -1079,7 +1105,7 @@ class Chart extends WriterPart
$objWriter->endElement(); // a:ln
}
}
$nofill = $groupType == DataSeries::TYPE_STOCKCHART || ($groupType === DataSeries::TYPE_SCATTERCHART && !$plotSeriesValues->getScatterLines());
$nofill = $groupType === DataSeries::TYPE_STOCKCHART || (($groupType === DataSeries::TYPE_SCATTERCHART || $groupType === DataSeries::TYPE_LINECHART) && !$plotSeriesValues->getScatterLines());
if ($callLineStyles) {
$this->writeLineStyles($objWriter, $plotSeriesValues, $nofill);
$this->writeEffects($objWriter, $plotSeriesValues);

View File

@ -109,7 +109,9 @@ class AxisPropertiesTest extends AbstractFunctional
'8', //minimum
'68', //maximum
'20', //majorUnit
'5' //minorUnit
'5', //minorUnit
'6', //textRotation
'0', //hidden
);
self::assertSame(Properties::AXIS_LABELS_HIGH, $xAxis->getAxisOptionsProperty('axis_labels'));
self::assertNull($xAxis->getAxisOptionsProperty('horizontal_crosses_value'));
@ -121,6 +123,8 @@ class AxisPropertiesTest extends AbstractFunctional
self::assertSame('68', $xAxis->getAxisOptionsProperty('maximum'));
self::assertSame('20', $xAxis->getAxisOptionsProperty('major_unit'));
self::assertSame('5', $xAxis->getAxisOptionsProperty('minor_unit'));
self::assertSame('6', $xAxis->getAxisOptionsProperty('textRotation'));
self::assertSame('0', $xAxis->getAxisOptionsProperty('hidden'));
$yAxis = new Axis();
$yAxis->setFillParameters('accent1', 30, 'schemeClr');
@ -158,6 +162,8 @@ class AxisPropertiesTest extends AbstractFunctional
self::assertSame('68', $xAxis2->getAxisOptionsProperty('maximum'));
self::assertSame('20', $xAxis2->getAxisOptionsProperty('major_unit'));
self::assertSame('5', $xAxis2->getAxisOptionsProperty('minor_unit'));
self::assertSame('6', $xAxis2->getAxisOptionsProperty('textRotation'));
self::assertSame('0', $xAxis2->getAxisOptionsProperty('hidden'));
$yAxis2 = $chart->getChartAxisY();
self::assertSame('accent1', $yAxis2->getFillProperty('value'));
@ -198,6 +204,8 @@ class AxisPropertiesTest extends AbstractFunctional
self::assertSame('68', $xAxis3->getAxisOptionsProperty('maximum'));
self::assertSame('20', $xAxis3->getAxisOptionsProperty('major_unit'));
self::assertSame('5', $xAxis3->getAxisOptionsProperty('minor_unit'));
self::assertSame('6', $xAxis3->getAxisOptionsProperty('textRotation'));
self::assertSame('0', $xAxis3->getAxisOptionsProperty('hidden'));
$yAxis3 = $chart2->getChartAxisY();
self::assertSame('accent1', $yAxis3->getFillProperty('value'));

View File

@ -23,6 +23,8 @@ class Charts32CatAxValAxTest extends TestCase
/** @var string */
private $outputFileName = '';
private const FORMAT_CODE_DATE_ISO8601_SLASH = 'yyyy/mm/dd'; // not automatically treated as numeric
protected function tearDown(): void
{
if ($this->outputFileName !== '') {
@ -48,7 +50,7 @@ class Charts32CatAxValAxTest extends TestCase
['=DATEVALUE("2021-01-10")', 30.2, 32.2, 0.2],
]
);
$worksheet->getStyle('A2:A5')->getNumberFormat()->setFormatCode(Properties::FORMAT_CODE_DATE_ISO8601);
$worksheet->getStyle('A2:A5')->getNumberFormat()->setFormatCode(self::FORMAT_CODE_DATE_ISO8601_SLASH);
$worksheet->getColumnDimension('A')->setAutoSize(true);
$worksheet->setSelectedCells('A1');
@ -91,9 +93,9 @@ class Charts32CatAxValAxTest extends TestCase
$xAxis = new Axis();
//$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE );
if (is_bool($numeric)) {
$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE_ISO8601, $numeric);
$xAxis->setAxisNumberProperties(self::FORMAT_CODE_DATE_ISO8601_SLASH, $numeric);
} else {
$xAxis->setAxisNumberProperties(Properties::FORMAT_CODE_DATE_ISO8601);
$xAxis->setAxisNumberProperties(self::FORMAT_CODE_DATE_ISO8601_SLASH);
}
// Build the dataseries

View File

@ -177,4 +177,45 @@ class Charts32XmlTest extends TestCase
)
);
}
public function testDateAx(): void
{
$file = self::DIRECTORY . '32readwriteLineDateAxisChart1.xlsx';
$reader = new XlsxReader();
$reader->setIncludeCharts(true);
$spreadsheet = $reader->load($file);
$sheet = $spreadsheet->getActiveSheet();
$charts = $sheet->getChartCollection();
self::assertCount(2, $charts);
$chart = $charts[1];
self::assertNotNull($chart);
$writer = new XlsxWriter($spreadsheet);
$writer->setIncludeCharts(true);
$writerChart = new XlsxWriter\Chart($writer);
$data = $writerChart->writeChart($chart);
$spreadsheet->disconnectWorksheets();
self::assertSame(
1,
substr_count(
$data,
'<c:baseTimeUnit val="days"/><c:majorTimeUnit val="months"/><c:minorTimeUnit val="months"/>'
)
);
self::assertSame(
1,
substr_count(
$data,
'<c:dateAx>'
)
);
self::assertSame(
1,
substr_count(
$data,
'<c:valAx>'
)
);
}
}