zoukankan      html  css  js  c++  java
  • Qt实现数字滚动动画效果

    自己开发了一个股票智能分析软件,功能很强大,需要的点击下面的链接获取:

    https://www.cnblogs.com/bclshuai/p/11380657.html

    1.1  Qt实现数字滚动动画效果

    1.1.1         应用场景说明

    如下图所示,需要显示人脸检测的数量,变动画的方式实现个位数字滚动,个位由9变成0时,十位也要滚动,实现进位。当个位十位都是9时,数字不在增加,而是显示加号+。

      

    1.1.2         实现方法

    实现方案,个位十位都有上下两个label显示数字。通过QPropertyAnimation属性动画控制两个label位置同时向上。动画结束后,再将两个label还原到原始位置。在还原位置之前,先前上面的labelnum值设置为下面labelnum1的值,下面labelnum1的值设置为+1后的值,避免出现数字闪现变小的问题。

     

    头文件实现

    #ifndef NUMSHOWWIDGET_H

    #define NUMSHOWWIDGET_H

    #include <QPropertyAnimation>

    #include<QParallelAnimationGroup>

    #include <QSequentialAnimationGroup>

    #include <QWidget>

    #include"ui_NumShowWidget.h"

    #include<QMutex>

    #include<QWaitCondition>

    #include<QTimer>

    class NumShowWidget : public QWidget

    {

        Q_OBJECT

     

    public:

        NumShowWidget();

        ~NumShowWidget();

        void initNum();//个位十位上下初始化0,1值

        /*

        设置为某个值,会根据数字增量的大小增加数字值,根据time求出平均动画时间步长。增量大时速度快,增量小时速度慢

        */

        void setNum(int num,int time);

        void addNum(int num, int time);

        public slots:

        void SlotTimeAddNum();

        int getNum();

        void pushNum(int num);

    private:

        Ui::NumShowWidget ui;

        int m_tenwei = 0;//十位

        int m_gewei = 0;//个位

        QLabel* m_tenCurrent = NULL;//十位当前label

        QLabel* m_tenDown=NULL;//十位下面的label

        QLabel* m_geCurrent = NULL;//个位当前label

        QLabel* m_geDown = NULL;//个位下面的label

        int m_count = 0;//动画执行的次数,增量为10,则执行十次上滚动画

        int m_num=0;//保存当前显示的数字。

        QParallelAnimationGroup* tenAnimation;

        QMutex m_mutex;

        QWaitCondition m_FinishAnimation;

        QTimer m_checktime;

        QMutex m_addNumMutex;

        QVector<int> m_vectNum;

        bool m_bFinishAni=true;//避免第一次动画未执行结束,第二次动画就开始,会错乱,所加上一个判断条件。

        QPropertyAnimation * tenCurrent =NULL;

        QPropertyAnimation * tenDown = NULL;

    };

    #endif // NUMSHOWWIDGET_H

    源文件实现

    #include "NumShowWidget.h"

    #include"hlog1.h"

    #include<QFontDatabase>

    NumShowWidget::NumShowWidget()

    {

        ui.setupUi(this);

        setWindowModality(Qt::NonModal);

        setWindowFlags(Qt::FramelessWindowHint);

        this->resize(32, 32);

        m_tenCurrent = ui.labelten;

        m_tenDown = ui.labelten1;

        m_geCurrent = ui.labelnum;

        m_geDown = ui.labelnum1;

        m_tenCurrent->setText("0");

        m_tenDown->setText("1");

        m_geCurrent->setText("0");

        m_geDown->setText("1");

        ui.labelplus->hide();

        tenAnimation = new QParallelAnimationGroup(this);

        tenCurrent = new QPropertyAnimation(m_tenCurrent, "geometry");

        tenCurrent->setDuration(100);

        tenCurrent->setStartValue(QRect(4, 0, 12, 32));

        tenCurrent->setEndValue(QRect(4, -32, 12, 32));

        tenAnimation->addAnimation(tenCurrent);

        tenDown = new QPropertyAnimation(m_tenDown, "geometry");

        tenDown->setDuration(100);

        tenDown->setStartValue(QRect(4, 32, 12, 32));

        tenDown->setEndValue(QRect(4, 0, 12, 32));

        tenAnimation->addAnimation(tenDown);

        connect(tenAnimation, &QAbstractAnimation::finished, this, [=]() {

            m_tenCurrent->setText(QString::number(m_tenwei++));

            m_tenCurrent->setGeometry(4, 0, 12, 32);

            m_tenCurrent->raise();

            m_tenDown->setGeometry(4, 32, 12, 32);

            m_tenDown->setText(QString::number((m_tenwei + 1)));

        });

        m_checktime.setInterval(1000);

        connect(&m_checktime, &QTimer::timeout, this, &NumShowWidget::SlotTimeAddNum);

        m_checktime.start();

    }

     

    NumShowWidget::~NumShowWidget()

    {

        if (tenAnimation != NULL)

        {

            delete tenAnimation;

            tenAnimation = NULL;

        }

    }

     

    void NumShowWidget::initNum()

    {

        m_tenwei = 1;

        m_gewei = 1;

        m_num = 0;

        m_tenCurrent->setText("0");

        m_tenCurrent->setGeometry(QRect(4, 0, 12, 32));

        m_tenDown->setText("1");

        m_tenDown->setGeometry(QRect(4, 32, 12, 32));

        m_geCurrent->setText("0");

        m_geDown->setText("1");

        m_geCurrent->setGeometry(QRect(15, 0, 12, 32));

        m_geDown->setGeometry(QRect(15, 32, 12, 32));

        ui.labelplus->hide();

        m_vectNum.clear();

        m_bFinishAni = true;

       

    }

     

    void NumShowWidget::setNum(int num, int time)

    {

        if (ui.labelplus->isVisible())

        {

            return;

        }

        m_num = ui.labelten->text().toInt()*10+ui.labelnum->text().toInt();

        if (num <= m_num)//值没有变

        {

            m_mutex.lock();

            m_bFinishAni = true;

            m_mutex.unlock();

            return;

        }

        addNum(num - m_num, time);

    }

     

    void NumShowWidget::addNum(int num, int time)

    {

       

        if (num <= 0)

        {

            return;

        }

        LOG_INFO("NUCOUNT LOCK");

        int steptime = time / num;//动画时间步长

        tenCurrent->setDuration(steptime);

        tenDown->setDuration(steptime);

        m_count = num;

        QParallelAnimationGroup* paraAnimation = new QParallelAnimationGroup(this);

        QPropertyAnimation * geCurrent = new QPropertyAnimation(m_geCurrent, "geometry");

        geCurrent->setDuration(steptime);

        geCurrent->setStartValue(QRect(15, 0, 12, 32));

        geCurrent->setEndValue(QRect(15, -32, 12, 32));

        paraAnimation->addAnimation(geCurrent);

        QPropertyAnimation *geDown = new QPropertyAnimation(m_geDown, "geometry");

        geDown->setDuration(steptime);

        geDown->setStartValue(QRect(15, 32, 12, 32));

        geDown->setEndValue(QRect(15, 0, 12, 32));

        paraAnimation->addAnimation(geDown);

        paraAnimation->start();

        connect(paraAnimation, &QAbstractAnimation::finished, this, [=]() {

            m_count--;

            m_geCurrent->setText(QString::number(m_gewei++));

            m_geCurrent->setGeometry(15, 0, 12, 32);

            m_geCurrent->raise();

            m_geDown->setGeometry(15, 32, 12, 32);

            if (m_gewei >= 10)

            {

                 if (m_tenwei < 10)

                 {

                     tenAnimation->start();

                 }

                 else

                 {

                     ui.labelplus->show();

                     m_mutex.lock();

                     m_bFinishAni = true;

                     m_mutex.unlock();

                     delete paraAnimation;

                     LOG_INFO("NUCOUNT ULOCK");

                     return;

                }

                 m_gewei = 0;

            }

            m_geDown->setText(QString::number((m_gewei) % 10));

            if (m_count > 0)

            {

                 paraAnimation->start();

            }

            else

            {

                 m_mutex.lock();

                 m_bFinishAni = true;

                 m_mutex.unlock();

                 delete paraAnimation;

                 LOG_INFO("NUCOUNT ULOCK");

                

            }

        })

    }

    void NumShowWidget::SlotTimeAddNum()

    {

        if (m_bFinishAni)

        {

            int num = getNum();

            if (num > 0)

            {  

                 m_mutex.lock();

                 m_bFinishAni = false;

                 m_mutex.unlock();

                 setNum(num, 1000);

                

            }

        }

    }

    int NumShowWidget::getNum()

    {

        m_addNumMutex.lock();

        if (m_vectNum.size() > 0)

        {

            int num = m_vectNum.front();

            m_vectNum.pop_front();

            m_addNumMutex.unlock();

            return num;

        }

        else

        {

            m_addNumMutex.unlock();

            return -1;

        }

       

    }

    void NumShowWidget::pushNum(int num)

    {

        m_addNumMutex.lock();

        m_vectNum.push_back(num);

        m_addNumMutex.unlock();

    }

  • 相关阅读:
    方便的使用单击和双击更新DataGrid中的数据的例子 (转)
    针对 .NET 开发人员的存储过程评估(转)
    ASP.NET创建Web服务之XML基础结构(转)
    移动业务咨询系统--用VoiceXML开发语音应用程序(转)
    创建动态数据输入用户界面 (转)
    ASP.NET缓存:方法和最佳实践(转)
    ASP.NET 应用程序性能优化(转)
    出色图形用户界面(GUI)设计规范(转,中英对比)
    五种常见的ASP.NET安全缺陷(转)
    ASP.net控件开发系列之(一)开篇(转)
  • 原文地址:https://www.cnblogs.com/bclshuai/p/14104969.html
Copyright © 2011-2022 走看看