qt图表库qcustomplot使用心得记录三 (选区取点)

小王子🤴 2020-08-23 21:17:12 5600
qt图表库qcustomplot使用心得记录三 (选区取点)

本系列讲述的是我使用qt图表库qcustomplot中的使用心得分享,借此记录我的学习内容,也希望可以给与初学者一些帮助。
本篇文章讲述的是实现选取、获取选取内数据的功能,虽然qcustomplot自带选取功能,但是感觉不太好用(可能是不太会用的原因吧),所以就自己封装了选取功能。

1.实现原理

选区功能的实现原理非常简单,就是使用橡皮筋选择区域,取选区内数据点是通过橡皮筋的选择范围坐标获取在坐标内的数据。

 代码实例:

 代码中没有用到多么复杂的函数,一些QCustomPlot的函数第二篇文章都有介绍
#ifndef CUSTONPLOTEX_H
#define CUSTONPLOTEX_H
#include <QWidget>
#include "QCustomPlot/qcustomplot.h"
#include <QRubberBand>
#include "stdio.h"
class CustomPlotEx : public QCustomPlot
{
    Q_OBJECT
public:
    CustomPlotEx();
    CustomPlotEx(QWidget *widget);
    ~CustomPlotEx() Q_DECL_OVERRIDE;
    //打开选区功能
    //关闭选区功能
    void openSeleteArea();
    void closeSeleteArea();
    bool seleteAreaState();//获取当前选区功能状态
    //锁定,解锁
    void lock();
    void unLock();
    //自动选取
    void selectionRectFromRange(double startKey,double endKey);
    //选区范围值
    QCPRange selectionRectAxis_X();
    QCPRange selectionRectAxis_Y();
    //参数是否是选区内的key
    bool isSelectionRectKey(double key);
    //参数是否是选区内的value
    bool isSelectionRectValue(double value);
    /********************************选区内图表数据**************************************/
    //选区内图表key
    QVector<double> selectionRectGraphKey(int index);
    QVector<double> selectionRectGraphKey(QCPGraph *graph);
    //选区内图表value
    QVector<double> selectionRectGraphValue(int index);
    QVector<double> selectionRectGraphValue(QCPGraph *graph);
    //选区内图表所有的点的值
    QMap<double,double> selectionRectGraphData(int index);
    QMap<double,double> selectionRectGraphData(QCPGraph *graph);
    //复位选区
    void resetSelectionRect();
protected:
    //键盘按下事件
    virtual void keyPressEvent(QKeyEvent *event) Q_DECL_OVERRIDE;
    virtual void mousePressEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
    virtual void mouseDoubleClickEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
    virtual void mouseMoveEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
    virtual void mouseReleaseEvent(QMouseEvent *event) Q_DECL_OVERRIDE;
    virtual void wheelEvent(QWheelEvent *event) Q_DECL_OVERRIDE;
    virtual void paintEvent(QPaintEvent *event) Q_DECL_OVERRIDE;
public slots:
    //鼠标按下
    void mousePress(QMouseEvent *event);
    //鼠标移动
    void mouseMove(QMouseEvent *event);
    //鼠标释放
    void mouseRelease(QMouseEvent *event);

    //鼠标滑轮
    void mouseWheel(QWheelEvent *event);

private:
    void Init();
    //选区
    QRubberBand *rb;
    QPoint startPos;//选区开始
    bool cancelRb = false;
    bool isSeleteArea = false;//是否选区
    bool isLock = false;//锁定
};
#endif // CUSTONPLOTEX_H
#include "customplotex.h"
CustomPlotEx::CustomPlotEx() : QCustomPlot(new QWidget())
{
    Init();
}
CustomPlotEx::CustomPlotEx(QWidget *widget) : QCustomPlot(widget)
{
    Init();
}
CustomPlotEx::~CustomPlotEx()
{
}
void CustomPlotEx::openSeleteArea()
{
    isSeleteArea = true;
}
void CustomPlotEx::closeSeleteArea()
{
    resetSelectionRect();
    isSeleteArea = false;
}
bool CustomPlotEx::seleteAreaState()
{
    return isSeleteArea;
}
void CustomPlotEx::lock()
{
    isLock = true;
}
void CustomPlotEx::unLock()
{
    isLock = false;
}
void CustomPlotEx::selectionRectFromRange(double startKey, double endKey)
{

    startPos.rx() = static_cast<int>(xAxis->coordToPixel(startKey));
    startPos.ry() = 0;
    QPoint endPos;
    endPos.rx() = static_cast<int>(xAxis->coordToPixel(endKey));
    endPos.ry() = this->height();

     resetSelectionRect();

     QRect normalRect = QRect(startPos, endPos).normalized();//任意两点定义矩形
     rb->setGeometry(normalRect);
     rb->show();
}
QCPRange CustomPlotEx::selectionRectAxis_X()
{
//    qDebug() << "rb:" << rb->x() << "," << rb->x()+rb->rect().width();
    return QCPRange(xAxis->pixelToCoord(rb->x()), xAxis->pixelToCoord(rb->x()+rb->rect().width()));
}
QCPRange CustomPlotEx::selectionRectAxis_Y()
{
//    qDebug() << "rb->y()-rb->rect().height():" << rb->y()-rb->rect().height() << "rb->y():" << rb->y();
    return QCPRange(yAxis->pixelToCoord(rb->y()+rb->rect().height()), yAxis->pixelToCoord(rb->y()));
}
bool CustomPlotEx::isSelectionRectKey(double key)
{
    QCPRange rang = selectionRectAxis_X();
    return  (key >= rang.lower && key <= rang.upper);
}
bool CustomPlotEx::isSelectionRectValue(double value)
{
    QCPRange rang = selectionRectAxis_Y();
    return  (value >= rang.lower && value <= rang.upper);
}
QVector<double> CustomPlotEx::selectionRectGraphKey(int index)
{
    QVector<double> keyVector;
    for (auto i = graph(index)->data().data()->begin();i != graph(index)->data().data()->end();i++)
    {
        if(isSelectionRectKey(i->key))
        {
            keyVector.append(i->key);
        }
    }
    return keyVector;
}

QVector<double> CustomPlotEx::selectionRectGraphKey(QCPGraph *graph)
{
    QVector<double> keyVector;
    for (auto i = graph->data().data()->begin();i != graph->data().data()->end();i++)
    {
        if(isSelectionRectKey(i->key))
        {
            keyVector.append(i->key);
        }
    }
    return keyVector;
}
QVector<double> CustomPlotEx::selectionRectGraphValue(int index)
{
    QVector<double> valueVector;
    for (auto i = graph(index)->data().data()->begin();i != graph(index)->data().data()->end();i++)
    {
        if(isSelectionRectValue(i->value))
        {
            valueVector.append(i->value);
        }
    }
    return valueVector;
}
QVector<double> CustomPlotEx::selectionRectGraphValue(QCPGraph *graph)
{
    QVector<double> valueVector;
    for (auto i = graph->data().data()->begin();i != graph->data().data()->end();i++)
    {
        if(isSelectionRectValue(i->value))
        {
            valueVector.append(i->value);
        }
    }
    return valueVector;
}
QMap<double, double> CustomPlotEx::selectionRectGraphData(int index)
{
    QMap<double,double> graphData;
    for (auto i = graph(index)->data().data()->begin();i != graph(index)->data().data()->end();i++)
    {
        if(isSelectionRectKey(i->key) && isSelectionRectValue(i->value))
        {
//            qDebug() << i->key;
            graphData.insert(i->key,i->value);
        }
    }
    return graphData;
}
QMap<double, double> CustomPlotEx::selectionRectGraphData(QCPGraph *graph)
{
    QMap<double,double> graphData;
    for (auto i = graph->data().data()->begin();i != graph->data().data()->end();i++)
    {
        if(isSelectionRectKey(i->key) && isSelectionRectValue(i->value))
        {
            graphData.insert(i->key,i->value);
        }
    }
    return graphData;
}

void CustomPlotEx::keyPressEvent(QKeyEvent *event)
{
    if(isLock)
        return;
    if(cancelRb)
    {
        if(event->key() == Qt::Key_Up)
        {
        }else if (event->key() == Qt::Key_Down) {
        }else if (event->key() == Qt::Key_Left) {
            rb->move(rb->x()-1,rb->y());
        }else if (event->key() == Qt::Key_Right) {
            rb->move(rb->x()+1,rb->y());
        }

    }
}
void CustomPlotEx::mousePressEvent(QMouseEvent *event)
{
    if(isLock)
        return;
    if(isSeleteArea)
    {
        /*gyh add start*/
        if((event->buttons() & Qt::RightButton) || (event->buttons() & Qt::LeftButton))
        {
            if(cancelRb)
            {
                if(event->pos().x() >= rb->x() &&
                   event->pos().y() >= rb->y() &&
                   event->pos().x() <= rb->x() + rb->width() &&
                   event->pos().y() <= rb->y() + rb->height())
                {
                    cancelRb = true;
                    startPos = event->pos();
                    goto other;
                }
            }
            resetSelectionRect();
            startPos.rx() = event->pos().rx();
            startPos.ry() = 0;
   //         startPos = event->pos();
            rb->show();
           other:;
        }
        /*gyh add end*/
        replot();

    }else{
       QCustomPlot::mousePressEvent(event);
    }
}
void CustomPlotEx::mouseDoubleClickEvent(QMouseEvent *event)
{
    if(isLock)
        return;
    QCustomPlot::mouseDoubleClickEvent(event);
}

void CustomPlotEx::mouseMoveEvent(QMouseEvent *event)
{
    if(isLock)
        return;
    QCustomPlot::mouseMoveEvent(event);
}
void CustomPlotEx::mouseReleaseEvent(QMouseEvent *event)
{
    if(isLock)
        return;
    QCustomPlot::mouseReleaseEvent(event);
}
void CustomPlotEx::wheelEvent(QWheelEvent *event)
{
    if(isLock)
        return;
    QCustomPlot::wheelEvent(event);
}
void CustomPlotEx::paintEvent(QPaintEvent *event)
{
    QCustomPlot::paintEvent(event);
}
void CustomPlotEx::mousePress(QMouseEvent *event)
{
    Q_UNUSED(event);
}
void CustomPlotEx::mouseMove(QMouseEvent *event)
{
    QList<QCPLayerable*> candidates = layerableListAt(event->pos(), false);
    if(candidates.contains(this->xAxis))
    {
        setCursor(Qt::SizeHorCursor);
    }else if(candidates.contains(this->yAxis))
    {
        setCursor(Qt::SizeVerCursor);
    }else{
        setCursor(Qt::ArrowCursor);
    }
    /*gyh add start*/
    if(cancelRb)
    {
        if((event->buttons() & Qt::RightButton) || (event->buttons() & Qt::LeftButton))
        {
            clearAverageGraph();
            QPoint movePos = event->pos() - startPos;
            startPos = event->pos();
            rb->move(rb->x() + movePos.x(),rb->y() /*+ movePos.y()*/);
            return;
        }
    }
    if(event->buttons() & Qt::RightButton || event->buttons() & Qt::LeftButton)
    {
        QPoint endPos;
        endPos.rx() = event->pos().rx();
        endPos.ry() = this->height();
            QRect normalRect = QRect(startPos, endPos).normalized();//任意两点定义矩形
            rb->setGeometry(normalRect);
    }
     /*gyh add end*/
}
void CustomPlotEx::mouseRelease(QMouseEvent *event)
{
    /*gyh add start*/
    if((event->button() == Qt::RightButton) || (event->button() == Qt::LeftButton))
    {
        if(cancelRb)
        {
            return;
        }
        //起始位置与结束位置相同取消选区
        if(startPos == event->pos())
        {
            cancelRb = false;
            rb->resize(0, 0);
            rb->hide();
        }
        cancelRb = true;
    }
    /*gyh add end*/
}

void CustomPlotEx::mouseWheel(QWheelEvent *event)
{
    Q_UNUSED(event);
    resetSelectionRect();
}
void CustomPlotEx::Init()
{
//    setAntialiasedElement(QCP::aeAll);//抗锯齿
    setInteractions(QCP::iRangeDrag | QCP::iRangeZoom | QCP::iSelectAxes |
                                    QCP::iSelectLegend | QCP::iSelectPlottables);

    setPlottingHints(QCP::phFastPolylines | QCP::phImmediateRefresh | QCP::phCacheLabels);
    rb = new QRubberBand(QRubberBand::Rectangle, this);
    rb->resize(0,0);
    startPos = QPoint(0, 0);
    this->setOpenGl(true);
    setNoAntialiasingOnDrag(true);
    connect(this, SIGNAL(mousePress(QMouseEvent*)), this, SLOT(mousePress(QMouseEvent*)));
    connect(this, SIGNAL(mouseMove(QMouseEvent*)), this, SLOT(mouseMove(QMouseEvent*)));
    connect(this, SIGNAL(mouseRelease(QMouseEvent*)), this, SLOT(mouseRelease(QMouseEvent*)));
    connect(this, SIGNAL(mouseWheel(QWheelEvent*)), this, SLOT(mouseWheel(QWheelEvent*)));
}
声明:本文内容由易百纳平台入驻作者撰写,文章观点仅代表作者本人,不代表易百纳立场。如有内容侵权或者其他问题,请联系本站进行删除。
红包 点赞 收藏 评论 打赏
评论
0个
内容存在敏感词
手气红包
    易百纳技术社区暂无数据
相关专栏
置顶时间设置
结束时间
删除原因
  • 广告/SPAM
  • 恶意灌水
  • 违规内容
  • 文不对题
  • 重复发帖
打赏作者
易百纳技术社区
小王子🤴
您的支持将鼓励我继续创作!
打赏金额:
¥1易百纳技术社区
¥5易百纳技术社区
¥10易百纳技术社区
¥50易百纳技术社区
¥100易百纳技术社区
支付方式:
微信支付
支付宝支付
易百纳技术社区微信支付
易百纳技术社区
打赏成功!

感谢您的打赏,如若您也想被打赏,可前往 发表专栏 哦~

举报反馈

举报类型

  • 内容涉黄/赌/毒
  • 内容侵权/抄袭
  • 政治相关
  • 涉嫌广告
  • 侮辱谩骂
  • 其他

详细说明

审核成功

发布时间设置
发布时间:
是否关联周任务-专栏模块

审核失败

失败原因
备注
拼手气红包 红包规则
祝福语
恭喜发财,大吉大利!
红包金额
红包最小金额不能低于5元
红包数量
红包数量范围10~50个
余额支付
当前余额:
可前往问答、专栏板块获取收益 去获取
取 消 确 定

小包子的红包

恭喜发财,大吉大利

已领取20/40,共1.6元 红包规则

    易百纳技术社区