Qt开发笔记之Qwt(二):Qwt仪表盘的基本使用

简介: Qt开发笔记之Qwt(二):Qwt仪表盘的基本使用

若该文为原创文章,未经允许不得转载

原博主博客地址:https://blog.csdn.net/qq21497936

原博主博客导航:https://blog.csdn.net/qq21497936/article/details/102478062

本文章博客地址:http://blog.csdn.net/qq21497936/article/details/77881844

各位读者,知识无穷而人力有穷,要么改需求,要么找专业人士,要么自己研究

红胖子(红模仿)的博文大全:开发技术集合(包含Qt实用技术、树莓派、三维、OpenCV、OpenGL、ffmpeg、OSG、单片机、软硬结合等等)持续更新中…(点击传送门)

Qt开发专栏:三方库开发技术(点击传送门

Qt开发笔记之Qwt开发笔记(一):Qwt介绍、编译与Demo

Qt开发笔记之Qwt开发笔记(二):Qwt仪表盘的基本使用

 

背景

   目前正在做云桌面,前面使用了QCursorPlot实现了二维图表,使用了QPropertyAnimation实现了按钮的抖动,现在需要一个动态显示空间的圆形效果图,如下图:

   用100张图刷也可以,不过太原始了,所以研究研究Qwt,想使用Qwt仪表盘来实现。

                                                                      图片.png

前后关联

   上一篇《Qt之Qwt初探(一)》我们介绍了扫盲了Qwt的官网图片示例的效果和代码提供示例的效果截图,  

   《Qt之Qwt初探(一)》:  http://blog.csdn.net/qq21497936/article/details/77852657

   本篇qwtDemo将实现下图的效果:

                                                            2.gif

   qwtDemo下载地址:http://download.csdn.net/download/qq21497936/9968406

 

本人对于qwt仪表盘的理解

   Qwt的仪表盘分为三个部分,可分为“容器”,“表盘”,“指针”(名字是本人随便指定的,是否有专业的名次,请留言指正,谢谢!!!)。

1.“容器”部分QwtDial

   仪表盘所在的dialog,有了dialog才能在dialog上面设置背景,需要仪表盘的时候需要先new一个QwtDial对象,起的作用与容器类似,本次继承了QwtDial在其构造函数中,new了仪表盘表盘部分,new了指针部分,分别做好初始化后,设置到容器上,类似于给“容器”托管了,设置的关键如下图:

 

      ……
  //设置仪表盘背景到“容器”上
  setScaleDraw(_pScaleDraw);
  ……
  //设置仪表盘指针到“容器”上
  setNeedle( needle );
        ……

2.仪表盘的表盘部分

   表盘部分都是QwtAbstractScaleDraw的子类,具体读者可以自行查阅qwt的帮助文件。

 

    _pScaleDraw=newQwtRoundScaleDraw();
       //刻度线和标值之间的距离,默认为4pixels
    //_pScaleDraw->setSpacing(16);
    //是否显示将所有刻度连接起来的中心圆
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,true);
    //画线的宽度
//    _pScaleDraw->setPenWidth(15);
    //修改颜色
    QPalettepale=palette();
    //中间的背景
//    pale.setColor(QPalette::Foreground,Qt::red);
    //画线的颜色
    pale.setColor(QPalette::Text,Qt::black);
    setPalette(pale);
    //是否显示刻度线,下面可以不设置刻度线了
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Ticks,false);
    //是否显示仪表盘刻度线周围的显示值
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Labels,false);
    //非主刻度线非中间刻度其他小刻度沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MinorTick,20);
    //主刻度线之间中间的刻度沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MediumTick,20);
    //主刻度线沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MajorTick,20);
    //设置仪表盘刻度层到主层上
    setScaleDraw(_pScaleDraw);
    //???目前不太理解效果
    setWrapping(false);
    //只读,如果只读则鼠标无法移动指针
    setReadOnly(false);
    //起始角度,从中心右边横轴为0°,瞬时钟计算角度
    setOrigin(270.0);
// 角度范围,设置的其实角度为相对0°,相对于起始角度可活动多少度
    // 设置范围0°,仍然有表盘,所以我们不显示
// 特别注意:我们使用动态控制表盘的刻度范围来实现空间的百分比效果,本Demo没有使用到指针
    if(_radius<0.01)
    {
        _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,false);
    }else
    {
        _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,true);
    }
    setScaleArc(0.0,0.0);

3.仪表盘的指针部分

   指针剪头分为多种,箭头类型的可实现一种颜色或者左右对阵与箭头中心显示两种颜色,实现的效果可参照Demo或者之前的该系列上一篇的博客,博客地址为:

Qt之Qwt初探(一)

   http://blog.csdn.net/qq21497936/article/details/77852657

   指针范例的代码如下图:

 

//    QwtDialSimpleNeedle*needle=newQwtDialSimpleNeedle(
//    QwtDialSimpleNeedle::Arrow,true,Qt::red,
//    QColor(Qt::gray).light(130));
    //设置仪表盘指针到容器上
//    setNeedle(needle);

 

实现步骤

1.   初始化仪表盘

   设置仪表盘的表盘,没有指针所以不设置(后面开发的过程中,发现qwt本身是无法实现我们要的效果,需要我们重新补充其他部分)。

   下面是继承了QwtDial的类的构造函数中的初始化代码:

 

MSpacePanel::MSpacePanel(QWidget*parent):
 QwtDial(parent),
    _radius(0.0)
{
    QPalettepa(palette());
    pa.setColor(QPalette::Foreground,Qt::black);
    pa.setColor(QPalette::Text,Qt::black);
    pa.setColor(QPalette::Background,Qt::black);
    //显示百分比的lable
    _pLabel=newQLabel(this);
    _pLabel->setPalette(pa);
    _pLabel->show();
        //显示百分比下面文字信息的lable   
        _pLabel2=newQLabel(this);
    _pLabel2->setPalette(pa);
    _pLabel2->show();
    _pScaleDraw=newQwtRoundScaleDraw();
    //刻度线和标值之间的距离,默认为4pixels
    //_pScaleDraw->setSpacing(16);
    //是否显示将所有刻度连接起来的中心圆
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,true);
    //画线的宽度
//    _pScaleDraw->setPenWidth(15);
    //修改颜色
    QPalettepale=palette();
    //中间的背景
//    pale.setColor(QPalette::Foreground,Qt::red);
    //画线的颜色
    pale.setColor(QPalette::Text,Qt::black);
    setPalette(pale);
    //是否显示刻度线,下面可以不设置刻度线了
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Ticks,false);
    //是否显示仪表盘刻度线周围的显示值
    _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Labels,false);
    //非主刻度线非中间刻度其他小刻度沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MinorTick,20);
    //主刻度线之间中间的刻度沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MediumTick,20);
    //主刻度线沿指针方向的长度,默认显示刻度线
    _pScaleDraw->setTickLength(QwtScaleDiv::MajorTick,20);
    //设置仪表盘刻度层到主层上
    setScaleDraw(_pScaleDraw);
    //???目前不太理解效果
    setWrapping(false);
    //只读,如果只读则鼠标无法移动指针
    setReadOnly(false);
    //起始角度,从中心右边横轴为0°,瞬时钟计算角度
    setOrigin(270.0);
    //角度范围,设置的其实角度为相对0°,相对于起始角度可活动多少度
    //设置范围0°,仍然有表盘,所以我们不显示
    //特别注意:我们使用动态控制表盘的刻度范围来实现空间的百分比效果,本Demo没有使用到指针
    if(_radius<0.01)
    {
        _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,false);
    }else
    {
        _pScaleDraw->enableComponent(QwtAbstractScaleDraw::Backbone,true);
    }
    setScaleArc(0.0,0.0);
    //注释掉指针
//    QwtDialSimpleNeedle*needle=newQwtDialSimpleNeedle(
//        QwtDialSimpleNeedle::Arrow,true,Qt::red,
//        QColor(Qt::gray).light(130));
    //设置仪表盘指针到容器上
    //    setNeedle(needle);
    _propertyAnimation.setTargetObject(this);
    _propertyAnimation.setPropertyName("radius");
    _propertyAnimation.setStartValue(0.0);
    _propertyAnimation.setEndValue(0.0);
    _propertyAnimation.setDuration(DURATION_MS);
    _propertyAnimation.setEasingCurve(QEasingCurve::OutQuad);
    _propertyAnimation.start();
}  

   上文中使用了动画的效果,主要目的是使指针变数缓冲,动画效果的类实例_propertyAnimation,其中值得注意的是属性setPropertyName()函数的参数radius,这个我们在类声明的时候是手动注册的属性,注册的方法有两个步骤,步骤如下:

第一步:添加成员变量,添加成员变量读/写函数,如下:

class MSpacePanel:public QwtDial
{
   ……
private:
    ……
    double getRadius()const;
    void setRadius(constdoubleradius);
   ……
private:
   ……
   double _radius;
   ……
}

第二步:注册为属性

class MSpacePanel:public QwtDial
{
   Q_OBJECT
   //自定义属性
   Q_PROPERTY(double radius READ getRadius WRITEsetRadius)
   ……
}

2.resize窗口大小要做的事情

voidMSpacePanel::resizeEvent(QResizeEvent*event)
{
   _w=geometry().width();
   _h=geometry().height();
   _pLabel->setStyleSheet(QString("font:%1px").arg((int)(_w/4)));
   _pLabel->setGeometry((_w-_w/2.5)/2-10,(_h-_h/3)/2,_w/2.5+20,_h/3);
   _pLabel->setAlignment(Qt::AlignHCenter);
   _pLabel2->setStyleSheet(QString("font:%1px").arg((int)(_w/8)));
   _pLabel2->setGeometry((_w-_w/2.5)/2-20,(_h-_h/3)/2+50,_w/2.5+50,_h/3);
   _pLabel2->setAlignment(Qt::AlignHCenter);
   _pLabel2->setText("空间使用率");
   _pScaleDraw->setPenWidth(_w/15);
   _penWidth=_pScaleDraw->penWidth();
}

3.重画窗口需要设置值

   主要是限制最大值最小值和动画效果,动画不能使用pause,否则会直接设置到值(接上次剩余的时间到endValue),应该是stop然后重新开始运行动画。

 

voidMSpacePanel::setValue(double value)
{
     if(value>100.0)
        value=100.0;
    elseif(value<0.01)
        value=0;
    _propertyAnimation.stop();
    _propertyAnimation.setDuration(DURATION_MS);
    _propertyAnimation.setStartValue(_propertyAnimation.currentValue().toDouble());
    _propertyAnimation.setEndValue(value*3.6);
    _propertyAnimation.start();
}

4.实现我们的效果(还有空间未使用部分的灰色没有实现)

   为了实现我们的效果,只能重载painter函数,使用QPainter补充画剩余的圆弧,代码如下:

 

voidMSpacePanel::paintEvent(QPaintEvent*event)
{
    //调用基类,画基类
    QwtDial::paintEvent(event);
    //在已有的图形上画
    QPainter painter(this);
    painter.setPen(QPen(QColor(199,199,199),15));
    double space=13.5f;
//  qDebug()<<__FILE__<<__LINE__<<_radius*16<<360*16<<_w<<_h;
    painter.drawArc(0+space,0+space, _w-space*2,_h-space*2,90*16,360*16-_radius*16);
}

 

总结

   本次项目中需要实现的效果使用qwt完成,在开发的过程中,对qwt进一步了解,我们可以发现,需要实现的效果其实直接使用QPainter画图完成更好,我们主要的目的是实现效果的同时熟悉qwt技术,本次需求该效果的项目中将不会使用qwt完成。

 

原博主博客地址:https://blog.csdn.net/qq21497936

原博主博客导航:https://blog.csdn.net/qq21497936/article/details/102478062

本文章博客地址:http://blog.csdn.net/qq21497936/article/details/77881844



相关文章
|
2月前
|
算法 编译器 Linux
【Qt4 部署】ARM系统上使用Qt 4 进行开发的QWS 等环境变量部署
【Qt4 部署】ARM系统上使用Qt 4 进行开发的QWS 等环境变量部署
25 0
|
13天前
|
开发框架 编译器 C++
Qt:一个强大的跨平台C++应用程序开发框架
Qt:一个强大的跨平台C++应用程序开发框架
30 1
|
13天前
|
开发框架 Linux C++
Qt:强大的跨平台C++应用程序开发框架
Qt:强大的跨平台C++应用程序开发框架
44 3
|
17天前
|
开发框架 数据可视化 编译器
Qt的魅力:探索跨平台图形界面开发之旅
Qt的魅力:探索跨平台图形界面开发之旅
30 1
|
1月前
|
图形学 Python 容器
【PyQt5桌面应用开发】3.Qt Designer快速入门(控件详解)
【PyQt5桌面应用开发】3.Qt Designer快速入门(控件详解)
53 0
|
1月前
qt开发使用camera类获取摄像头信息并拍照保存
qt开发使用camera类获取摄像头信息并拍照保存
|
2月前
|
监控 C++
C++ Qt开发:QProcess进程管理模块
Qt是一个跨平台的C++图形库,简化了窗体应用开发,支持通过拖放组件提升效率。本章节关注`QProcess`组件,它用于控制和管理进程,例如执行命令、运行可执行文件及与外部进程通信。`QProcess`提供多种方法如`start`、`waitForStarted`和`waitForFinished`等,实现启动、监控和交互。示例展示了如何使用`QProcess`获取系统进程和信息,通过`tasklist`和`systeminfo`命令,并将结果展示在`QTreeWidget`中。
33 0
C++ Qt开发:QProcess进程管理模块
|
2月前
|
网络协议 C++
C++ Qt开发:QTcpSocket网络通信组件
`QTcpSocket`和`QTcpServer`是Qt中用于实现基于TCP(Transmission Control Protocol)通信的两个关键类。TCP是一种面向连接的协议,它提供可靠的、双向的、面向字节流的通信。这两个类允许Qt应用程序在网络上建立客户端和服务器之间的连接。Qt 是一个跨平台C++图形界面开发库,利用Qt可以快速开发跨平台窗体应用程序,在Qt中我们可以通过拖拽的方式将不同组件放到指定的位置,实现图形化开发极大的方便了开发效率,本章将重点介绍如何运用`QTcpSocket`组件实现基于TCP的网络通信功能。
44 8
C++ Qt开发:QTcpSocket网络通信组件
|
4月前
|
SQL 数据库 C++
C++ Qt开发:Charts与数据库组件联动
Qt 是一个跨平台C++图形界面开发库,利用Qt可以快速开发跨平台窗体应用程序,在Qt中我们可以通过拖拽的方式将不同组件放到指定的位置,实现图形化开发极大的方便了开发效率,本章将重点介绍`Charts`组件与`QSql`数据库组件的常用方法及灵活运用。在之前的文章中详细介绍了关于`QCharts`绘图组件的使用方式,本章将继续延续这个知识点,通过使用`QSql`数据库模块动态的读取某一个时间节点上的数据,当用户点击查询数据时则动态的输出该事件节点的所有数据,并将数据绘制到图形组件内,实现动态查询图形的功能。
37 0
C++ Qt开发:Charts与数据库组件联动
|
2月前
|
存储 C++ 网络架构
C++ Qt开发:QUdpSocket实现组播通信
Qt教程:使用`QUdpSocket`实现UDP组播通信。通过设置套接字选项、绑定端口、加入和离开组播组,以及发送和接收数据报,简化跨平台窗体应用开发。关键函数包括`setSocketOption`设置多播TTL,`bind`绑定地址和端口,`joinMulticastGroup`加入组播,`leaveMulticastGroup`退出,`writeDatagram`发送,和`readDatagram`接收数据报。
40 1
C++ Qt开发:QUdpSocket实现组播通信

推荐镜像

更多