2016-12-11 09:02:04 -06:00
|
|
|
<?php
|
|
|
|
/**
|
|
|
|
* ChartJsGenerator.php
|
2017-10-21 01:40:00 -05:00
|
|
|
* Copyright (c) 2017 thegrumpydictator@gmail.com
|
2016-12-11 09:02:04 -06:00
|
|
|
*
|
2017-10-21 01:40:00 -05:00
|
|
|
* This file is part of Firefly III.
|
2016-12-11 09:02:04 -06:00
|
|
|
*
|
2017-10-21 01:40:00 -05:00
|
|
|
* Firefly III is free software: you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU General Public License as published by
|
|
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* Firefly III is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
2017-12-17 07:41:58 -06:00
|
|
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
2016-12-11 09:02:04 -06:00
|
|
|
*/
|
2017-04-09 00:44:22 -05:00
|
|
|
declare(strict_types=1);
|
2016-12-11 09:02:04 -06:00
|
|
|
|
|
|
|
namespace FireflyIII\Generator\Chart\Basic;
|
|
|
|
|
2016-12-11 10:05:48 -06:00
|
|
|
use FireflyIII\Support\ChartColour;
|
2017-02-11 08:52:55 -06:00
|
|
|
use Steam;
|
2016-12-11 10:05:48 -06:00
|
|
|
|
2016-12-11 09:02:04 -06:00
|
|
|
/**
|
2017-11-15 05:25:49 -06:00
|
|
|
* Class ChartJsGenerator.
|
2016-12-11 09:02:04 -06:00
|
|
|
*/
|
|
|
|
class ChartJsGenerator implements GeneratorInterface
|
|
|
|
{
|
|
|
|
/**
|
2017-11-15 05:25:49 -06:00
|
|
|
* Will generate a Chart JS compatible array from the given input. Expects this format.
|
2016-12-15 02:49:35 -06:00
|
|
|
*
|
|
|
|
* Will take labels for all from first set.
|
2016-12-11 09:02:04 -06:00
|
|
|
*
|
|
|
|
* 0: [
|
|
|
|
* 'label' => 'label of set',
|
2016-12-11 10:46:30 -06:00
|
|
|
* 'type' => bar or line, optional
|
2016-12-23 00:20:47 -06:00
|
|
|
* 'yAxisID' => ID of yAxis, optional, will not be included when unused.
|
|
|
|
* 'fill' => if to fill a line? optional, will not be included when unused.
|
2016-12-11 09:02:04 -06:00
|
|
|
* 'entries' =>
|
|
|
|
* [
|
|
|
|
* 'label-of-entry' => 'value'
|
|
|
|
* ]
|
|
|
|
* ]
|
|
|
|
* 1: [
|
|
|
|
* 'label' => 'label of another set',
|
2016-12-11 10:46:30 -06:00
|
|
|
* 'type' => bar or line, optional
|
2016-12-23 00:20:47 -06:00
|
|
|
* 'yAxisID' => ID of yAxis, optional, will not be included when unused.
|
|
|
|
* 'fill' => if to fill a line? optional, will not be included when unused.
|
2016-12-11 09:02:04 -06:00
|
|
|
* 'entries' =>
|
|
|
|
* [
|
|
|
|
* 'label-of-entry' => 'value'
|
|
|
|
* ]
|
|
|
|
* ]
|
|
|
|
*
|
2017-01-02 13:42:29 -06:00
|
|
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity) // it's five.
|
2016-12-11 09:02:04 -06:00
|
|
|
*
|
|
|
|
* @param array $data
|
|
|
|
*
|
|
|
|
* @return array
|
|
|
|
*/
|
|
|
|
public function multiSet(array $data): array
|
|
|
|
{
|
2016-12-15 06:47:28 -06:00
|
|
|
reset($data);
|
|
|
|
$first = current($data);
|
2016-12-30 06:45:02 -06:00
|
|
|
$labels = is_array($first['entries']) ? array_keys($first['entries']) : [];
|
2016-12-15 06:47:28 -06:00
|
|
|
|
2016-12-11 09:02:04 -06:00
|
|
|
$chartData = [
|
|
|
|
'count' => count($data),
|
2016-12-15 06:47:28 -06:00
|
|
|
'labels' => $labels, // take ALL labels from the first set.
|
2016-12-11 09:02:04 -06:00
|
|
|
'datasets' => [],
|
|
|
|
];
|
2016-12-15 06:47:28 -06:00
|
|
|
unset($first, $labels);
|
2016-12-11 09:02:04 -06:00
|
|
|
|
|
|
|
foreach ($data as $set) {
|
2016-12-23 00:20:47 -06:00
|
|
|
$currentSet = [
|
2016-12-11 09:02:04 -06:00
|
|
|
'label' => $set['label'],
|
2016-12-11 10:46:30 -06:00
|
|
|
'type' => $set['type'] ?? 'line',
|
2016-12-11 09:02:04 -06:00
|
|
|
'data' => array_values($set['entries']),
|
|
|
|
];
|
2016-12-23 00:20:47 -06:00
|
|
|
if (isset($set['yAxisID'])) {
|
|
|
|
$currentSet['yAxisID'] = $set['yAxisID'];
|
|
|
|
}
|
|
|
|
if (isset($set['fill'])) {
|
|
|
|
$currentSet['fill'] = $set['fill'];
|
|
|
|
}
|
2017-04-15 10:26:03 -05:00
|
|
|
if (isset($set['currency_symbol'])) {
|
|
|
|
$currentSet['currency_symbol'] = $set['currency_symbol'];
|
|
|
|
}
|
2016-12-23 00:20:47 -06:00
|
|
|
|
|
|
|
$chartData['datasets'][] = $currentSet;
|
2016-12-11 09:02:04 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
return $chartData;
|
|
|
|
}
|
2016-12-11 09:25:25 -06:00
|
|
|
|
2016-12-11 10:05:48 -06:00
|
|
|
/**
|
2017-11-15 05:25:49 -06:00
|
|
|
* Expects data as:.
|
2016-12-11 10:05:48 -06:00
|
|
|
*
|
|
|
|
* key => value
|
|
|
|
*
|
|
|
|
* @param array $data
|
|
|
|
*
|
|
|
|
* @return array
|
|
|
|
*/
|
|
|
|
public function pieChart(array $data): array
|
|
|
|
{
|
2016-12-11 10:46:30 -06:00
|
|
|
$chartData = [
|
2016-12-11 10:05:48 -06:00
|
|
|
'datasets' => [
|
|
|
|
0 => [],
|
|
|
|
],
|
|
|
|
'labels' => [],
|
|
|
|
];
|
2017-04-22 00:05:44 -05:00
|
|
|
|
|
|
|
// sort by value, keep keys.
|
2017-07-14 10:21:30 -05:00
|
|
|
// different sort when values are positive and when they're negative.
|
2017-04-22 00:05:44 -05:00
|
|
|
asort($data);
|
2017-07-15 03:26:27 -05:00
|
|
|
$next = next($data);
|
2017-11-15 05:25:49 -06:00
|
|
|
if (!is_bool($next) && 1 === bccomp($next, '0')) {
|
2017-07-14 10:21:30 -05:00
|
|
|
// next is positive, sort other way around.
|
|
|
|
arsort($data);
|
|
|
|
}
|
2017-07-15 03:26:27 -05:00
|
|
|
unset($next);
|
2017-04-22 00:05:44 -05:00
|
|
|
|
2017-06-05 04:12:50 -05:00
|
|
|
$index = 0;
|
2016-12-11 10:05:48 -06:00
|
|
|
foreach ($data as $key => $value) {
|
|
|
|
// make larger than 0
|
2017-02-11 08:52:55 -06:00
|
|
|
$chartData['datasets'][0]['data'][] = floatval(Steam::positive($value));
|
2016-12-11 10:05:48 -06:00
|
|
|
$chartData['datasets'][0]['backgroundColor'][] = ChartColour::getColour($index);
|
|
|
|
$chartData['labels'][] = $key;
|
2017-11-15 05:25:49 -06:00
|
|
|
++$index;
|
2016-12-11 10:05:48 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
return $chartData;
|
|
|
|
}
|
2016-12-11 10:46:30 -06:00
|
|
|
|
|
|
|
/**
|
2017-11-15 05:25:49 -06:00
|
|
|
* Will generate a (ChartJS) compatible array from the given input. Expects this format:.
|
2016-12-11 10:46:30 -06:00
|
|
|
*
|
|
|
|
* 'label-of-entry' => value
|
|
|
|
* 'label-of-entry' => value
|
|
|
|
*
|
|
|
|
* @param string $setLabel
|
|
|
|
* @param array $data
|
|
|
|
*
|
|
|
|
* @return array
|
|
|
|
*/
|
|
|
|
public function singleSet(string $setLabel, array $data): array
|
|
|
|
{
|
|
|
|
$chartData = [
|
|
|
|
'count' => 1,
|
|
|
|
'labels' => array_keys($data), // take ALL labels from the first set.
|
|
|
|
'datasets' => [
|
|
|
|
[
|
|
|
|
'label' => $setLabel,
|
|
|
|
'data' => array_values($data),
|
|
|
|
],
|
|
|
|
],
|
|
|
|
];
|
|
|
|
|
|
|
|
return $chartData;
|
|
|
|
}
|
2016-12-22 12:42:45 -06:00
|
|
|
}
|