#include "CustomLineGraph.h" #include #include #include #include CustomLineGraph::CustomLineGraph(QWidget* parent):QWidget(parent), linePen(Qt::blue), rectPen(Qt::red), axisPen(Qt::black) { linePen.setWidth(3); linePen.setJoinStyle(Qt::PenJoinStyle::RoundJoin); LineGraphSeries lgs; //Populate data with DummyData //Draw Points std::random_device rd; //Will be used to obtain a seed for the random number engine std::mt19937 gen(rd()); //Standard mersenne_twister_engine seeded with rd() std::uniform_int_distribution<> dis(-3, 3); for (int randomSeries = 0; randomSeries < 2; randomSeries++) { for (int i = 0; i < 21; i++) { QPoint point(i * 50 + 500,i * 1 + dis(gen) - 10000); lgs.data.push_back(point); } auto pairX = std::minmax_element(std::begin(lgs.data), std::end(lgs.data), [](const QPoint& a,const QPoint& b) -> bool {return a.x() < b.x(); }); lgs.minX = pairX.first->x(); lgs.maxX = pairX.second->x(); auto pairY = std::minmax_element(std::begin(lgs.data), std::end(lgs.data), [](const QPoint& a, const QPoint& b) -> bool {return a.y() < b.y(); }); lgs.minY = pairY.first->y(); lgs.maxY = pairY.second->y(); lgs.rangeX = std::abs(lgs.maxX - lgs.minX); lgs.rangeY = std::abs(lgs.maxY - lgs.minY); seriesVec.push_back(lgs); } } CustomLineGraph::~CustomLineGraph() { } void CustomLineGraph::paintEvent(QPaintEvent* event) { QPainter painter(this); painter.setRenderHint(QPainter::RenderHint::HighQualityAntialiasing); //Calculate LineRect QRect lineRect(rect()); lineRect.setBottom(lineRect.bottom() - 20); lineRect.setLeft(lineRect.left() + 40); lineRect.setTop(lineRect.top() + 20); lineRect.setRight(lineRect.right() - 10); lineRect.setWidth(lineRect.width() - (lineRect.width() % 10) + 1); lineRect.setHeight(lineRect.height() - (lineRect.height() % 10) + 1); //draw Title painter.setPen(axisPen); painter.setFont(QFont("Arial", 12)); QRect titleRect(QPoint(lineRect.left(), rect().top()), QPoint(lineRect.right(), lineRect.top())); painter.drawText(titleRect, Qt::AlignCenter, "title"); //draw X-Axis QRect xAxisRect(QPoint(lineRect.left(), lineRect.bottom()), QPoint(lineRect.right(), rect().bottom())); QPainterPath xAxisPath; xAxisPath.moveTo(xAxisRect.left(), xAxisRect.top()); xAxisPath.lineTo(xAxisRect.right(), xAxisRect.top()); int xGap = xAxisRect.width() / 10; for (int i = 0; i < 11; i++) { xAxisPath.moveTo(xAxisRect.left() + i * xGap, xAxisRect.top() + 5); xAxisPath.lineTo(xAxisRect.left() + i * xGap, xAxisRect.top()); } painter.drawPath(xAxisPath); //draw Y-Axis QRect yAxisRect(QPoint(rect().left(), lineRect.top()), QPoint(lineRect.left(), lineRect.bottom())); QPainterPath yAxisPath; yAxisPath.moveTo(yAxisRect.right(), yAxisRect.bottom() + 5); yAxisPath.lineTo(yAxisRect.right(), yAxisRect.top()); int yGap = yAxisRect.height() / 10; for (int i = 0; i < 11; i++) { yAxisPath.moveTo(yAxisRect.right() - 5, yAxisRect.top() + i * yGap); yAxisPath.lineTo(yAxisRect.right(), yAxisRect.top() + i * yGap); } painter.drawPath(yAxisPath); painter.setPen(linePen); for (LineGraphSeries series : seriesVec) { double stregth_factorX = lineRect.width() / series.rangeX; double stregth_factorY = lineRect.height() / series.rangeY; QPointF translation(lineRect.left(), lineRect.top()); QPainterPath painterPath; painterPath.moveTo(transformPoint(series.data[0], series, stregth_factorX, stregth_factorY)); for(int i = 1; i < seriesVec[0].data.size(); i++) { painterPath.lineTo(transformPoint(series.data[i], series, stregth_factorX, stregth_factorY)); } painterPath.translate(translation); painter.drawPath(painterPath); int radius; for (int i = 0; i < seriesVec[0].data.size(); i++) { painter.drawEllipse(transformPoint(series.data[i], series, stregth_factorX, stregth_factorY) + translation, 3, 3); } } } QPoint CustomLineGraph::transformPoint(QPoint& point, LineGraphSeries& lgs, double stregth_factorX, double stregth_factorY) { return QPoint((point.x() - lgs.minX)* stregth_factorX , (lgs.maxY - point.y()) * stregth_factorY); }