mirror of
https://github.com/fralx/LimeReport.git
synced 2024-12-24 16:44:39 +03:00
Refactor axis data. Remove duplicate paint code
This commit is contained in:
parent
95a11bdc14
commit
dfa378970f
@ -36,8 +36,8 @@ void HorizontalBarChart::paintHorizontalBars(QPainter *painter, QRectF barsRect)
|
|||||||
|
|
||||||
painter->save();
|
painter->save();
|
||||||
painter->setRenderHint(QPainter::Antialiasing,false);
|
painter->setRenderHint(QPainter::Antialiasing,false);
|
||||||
int delta = int(maxValue()-minValue());
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
delta = genNextValue(delta);
|
const qreal delta = yAxisData.delta();
|
||||||
|
|
||||||
qreal vStep = (barsRect.height()-painter->fontMetrics().height()) / valuesCount() / seriesCount();
|
qreal vStep = (barsRect.height()-painter->fontMetrics().height()) / valuesCount() / seriesCount();
|
||||||
qreal hStep = (barsRect.width()-painter->fontMetrics().boundingRect(QString::number(maxValue())).width()) / delta;
|
qreal hStep = (barsRect.width()-painter->fontMetrics().boundingRect(QString::number(maxValue())).width()) / delta;
|
||||||
|
@ -68,35 +68,70 @@ void LinesChart::drawDesignMode(QPainter* painter, qreal hStep, qreal vStep, qre
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
qreal LinesChart::calculateValueYPos(qreal, qreal max, qreal value, qreal delta, qreal height)
|
||||||
|
{
|
||||||
|
return (max - value) / delta * height;
|
||||||
|
}
|
||||||
|
|
||||||
|
void LinesChart::paintSeries(QPainter *painter, SeriesItem *series, QRectF barsRect)
|
||||||
|
{
|
||||||
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
|
const qreal delta = yAxisData.delta();
|
||||||
|
|
||||||
|
const qreal hStep = barsRect.width() / valuesCount();
|
||||||
|
const qreal topMargin = barsRect.top();
|
||||||
|
|
||||||
|
QPen pen(series->color());
|
||||||
|
pen.setWidth(4);
|
||||||
|
painter->setPen(pen);
|
||||||
|
|
||||||
|
const QList<qreal> &values = series->data()->values();
|
||||||
|
|
||||||
|
qreal lastYValue = 0;
|
||||||
|
qreal lastXValue = barsRect.left() + hStep/2;
|
||||||
|
if (!values.isEmpty()) {
|
||||||
|
// Calculate first point position on plot before loop
|
||||||
|
lastYValue = calculateValueYPos(yAxisData.rangeMin(), yAxisData.rangeMax(), values.first(), delta, barsRect.height());
|
||||||
|
}
|
||||||
|
for (int i = 0; i < values.count()-1; ++i ){
|
||||||
|
const qreal startY = lastYValue;
|
||||||
|
const qreal endY = calculateValueYPos(yAxisData.rangeMin(), yAxisData.rangeMax(), values.at(i+1), delta, barsRect.height());
|
||||||
|
// Record last used Y position to only calculate new one
|
||||||
|
lastYValue = endY;
|
||||||
|
|
||||||
|
const qreal startX = lastXValue;
|
||||||
|
const qreal endX = startX + hStep;
|
||||||
|
// Record last used X position to only calculate new one
|
||||||
|
lastXValue = endX;
|
||||||
|
|
||||||
|
QPoint startPoint = QPoint(startX, startY + topMargin);
|
||||||
|
QPoint endPoint = QPoint(endX, endY + topMargin);
|
||||||
|
drawSegment(painter, startPoint, endPoint, series->color());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void LinesChart::paintSerialLines(QPainter* painter, QRectF barsRect)
|
void LinesChart::paintSerialLines(QPainter* painter, QRectF barsRect)
|
||||||
{
|
{
|
||||||
if (valuesCount() == 0) return;
|
if (valuesCount() == 0) return;
|
||||||
|
|
||||||
painter->save();
|
painter->save();
|
||||||
painter->setRenderHint(QPainter::Antialiasing,true);
|
painter->setRenderHint(QPainter::Antialiasing,true);
|
||||||
int delta = int(maxValue() - minValue());
|
|
||||||
delta = genNextValue(delta);
|
|
||||||
|
|
||||||
qreal vStep = barsRect.height() / delta;
|
if (m_chartItem->itemMode() == DesignMode){
|
||||||
qreal hStep = barsRect.width() / valuesCount();
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
qreal topShift = (delta - (maxValue() - minValue())) * vStep +barsRect.top();
|
const qreal delta = yAxisData.delta();
|
||||||
|
const qreal hStep = barsRect.width() / valuesCount();
|
||||||
if (m_chartItem->itemMode() != DesignMode){
|
const qreal vStep = barsRect.height() / delta;
|
||||||
foreach (SeriesItem* series, m_chartItem->series()) {
|
const qreal topShift = (delta - (maxValue() - minValue())) * vStep + barsRect.top();
|
||||||
QPen pen(series->color());
|
|
||||||
pen.setWidth(4);
|
|
||||||
painter->setPen(pen);
|
|
||||||
for (int i = 0; i < series->data()->values().count()-1; ++i ){
|
|
||||||
QPoint startPoint = QPoint((i+1) * hStep + barsRect.left() - hStep/2,
|
|
||||||
(maxValue()*vStep+topShift) - series->data()->values().at(i) * vStep);
|
|
||||||
QPoint endPoint = QPoint((i+2) * hStep + barsRect.left() - hStep/2,
|
|
||||||
(maxValue() * vStep+topShift) - series->data()->values().at(i+1) * vStep);
|
|
||||||
drawSegment(painter, startPoint, endPoint, series->color());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
drawDesignMode(painter, hStep, vStep, topShift, barsRect);
|
drawDesignMode(painter, hStep, vStep, topShift, barsRect);
|
||||||
|
painter->restore();
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (SeriesItem *series : m_chartItem->series()) {
|
||||||
|
paintSeries(painter, series, barsRect);
|
||||||
|
}
|
||||||
|
|
||||||
painter->restore();
|
painter->restore();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,9 +8,13 @@ class LinesChart: public AbstractBarChart{
|
|||||||
public:
|
public:
|
||||||
LinesChart(ChartItem* chartItem):AbstractBarChart(chartItem){}
|
LinesChart(ChartItem* chartItem):AbstractBarChart(chartItem){}
|
||||||
void paintChart(QPainter *painter, QRectF chartRect);
|
void paintChart(QPainter *painter, QRectF chartRect);
|
||||||
|
protected:
|
||||||
|
void drawDesignMode(QPainter *painter, qreal hStep, qreal vStep, qreal topShift, QRectF barsRect);
|
||||||
|
qreal calculateValueYPos(qreal min, qreal max, qreal value, qreal delta, qreal height);
|
||||||
|
void paintSeries(QPainter *painter, SeriesItem *series, QRectF barsRect);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void paintSerialLines(QPainter *painter, QRectF barsRect);
|
void paintSerialLines(QPainter *painter, QRectF barsRect);
|
||||||
void drawDesignMode(QPainter *painter, qreal hStep, qreal vStep, qreal topShift, QRectF barsRect);
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -54,8 +54,8 @@ void VerticalBarChart::paintVerticalBars(QPainter *painter, QRectF barsRect)
|
|||||||
|
|
||||||
if (valuesCount() == 0) return;
|
if (valuesCount() == 0) return;
|
||||||
|
|
||||||
int delta = int(maxValue() - minValue());
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
delta = genNextValue(delta);
|
const qreal delta = yAxisData.delta();
|
||||||
|
|
||||||
int barSeriesCount = 0;
|
int barSeriesCount = 0;
|
||||||
foreach(SeriesItem* series, m_chartItem->series()){
|
foreach(SeriesItem* series, m_chartItem->series()){
|
||||||
@ -102,30 +102,14 @@ void VerticalBarChart::paintVerticalBars(QPainter *painter, QRectF barsRect)
|
|||||||
|
|
||||||
void VerticalBarChart::paintSerialLines(QPainter* painter, QRectF barsRect)
|
void VerticalBarChart::paintSerialLines(QPainter* painter, QRectF barsRect)
|
||||||
{
|
{
|
||||||
if (valuesCount() == 0 ) return;
|
if (valuesCount() == 0 || m_chartItem->series().isEmpty() ) return;
|
||||||
|
|
||||||
painter->save();
|
painter->save();
|
||||||
painter->setRenderHint(QPainter::Antialiasing,true);
|
painter->setRenderHint(QPainter::Antialiasing,true);
|
||||||
int delta = int(maxValue() - minValue());
|
|
||||||
delta = genNextValue(delta);
|
|
||||||
|
|
||||||
qreal vStep = barsRect.height() / delta;
|
for (SeriesItem *series : m_chartItem->series()) {
|
||||||
qreal hStep = (barsRect.width() / valuesCount());
|
|
||||||
qreal topShift = (delta - (maxValue()-minValue())) * vStep + barsRect.top();
|
|
||||||
|
|
||||||
if (!m_chartItem->series().isEmpty()){
|
|
||||||
foreach (SeriesItem* series, m_chartItem->series()) {
|
|
||||||
if (series->preferredType() == SeriesItem::Line){
|
if (series->preferredType() == SeriesItem::Line){
|
||||||
for (int i = 0; i < series->data()->values().count()-1; ++i ){
|
paintSeries(painter, series, barsRect);
|
||||||
QPoint startPoint = QPoint((i+1)*hStep + barsRect.left()-hStep/2,
|
|
||||||
(maxValue() * vStep+topShift) - series->data()->values().at(i) * vStep
|
|
||||||
);
|
|
||||||
QPoint endPoint = QPoint((i+2)*hStep + barsRect.left()-hStep/2,
|
|
||||||
(maxValue() * vStep+topShift) - series->data()->values().at(i+1) * vStep
|
|
||||||
);
|
|
||||||
drawSegment(painter, startPoint, endPoint, series->color());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
painter->restore();
|
painter->restore();
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
#ifndef VERTICALBARCHART_H
|
#ifndef VERTICALBARCHART_H
|
||||||
#define VERTICALBARCHART_H
|
#define VERTICALBARCHART_H
|
||||||
|
|
||||||
#include "lrchartitem.h"
|
#include "lrlineschart.h"
|
||||||
|
|
||||||
namespace LimeReport{
|
namespace LimeReport{
|
||||||
|
|
||||||
class VerticalBarChart: public AbstractBarChart{
|
class VerticalBarChart: public LinesChart{
|
||||||
public:
|
public:
|
||||||
VerticalBarChart(ChartItem* chartItem):AbstractBarChart(chartItem){}
|
VerticalBarChart(ChartItem* chartItem):LinesChart(chartItem){}
|
||||||
void paintChart(QPainter *painter, QRectF chartRect);
|
void paintChart(QPainter *painter, QRectF chartRect);
|
||||||
// void paintVerticalGrid(QPainter *painter, QRectF gridRect);
|
// void paintVerticalGrid(QPainter *painter, QRectF gridRect);
|
||||||
void paintVerticalBars(QPainter *painter, QRectF barsRect);
|
void paintVerticalBars(QPainter *painter, QRectF barsRect);
|
||||||
|
@ -130,7 +130,7 @@ ChartItem::ChartItem(QObject *owner, QGraphicsItem *parent)
|
|||||||
: ItemDesignIntf(xmlTag, owner, parent), m_legendBorder(true),
|
: ItemDesignIntf(xmlTag, owner, parent), m_legendBorder(true),
|
||||||
m_legendAlign(LegendAlignCenter), m_titleAlign(TitleAlignCenter),
|
m_legendAlign(LegendAlignCenter), m_titleAlign(TitleAlignCenter),
|
||||||
m_chartType(Pie), m_labelsField(""), m_isEmpty(true),
|
m_chartType(Pie), m_labelsField(""), m_isEmpty(true),
|
||||||
m_showLegend(true)
|
m_showLegend(true), m_drawPoints(true), m_seriesLineWidth(4)
|
||||||
{
|
{
|
||||||
m_labels<<"First"<<"Second"<<"Thrid";
|
m_labels<<"First"<<"Second"<<"Thrid";
|
||||||
m_chart = new PieChart(this);
|
m_chart = new PieChart(this);
|
||||||
@ -433,6 +433,37 @@ bool ChartItem::isSeriesExists(const QString &name)
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int ChartItem::seriesLineWidth() const
|
||||||
|
{
|
||||||
|
return m_seriesLineWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ChartItem::drawPoints() const
|
||||||
|
{
|
||||||
|
return m_drawPoints;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ChartItem::setDrawPoints(bool drawPoints)
|
||||||
|
{
|
||||||
|
if (m_drawPoints != drawPoints){
|
||||||
|
m_drawPoints = drawPoints;
|
||||||
|
notify("drawPoints", !m_drawPoints, m_drawPoints);
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
m_drawPoints = drawPoints;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ChartItem::setSeriesLineWidth(int newSeriesLineWidth)
|
||||||
|
{
|
||||||
|
if (m_seriesLineWidth != newSeriesLineWidth){
|
||||||
|
int oldValue = m_seriesLineWidth;
|
||||||
|
m_seriesLineWidth = newSeriesLineWidth;
|
||||||
|
notify("seriesLineWidth", oldValue, m_seriesLineWidth);
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
m_seriesLineWidth = newSeriesLineWidth;
|
||||||
|
}
|
||||||
|
|
||||||
AbstractChart::AbstractChart(ChartItem *chartItem)
|
AbstractChart::AbstractChart(ChartItem *chartItem)
|
||||||
:m_chartItem(chartItem)
|
:m_chartItem(chartItem)
|
||||||
{
|
{
|
||||||
@ -492,14 +523,6 @@ void AbstractChart::prepareLegendToPaint(QRectF &legendRect, QPainter *painter)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int genNextValue(int value){
|
|
||||||
int curValue = value;
|
|
||||||
while (curValue % 4 != 0){
|
|
||||||
curValue++;
|
|
||||||
}
|
|
||||||
return curValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
AbstractSeriesChart::AbstractSeriesChart(ChartItem *chartItem)
|
AbstractSeriesChart::AbstractSeriesChart(ChartItem *chartItem)
|
||||||
:AbstractChart(chartItem)
|
:AbstractChart(chartItem)
|
||||||
{
|
{
|
||||||
@ -516,31 +539,37 @@ AbstractSeriesChart::AbstractSeriesChart(ChartItem *chartItem)
|
|||||||
|
|
||||||
qreal AbstractSeriesChart::maxValue()
|
qreal AbstractSeriesChart::maxValue()
|
||||||
{
|
{
|
||||||
return m_maxValue;
|
return m_yAxisData.maxValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
qreal AbstractSeriesChart::minValue()
|
qreal AbstractSeriesChart::minValue()
|
||||||
{
|
{
|
||||||
return m_minValue;
|
return m_yAxisData.minValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
AxisData AbstractSeriesChart::yAxisData()
|
||||||
|
{
|
||||||
|
return m_yAxisData;
|
||||||
}
|
}
|
||||||
|
|
||||||
void AbstractSeriesChart::updateMinAndMaxValues()
|
void AbstractSeriesChart::updateMinAndMaxValues()
|
||||||
{
|
{
|
||||||
|
qreal maxYValue = 0;
|
||||||
|
qreal minYValue = 0;
|
||||||
if (m_chartItem->itemMode() == DesignMode) {
|
if (m_chartItem->itemMode() == DesignMode) {
|
||||||
m_maxValue = 40;
|
maxYValue = 40;
|
||||||
m_minValue = 0;
|
} else {
|
||||||
return;
|
for (SeriesItem* series : m_chartItem->series()){
|
||||||
}
|
for (qreal value : series->data()->values()){
|
||||||
m_minValue = 0;
|
minYValue = std::min(minYValue, value);
|
||||||
m_maxValue = 0;
|
maxYValue = std::max(maxYValue, value);
|
||||||
foreach(SeriesItem* series, m_chartItem->series()){
|
|
||||||
foreach(qreal value, series->data()->values()){
|
|
||||||
if (value<m_minValue) m_minValue=value;
|
|
||||||
if (value>m_maxValue) m_maxValue=value;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
m_yAxisData = AxisData(minYValue, maxYValue);
|
||||||
|
}
|
||||||
|
|
||||||
qreal AbstractSeriesChart::hPadding(QRectF chartRect)
|
qreal AbstractSeriesChart::hPadding(QRectF chartRect)
|
||||||
{
|
{
|
||||||
return (chartRect.width() * 0.02);
|
return (chartRect.width() * 0.02);
|
||||||
@ -655,18 +684,22 @@ void AbstractSeriesChart::paintVerticalLabels(QPainter *painter, QRectF labelsRe
|
|||||||
void AbstractSeriesChart::paintHorizontalGrid(QPainter *painter, QRectF gridRect)
|
void AbstractSeriesChart::paintHorizontalGrid(QPainter *painter, QRectF gridRect)
|
||||||
{
|
{
|
||||||
painter->save();
|
painter->save();
|
||||||
int delta = int(maxValue() - minValue());
|
|
||||||
delta = genNextValue(delta);
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
|
const qreal delta = yAxisData.delta();
|
||||||
|
|
||||||
|
const int segmentCount = yAxisData.segmentCount();
|
||||||
|
const int lineCount = segmentCount + 1;
|
||||||
|
|
||||||
painter->setRenderHint(QPainter::Antialiasing,false);
|
painter->setRenderHint(QPainter::Antialiasing,false);
|
||||||
qreal hStep = (gridRect.width() - painter->fontMetrics().boundingRect(QString::number(maxValue())).width()) / 4;
|
qreal hStep = (gridRect.width() - painter->fontMetrics().boundingRect(QString::number(maxValue())).width()) / segmentCount;
|
||||||
|
|
||||||
painter->setFont(adaptValuesFont(hStep-4, painter->font()));
|
painter->setFont(adaptValuesFont(hStep-4, painter->font()));
|
||||||
|
|
||||||
for (int i=0;i<5;i++){
|
for (int i = 0 ; i < lineCount ; i++ ) {
|
||||||
painter->drawText(QRectF(gridRect.left() + 4 + hStep * i, gridRect.bottom() - painter->fontMetrics().height(),
|
painter->drawText(QRectF(gridRect.left() + 4 + hStep * i, gridRect.bottom() - painter->fontMetrics().height(),
|
||||||
hStep, painter->fontMetrics().height()),
|
hStep, painter->fontMetrics().height()),
|
||||||
QString::number(minValue() + i * delta / 4));
|
QString::number(minValue() + i * delta / segmentCount));
|
||||||
painter->drawLine( gridRect.left()+hStep*i, gridRect.bottom(),
|
painter->drawLine( gridRect.left()+hStep*i, gridRect.bottom(),
|
||||||
gridRect.left()+hStep*i, gridRect.top());
|
gridRect.left()+hStep*i, gridRect.top());
|
||||||
|
|
||||||
@ -676,20 +709,27 @@ void AbstractSeriesChart::paintHorizontalGrid(QPainter *painter, QRectF gridRect
|
|||||||
|
|
||||||
void AbstractSeriesChart::paintVerticalGrid(QPainter *painter, QRectF gridRect)
|
void AbstractSeriesChart::paintVerticalGrid(QPainter *painter, QRectF gridRect)
|
||||||
{
|
{
|
||||||
int delta = int(maxValue()-minValue());
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
delta = genNextValue(delta);
|
|
||||||
|
|
||||||
painter->setRenderHint(QPainter::Antialiasing,false);
|
painter->setRenderHint(QPainter::Antialiasing,false);
|
||||||
qreal vStep = gridRect.height() / 4;
|
|
||||||
|
const int segmentCount = yAxisData.segmentCount();
|
||||||
|
const int lineCount = segmentCount + 1;
|
||||||
|
qreal vStep = gridRect.height() / segmentCount;
|
||||||
|
|
||||||
const qreal valuesHMargin = this->valuesHMargin(painter);
|
const qreal valuesHMargin = this->valuesHMargin(painter);
|
||||||
|
const int fontHeight = painter->fontMetrics().height();
|
||||||
|
const int halfFontHeight = fontHeight / 2;
|
||||||
|
|
||||||
for (int i=0;i<5;i++){
|
const QTextOption verticalTextOption(Qt::AlignRight);
|
||||||
painter->drawText(QRectF(gridRect.bottomLeft()-QPointF(0,vStep*i+painter->fontMetrics().height()),
|
for (int i = 0 ; i < lineCount ; i++ ) {
|
||||||
QSizeF(valuesHMargin,painter->fontMetrics().height())),
|
const qreal y = vStep * i;
|
||||||
QString::number(minValue()+i*delta/4));
|
painter->drawText(QRectF(gridRect.bottomLeft()-QPointF(fontHeight,y+halfFontHeight),
|
||||||
painter->drawLine(gridRect.bottomLeft()-QPointF(-valuesHMargin,vStep*i),
|
QSizeF(valuesHMargin,fontHeight)),
|
||||||
gridRect.bottomRight()-QPointF(0,vStep*i));
|
verticalLabel(i, yAxisData.step(), yAxisData.rangeMin()),
|
||||||
|
verticalTextOption);
|
||||||
|
painter->drawLine(gridRect.bottomLeft()-QPointF(-valuesHMargin,y),
|
||||||
|
gridRect.bottomRight()-QPointF(0,y));
|
||||||
}
|
}
|
||||||
|
|
||||||
painter->setRenderHint(QPainter::Antialiasing,true);
|
painter->setRenderHint(QPainter::Antialiasing,true);
|
||||||
@ -697,11 +737,14 @@ void AbstractSeriesChart::paintVerticalGrid(QPainter *painter, QRectF gridRect)
|
|||||||
|
|
||||||
void AbstractSeriesChart::drawSegment(QPainter *painter, QPoint startPoint, QPoint endPoint, QColor color)
|
void AbstractSeriesChart::drawSegment(QPainter *painter, QPoint startPoint, QPoint endPoint, QColor color)
|
||||||
{
|
{
|
||||||
int radius = 4;
|
int radius = m_chartItem->seriesLineWidth();
|
||||||
QPen pen(color);
|
QPen pen(color);
|
||||||
pen.setWidth(radius);
|
pen.setWidth(radius);
|
||||||
painter->setPen(pen);
|
painter->setPen(pen);
|
||||||
painter->drawLine(startPoint, endPoint);
|
painter->drawLine(startPoint, endPoint);
|
||||||
|
if (!m_chartItem->drawPoints()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
QRect startPointRect(startPoint,startPoint);
|
QRect startPointRect(startPoint,startPoint);
|
||||||
QRect endPointRect(endPoint,endPoint);
|
QRect endPointRect(endPoint,endPoint);
|
||||||
painter->setBrush(color);
|
painter->setBrush(color);
|
||||||
@ -711,9 +754,16 @@ void AbstractSeriesChart::drawSegment(QPainter *painter, QPoint startPoint, QPoi
|
|||||||
|
|
||||||
qreal AbstractSeriesChart::valuesHMargin(QPainter *painter)
|
qreal AbstractSeriesChart::valuesHMargin(QPainter *painter)
|
||||||
{
|
{
|
||||||
int delta = int(maxValue()-minValue());
|
qreal max = 0;
|
||||||
delta = genNextValue(delta);
|
const AxisData &yAxisData = this->yAxisData();
|
||||||
return painter->fontMetrics().boundingRect(QString::number(delta)).width()+4;
|
const int offset = 4;
|
||||||
|
const int yAxisLineCount = yAxisData.segmentCount() + 1;
|
||||||
|
|
||||||
|
for (int i = 0 ; i < yAxisLineCount ; i++) {
|
||||||
|
const QString label = verticalLabel(i, yAxisData.step(), yAxisData.rangeMin());
|
||||||
|
max = std::max(max, (qreal)painter->fontMetrics().boundingRect(label).width()+offset);
|
||||||
|
}
|
||||||
|
return max;
|
||||||
}
|
}
|
||||||
|
|
||||||
qreal AbstractSeriesChart::valuesVMargin(QPainter *painter)
|
qreal AbstractSeriesChart::valuesVMargin(QPainter *painter)
|
||||||
@ -760,6 +810,16 @@ QFont AbstractSeriesChart::adaptValuesFont(qreal width, QFont font)
|
|||||||
return tmpFont;
|
return tmpFont;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString AbstractSeriesChart::verticalLabel(int i, qreal step, qreal min)
|
||||||
|
{
|
||||||
|
qreal value = min + i * step;
|
||||||
|
if (std::floor(step) == step) {
|
||||||
|
return QString::number(value);
|
||||||
|
}
|
||||||
|
// For float round numbers to small precision
|
||||||
|
return QString::number(value, 'g', 2);
|
||||||
|
}
|
||||||
|
|
||||||
void AbstractBarChart::paintChartLegend(QPainter *painter, QRectF legendRect)
|
void AbstractBarChart::paintChartLegend(QPainter *painter, QRectF legendRect)
|
||||||
{
|
{
|
||||||
prepareLegendToPaint(legendRect, painter);
|
prepareLegendToPaint(legendRect, painter);
|
||||||
@ -836,5 +896,4 @@ QRectF AbstractBarChart::horizontalLabelsRect(QPainter *painter, QRectF labelsRe
|
|||||||
else
|
else
|
||||||
return labelsRect.adjusted(0, (labelsRect.height() - maxWidth), 0, 0);
|
return labelsRect.adjusted(0, (labelsRect.height() - maxWidth), 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace LimeReport
|
} // namespace LimeReport
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
#define LRCHARTITEM_H
|
#define LRCHARTITEM_H
|
||||||
#include "lritemdesignintf.h"
|
#include "lritemdesignintf.h"
|
||||||
#include "lrglobal.h"
|
#include "lrglobal.h"
|
||||||
|
#include "lraxisdata.h"
|
||||||
#include <QtGlobal>
|
#include <QtGlobal>
|
||||||
|
|
||||||
namespace LimeReport{
|
namespace LimeReport{
|
||||||
@ -85,6 +86,7 @@ public:
|
|||||||
protected:
|
protected:
|
||||||
qreal maxValue();
|
qreal maxValue();
|
||||||
qreal minValue();
|
qreal minValue();
|
||||||
|
AxisData yAxisData();
|
||||||
void updateMinAndMaxValues();
|
void updateMinAndMaxValues();
|
||||||
int valuesCount();
|
int valuesCount();
|
||||||
int seriesCount();
|
int seriesCount();
|
||||||
@ -102,14 +104,13 @@ protected:
|
|||||||
virtual qreal valuesVMargin(QPainter *painter);
|
virtual qreal valuesVMargin(QPainter *painter);
|
||||||
virtual QFont adaptLabelsFont(QRectF rect, QFont font);
|
virtual QFont adaptLabelsFont(QRectF rect, QFont font);
|
||||||
virtual QFont adaptValuesFont(qreal width, QFont font);
|
virtual QFont adaptValuesFont(qreal width, QFont font);
|
||||||
|
virtual QString verticalLabel(int i, qreal step, qreal min);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
qreal m_minValue = 0, m_maxValue = 0;
|
AxisData m_yAxisData;
|
||||||
qreal m_designValues [9];
|
qreal m_designValues [9];
|
||||||
};
|
};
|
||||||
|
|
||||||
int genNextValue(int value);
|
|
||||||
|
|
||||||
class AbstractBarChart: public AbstractSeriesChart{
|
class AbstractBarChart: public AbstractSeriesChart{
|
||||||
public:
|
public:
|
||||||
AbstractBarChart(ChartItem* chartItem):AbstractSeriesChart(chartItem){}
|
AbstractBarChart(ChartItem* chartItem):AbstractSeriesChart(chartItem){}
|
||||||
@ -131,6 +132,10 @@ class ChartItem : public LimeReport::ItemDesignIntf
|
|||||||
Q_PROPERTY(ChartType chartType READ chartType WRITE setChartType)
|
Q_PROPERTY(ChartType chartType READ chartType WRITE setChartType)
|
||||||
Q_PROPERTY(QString labelsField READ labelsField WRITE setLabelsField)
|
Q_PROPERTY(QString labelsField READ labelsField WRITE setLabelsField)
|
||||||
Q_PROPERTY(bool showLegend READ showLegend WRITE setShowLegend)
|
Q_PROPERTY(bool showLegend READ showLegend WRITE setShowLegend)
|
||||||
|
|
||||||
|
//linesChart
|
||||||
|
Q_PROPERTY(bool drawPoints READ drawPoints WRITE setDrawPoints)
|
||||||
|
Q_PROPERTY(int seriesLineWidth READ seriesLineWidth WRITE setSeriesLineWidth)
|
||||||
friend class AbstractChart;
|
friend class AbstractChart;
|
||||||
public:
|
public:
|
||||||
|
|
||||||
@ -183,6 +188,12 @@ public:
|
|||||||
bool showLegend() const;
|
bool showLegend() const;
|
||||||
void setShowLegend(bool showLegend);
|
void setShowLegend(bool showLegend);
|
||||||
|
|
||||||
|
bool drawPoints() const;
|
||||||
|
void setDrawPoints(bool drawPoints);
|
||||||
|
|
||||||
|
int seriesLineWidth() const;
|
||||||
|
void setSeriesLineWidth(int newSeriesLineWidth);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void paintChartTitle(QPainter* painter, QRectF titleRect);
|
void paintChartTitle(QPainter* painter, QRectF titleRect);
|
||||||
virtual BaseDesignIntf* createSameTypeItem(QObject *owner, QGraphicsItem *parent);
|
virtual BaseDesignIntf* createSameTypeItem(QObject *owner, QGraphicsItem *parent);
|
||||||
@ -209,7 +220,8 @@ private:
|
|||||||
QList<QString> m_labels;
|
QList<QString> m_labels;
|
||||||
bool m_isEmpty;
|
bool m_isEmpty;
|
||||||
bool m_showLegend;
|
bool m_showLegend;
|
||||||
|
bool m_drawPoints;
|
||||||
|
int m_seriesLineWidth;
|
||||||
};
|
};
|
||||||
|
|
||||||
} //namespace LimeReport
|
} //namespace LimeReport
|
||||||
#endif // LRCHARTITEM_H
|
#endif // LRCHARTITEM_H
|
||||||
|
@ -75,6 +75,7 @@ SOURCES += \
|
|||||||
$$REPORT_PATH/lrcolorindicator.cpp \
|
$$REPORT_PATH/lrcolorindicator.cpp \
|
||||||
$$REPORT_PATH/lrreporttranslation.cpp \
|
$$REPORT_PATH/lrreporttranslation.cpp \
|
||||||
$$REPORT_PATH/exporters/lrpdfexporter.cpp \
|
$$REPORT_PATH/exporters/lrpdfexporter.cpp \
|
||||||
|
$$REPORT_PATH/lraxisdata.cpp \
|
||||||
$$REPORT_PATH/lrpreparedpages.cpp
|
$$REPORT_PATH/lrpreparedpages.cpp
|
||||||
|
|
||||||
CONFIG(staticlib) {
|
CONFIG(staticlib) {
|
||||||
@ -170,6 +171,7 @@ HEADERS += \
|
|||||||
$$REPORT_PATH/lrexportersfactory.h \
|
$$REPORT_PATH/lrexportersfactory.h \
|
||||||
$$REPORT_PATH/exporters/lrpdfexporter.h \
|
$$REPORT_PATH/exporters/lrpdfexporter.h \
|
||||||
$$REPORT_PATH/lrpreparedpages.h \
|
$$REPORT_PATH/lrpreparedpages.h \
|
||||||
|
$$REPORT_PATH/lraxisdata.h \
|
||||||
$$REPORT_PATH/lrpreparedpagesintf.h
|
$$REPORT_PATH/lrpreparedpagesintf.h
|
||||||
|
|
||||||
CONFIG(staticlib) {
|
CONFIG(staticlib) {
|
||||||
|
68
limereport/lraxisdata.cpp
Normal file
68
limereport/lraxisdata.cpp
Normal file
@ -0,0 +1,68 @@
|
|||||||
|
#include "lraxisdata.h"
|
||||||
|
|
||||||
|
namespace LimeReport {
|
||||||
|
AxisData::AxisData()
|
||||||
|
: m_rangeMin(0), m_rangeMax(0),
|
||||||
|
m_minValue(0), m_maxValue(0), m_step(0),
|
||||||
|
m_delta(0), m_segmentCount(4)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
AxisData::AxisData(qreal minValue, qreal maxValue)
|
||||||
|
: AxisData()
|
||||||
|
{
|
||||||
|
m_minValue = minValue;
|
||||||
|
m_maxValue = maxValue;
|
||||||
|
calculateValuesAboveMax(minValue, maxValue, 4);
|
||||||
|
m_delta = m_step * m_segmentCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
int AxisData::segmentCount() const
|
||||||
|
{
|
||||||
|
return m_segmentCount;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::rangeMin() const
|
||||||
|
{
|
||||||
|
return m_rangeMin;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::rangeMax() const
|
||||||
|
{
|
||||||
|
return m_rangeMax;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::minValue() const
|
||||||
|
{
|
||||||
|
return m_minValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::maxValue() const
|
||||||
|
{
|
||||||
|
return m_maxValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::step() const
|
||||||
|
{
|
||||||
|
return m_step;
|
||||||
|
}
|
||||||
|
|
||||||
|
qreal AxisData::delta() const
|
||||||
|
{
|
||||||
|
return m_delta;
|
||||||
|
}
|
||||||
|
|
||||||
|
void AxisData::calculateValuesAboveMax(qreal minValue, qreal maxValue, int segments)
|
||||||
|
{
|
||||||
|
const int delta = maxValue - minValue;
|
||||||
|
int max = delta;
|
||||||
|
while (max % segments != 0){
|
||||||
|
max++;
|
||||||
|
}
|
||||||
|
m_rangeMax = max;
|
||||||
|
m_step = max / segments;
|
||||||
|
m_rangeMin = minValue;
|
||||||
|
m_segmentCount = segments;
|
||||||
|
}
|
||||||
|
}
|
37
limereport/lraxisdata.h
Normal file
37
limereport/lraxisdata.h
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
#ifndef AXISDATA_H
|
||||||
|
#define AXISDATA_H
|
||||||
|
|
||||||
|
#include <QtGlobal>
|
||||||
|
|
||||||
|
namespace LimeReport {
|
||||||
|
class AxisData
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
AxisData();
|
||||||
|
AxisData(qreal minValue, qreal maxValue);
|
||||||
|
|
||||||
|
int segmentCount() const;
|
||||||
|
|
||||||
|
qreal rangeMin() const;
|
||||||
|
qreal rangeMax() const;
|
||||||
|
|
||||||
|
qreal minValue() const;
|
||||||
|
qreal maxValue() const;
|
||||||
|
qreal step() const;
|
||||||
|
|
||||||
|
qreal delta() const;
|
||||||
|
private:
|
||||||
|
void calculateValuesAboveMax(qreal minValue, qreal maxValue, int segments);
|
||||||
|
qreal calculateNiceNum(qreal range, bool round);
|
||||||
|
|
||||||
|
qreal m_rangeMin;
|
||||||
|
qreal m_rangeMax;
|
||||||
|
qreal m_minValue;
|
||||||
|
qreal m_maxValue;
|
||||||
|
qreal m_step;
|
||||||
|
qreal m_delta;
|
||||||
|
int m_segmentCount;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // AXISDATA_H
|
@ -165,6 +165,8 @@ void QObjectPropertyModel::translatePropertyName()
|
|||||||
tr("printBehavior");
|
tr("printBehavior");
|
||||||
tr("shiftItems");
|
tr("shiftItems");
|
||||||
tr("showLegend");
|
tr("showLegend");
|
||||||
|
tr("seriesLineWidth");
|
||||||
|
tr("drawPoints");
|
||||||
tr("removeGap");
|
tr("removeGap");
|
||||||
tr("dropPrinterMargins");
|
tr("dropPrinterMargins");
|
||||||
tr("notPrintIfEmpty");
|
tr("notPrintIfEmpty");
|
||||||
|
Loading…
Reference in New Issue
Block a user