Qt5开发从入门到精通——第十一篇三节(Qt5 事件处理及实例——事件过滤及实例)

提示:欢迎小伙伴的点评✨✨,相互学习c/c++应用开发。🍳🍳🍳
博主🧑🧑 本着开源的精神交流Qt开发的经验、将持续更新续章,为社区贡献博主自身的开源精神👩‍🚀


前言

本章节会给大家带来Qt5 事件处理及实例——事件过滤及实例详解。


一、事件过滤及实例概述

Qt 的事件模型中提供的事件过滤器功能使得 一个 QObject 对象可以监视另 一个 QObject 对象中的事件,通过在一个 QObject 对象中安装事件过滤器,可以在事件到达该对象前捕获事件,从而起到监视该对象事件的作用。
例如, Qt 已经提供了 QPushButton 用千表示一个普通的按钮类。如果需要实现一个动态的图片按钮,即当鼠标键按下时按钮图片发生变化,则需要同时响应鼠标按下等事件。

二、效果实例

三个图片分别对应三个 QLabel 对象 。 当用鼠标键按下某个图片时,图片大小会发生变化;而释放鼠标键时,图片又恢复初始大小,并且程序将提示当前事件的状态信息,如鼠标键类型、被鼠标键按下的图片序号。
新建Resources 并建立image文件 添加现有Src将tu.png图片放入其中
图一
在这里插入图片描述

图二
在这里插入图片描述

三、原码实例

eventfilter.h

#ifndef EVENTFILTER_H
#define EVENTFILTER_H

#include <QDialog>
#include <QLabel>
#include <QImage>
#include <QEvent>
class EventFilter : public QDialog
{
    Q_OBJECT

public:
    EventFilter(QWidget *parent = 0);
    ~EventFilter();
public slots:
    bool eventFilter(QObject *, QEvent *);
private:
    QLabel *label1;
    QLabel *label2;
    QLabel *label3;
    QLabel *stateLabel;
    QImage Image1;
    QImage Image2;
    QImage Image3;
};

#endif // EVENTFILTER_H

eventfilter.cpp

#include "eventfilter.h"
#include <QHBoxLayout>
#include <QVBoxLayout>
#include <QMouseEvent>
#include <QMatrix>
EventFilter::EventFilter(QWidget *parent)
    : QDialog(parent)
{


    setWindowTitle(tr(" 事件过滤")) ;
    label1 = new QLabel;
    Image1.load(":/Src/13.png");

    label1->setAlignment (Qt::AlignHCenter|Qt::AlignVCenter);
    label1->setPixmap(QPixmap::fromImage(Image1));
    label2 = new QLabel;
    Image2.load(":/Src/14.png");
    label2->setAlignment(Qt::AlignHCenter|Qt::AlignVCenter);
    label2->setPixmap(QPixmap::fromImage(Image2));
    label3 = new QLabel;
    Image3.load(":/Src/15.png");
    label3->setAlignment (Qt::AlignHCenter|Qt::AlignVCenter);
    label3->setPixmap(QPixmap::fromImage(Image3));
    stateLabel = new QLabel(tr("鼠标键按下标志"));
    stateLabel->setAlignment(Qt::AlignHCenter);
    QHBoxLayout *layout=new QHBoxLayout;
    layout->addWidget(label1);
    layout->addWidget(label2);
    layout->addWidget(label3);
    QVBoxLayout *mainLayout = new QVBoxLayout(this);
    mainLayout->addLayout(layout);
    mainLayout->addWidget(stateLabel);
    label1->installEventFilter(this);
    label2->installEventFilter(this);
    label3->installEventFilter(this);
    /* installEventFilterO函数为每一个图片安装事件过滤器,
     * 指定整个窗体为监视事件的对象,函数原型如下:
     * void QObject::installEventFilter
     * (
     *      QObject * filterObj
     * )
     * 参数 filterObj 是监视事件的对象,此对象可以通过 eventFilter()函数接收事件。如果某个事
     * 件需要被过滤,即停止正常的事件响应,则在 eventFilter()函数中返回 true, 否则返回 false 。
     * QObject 的 removeEventFilter() 函数可以解除已安装的事件过滤器。
     */


    
}

EventFilter::~EventFilter()
{

}

/*QObject 的事件监视函数 eventFilter()的具体实现*/
bool EventFilter::eventFilter(QObject *watched, QEvent *event)
{
    if(watched==label1) //首先判断当前发生事件的对象
    {
        ///判断发生的事件类型
        if(event->type()==QEvent::MouseButtonPress)
        {
            //将事件 event 转化为鼠标事件
            QMouseEvent *mouseEvent= (QMouseEvent *) event;
            /**以下根据鼠标键的类型分别显示*/
            if (mouseEvent->buttons()&Qt::LeftButton)
            {
                stateLabel->setText(tr("左键按下左边图片"));
            }
            else if (mouseEvent->buttons ()&Qt::MidButton)
            {
                stateLabel->setText(tr(" 中键按下左边图片"));
            }else if(mouseEvent->buttons()&Qt::RightButton)
            {
                stateLabel->setText(tr(" 右键按下左边图片")) ;
            }
            /*显示缩小的图片*/
            QMatrix matrix;
            matrix.scale(1.8,1.8);
            QImage tmpimg=Image1.transformed(matrix);
            label1->setPixmap(QPixmap::fromImage(tmpimg));
        }
         /*鼠标释放事件的处理,恢复图片的大小*/
        if(event->type()==QEvent::MouseButtonRelease)
        {
            stateLabel->setText(tr(" 鼠标释放左边图片")) ;
            label1->setPixmap(QPixmap::fromImage(Image1));
        }
    }else if(watched==label2)
    {
        ///判断发生的事件类型
        if(event->type()==QEvent::MouseButtonPress)
        {
            //将事件 event 转化为鼠标事件
            QMouseEvent *mouseEvent= (QMouseEvent *) event;
            /**以下根据鼠标键的类型分别显示*/
            if (mouseEvent->buttons()&Qt::LeftButton)
            {
                stateLabel->setText(tr("左键按下中间图片"));
            }
            else if (mouseEvent->buttons ()&Qt::MidButton)
            {
                stateLabel->setText(tr(" 中键按下中间图片"));
            }else if(mouseEvent->buttons()&Qt::RightButton)
            {
                stateLabel->setText(tr(" 右键按下中间图片")) ;
            }
            /*显示缩小的图片*/
            QMatrix matrix;
            matrix.scale(1.8,1.8);
            QImage tmpimg=Image2.transformed(matrix);
            label2->setPixmap(QPixmap::fromImage(tmpimg));
        }
         /*鼠标释放事件的处理,恢复图片的大小*/
        if(event->type()==QEvent::MouseButtonRelease)
        {
            stateLabel->setText(tr(" 鼠标释放中间图片")) ;
            label2->setPixmap(QPixmap::fromImage(Image2));
        }
    }else if(watched==label3)
    {
        ///判断发生的事件类型
        if(event->type()==QEvent::MouseButtonPress)
        {
            //将事件 event 转化为鼠标事件
            QMouseEvent *mouseEvent= (QMouseEvent *) event;
            /**以下根据鼠标键的类型分别显示*/
            if (mouseEvent->buttons()&Qt::LeftButton)
            {
                stateLabel->setText(tr("左键按下右边图片"));
            }
            else if (mouseEvent->buttons ()&Qt::MidButton)
            {
                stateLabel->setText(tr(" 中键按下右边图片"));
            }else if(mouseEvent->buttons()&Qt::RightButton)
            {
                stateLabel->setText(tr(" 右键按下右边图片")) ;
            }
            /*显示缩小的图片*/
            QMatrix matrix;
            matrix.scale(1.8,1.8);
            QImage tmpimg=Image3.transformed(matrix);
            label3->setPixmap(QPixmap::fromImage(tmpimg));
        }
         /*鼠标释放事件的处理,恢复图片的大小*/
        if(event->type()==QEvent::MouseButtonRelease)
        {
            stateLabel->setText(tr(" 鼠标释放右边图片")) ;
            label3->setPixmap(QPixmap::fromImage(Image3));
        }
    }

    //将事件交给上层对话框
    return QDialog::eventFilter(watched,event);
}

main.cpp

#include "eventfilter.h"
#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    EventFilter w;
    w.show();

    return a.exec();
}

EventFilter解析

  1. void QObject::installEventFilter (QObject* filterObj);
    把filterObj对象安装(或注册)为事件过滤器,filterObj也称为过滤器对象。事件过滤器通常在构造函数中进行注册。
  2. bool QObject::eventFilter(QObject* obj, QEvent* e);
    来接收拦截到的事件。也就是说拦截到的事件在filterObj对象中的eventFilter函数中处理。eventFilter的第一个参数obj指向的是事件本应传递到的目标对象。
  3. 使用QObject::removeEventFilter(QObject *obj);函数可以删除事件过滤器。

四、总结

Qt5 事件处理及实例——事件过滤及实例会在应用程序开发中经常用到的。

  • 12
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 21
    评论
评论 21
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

东.'

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值