精华内容
下载资源
问答
  • QEvent
    2020-07-27 17:46:40

    简述

    QEvent 是其他所有event类的基类,事件对象包含事件参数。

    QT的主事件循环(QCoreApplication::exec()) 从事件队列中获得窗口的事件,把他们转换为QEvent ,然后分发给对象。

    一般来说,事件来自底层的窗口系统(spontaneous() returns true),但是我们也可以通过QCoreApplication::sendEvent() 和QCoreApplication::postEvent() 来手动发送事件。

    对象收到事件后会调用QObject::event()函数。该函数也可以在子类中实现,可以自定义事件和添加额外的时间类型。

    QWidget::event() 是一个著名的例子。默认情况下,事件被分发给事件处理函数QObject::timerEvent() and QWidget::mouseMoveEvent()。通过 QObject::installEventFilter()可以拦截事件发送给另外一个对象。

    更多相关内容
  • QT之QEvent机制

    2020-05-25 21:01:58
    1.QEvent简介 QEvent是QT的事件机制。QT的事件机制,肯定是借鉴了Windows的消息机制。Windows把所有的鼠标键盘以及内部事件都当作消息,并放进消息处理机制处理。QT本身,是把各个操作系统的API进行调用。Windows...

    1.QEvent简介

           QEvent是QT的事件机制。QT的事件机制,肯定是借鉴了Windows的消息机制。Windows把所有的鼠标键盘以及内部事件都当作消息,并放进消息处理机制处理。QT本身,是把各个操作系统的API进行调用。Windows的消息机制,是一个非常简单有效的机制,QT作为借鉴,不为过。

          QEvent是QT的事件机制的基础;QEvent可以被QOject灵活运动,使事件得到接收和响应。

           Qt的主事件循环(QCoreApplication :: exec())从事件队列中获取本机窗口系统事件,将其转换为QEvents,然后将转换后的事件发送给QObject。

           通常,事件来自底层窗口系统(spontaneous()返回true),但是也可以使用QCoreApplication :: sendEvent()和QCoreApplication :: postEvent()手动发送事件(spontaneous()返回false)。

           QObject通過調用其QObject :: event()函數來接收事件。可以在子類中重新實現該函數,以自定義事件處理並添加其他事件類型。QWidget :: event()是一個著名的例子。默認情況下,事件被調度到事件處理程序,例如QObject :: timerEvent()和QWidget :: mouseMoveEvent()。QObject :: installEventFilter()允许一個對象攔截發往另一個對象的事件。

           基本的QEvent僅包含事件類型參數和“ accept”標誌。接受標誌設置為accept(),並使用ignore()清除。它是默認設置的,但是不要依賴它,因為子類可以選擇在其構造函數中清除它。

              QEvent的子類包含描述特定事件的其他參數。

    2.QEvent分类

           QEvent的分类如下:

         

    Constant

    Value

    Description

    QEvent::None

    0

    Not an event.

    QEvent::ActionAdded

    114

    A new action has been added (QActionEvent).

    QEvent::ActionChanged

    113

    An action has been changed (QActionEvent).

    QEvent::ActionRemoved

    115

    An action has been removed (QActionEvent).

    QEvent::ActivationChange

    99

    A widget's top-level window activation state has changed.

    QEvent::ApplicationActivate

    121

    This enum has been deprecated. Use ApplicationStateChange instead.

    QEvent::ApplicationActivated

    ApplicationActivate

    This enum has been deprecated. Use ApplicationStateChange instead.

    QEvent::ApplicationDeactivate

    122

    This enum has been deprecated. Use ApplicationStateChange instead.

    QEvent::ApplicationFontChange

    36

    The default application font has changed.

    QEvent::ApplicationLayoutDirectionChange

    37

    The default application layout direction has changed.

    QEvent::ApplicationPaletteChange

    38

    The default application palette has changed.

    QEvent::ApplicationStateChange

    214

    The state of the application has changed.

    QEvent::ApplicationWindowIconChange

    35

    The application's icon has changed.

    QEvent::ChildAdded

    68

    An object gets a child (QChildEvent).

    QEvent::ChildPolished

    69

    A widget child gets polished (QChildEvent).

    QEvent::ChildRemoved

    71

    An object loses a child (QChildEvent).

    QEvent::Clipboard

    40

    The clipboard contents have changed.

    QEvent::Close

    19

    Widget was closed (QCloseEvent).

    QEvent::CloseSoftwareInputPanel

    200

    A widget wants to close the software input panel (SIP).

    QEvent::ContentsRectChange

    178

    The margins of the widget's content rect changed.

    QEvent::ContextMenu

    82

    Context popup menu (QContextMenuEvent).

    QEvent::CursorChange

    183

    The widget's cursor has changed.

    QEvent::DeferredDelete

    52

    The object will be deleted after it has cleaned up (QDeferredDeleteEvent)

    QEvent::DragEnter

    60

    The cursor enters a widget during a drag and drop operation (QDragEnterEvent).

    QEvent::DragLeave

    62

    The cursor leaves a widget during a drag and drop operation (QDragLeaveEvent).

    QEvent::DragMove

    61

    A drag and drop operation is in progress (QDragMoveEvent).

    QEvent::Drop

    63

    A drag and drop operation is completed (QDropEvent).

    QEvent::DynamicPropertyChange

    170

    A dynamic property was added, changed, or removed from the object.

    QEvent::EnabledChange

    98

    Widget's enabled state has changed.

    QEvent::Enter

    10

    Mouse enters widget's boundaries (QEnterEvent).

    QEvent::EnterEditFocus

    150

    An editor widget gains focus for editing. QT_KEYPAD_NAVIGATION must be defined.

    QEvent::EnterWhatsThisMode

    124

    Send to toplevel widgets when the application enters "What's This?" mode.

    QEvent::Expose

    206

    Sent to a window when its on-screen contents are invalidated and need to be flushed from the backing store.

    QEvent::FileOpen

    116

    File open request (QFileOpenEvent).

    QEvent::FocusIn

    8

    Widget or Window gains keyboard focus (QFocusEvent).

    QEvent::FocusOut

    9

    Widget or Window loses keyboard focus (QFocusEvent).

    QEvent::FocusAboutToChange

    23

    Widget or Window focus is about to change (QFocusEvent)

    QEvent::FontChange

    97

    Widget's font has changed.

    QEvent::Gesture

    198

    A gesture was triggered (QGestureEvent).

    QEvent::GestureOverride

    202

    A gesture override was triggered (QGestureEvent).

    QEvent::GrabKeyboard

    188

    Item gains keyboard grab (QGraphicsItem only).

    QEvent::GrabMouse

    186

    Item gains mouse grab (QGraphicsItem only).

    QEvent::GraphicsSceneContextMenu

    159

    Context popup menu over a graphics scene (QGraphicsSceneContextMenuEvent).

    QEvent::GraphicsSceneDragEnter

    164

    The cursor enters a graphics scene during a drag and drop operation (QGraphicsSceneDragDropEvent).

    QEvent::GraphicsSceneDragLeave

    166

    The cursor leaves a graphics scene during a drag and drop operation (QGraphicsSceneDragDropEvent).

    QEvent::GraphicsSceneDragMove

    165

    A drag and drop operation is in progress over a scene (QGraphicsSceneDragDropEvent).

    QEvent::GraphicsSceneDrop

    167

    A drag and drop operation is completed over a scene (QGraphicsSceneDragDropEvent).

    QEvent::GraphicsSceneHelp

    163

    The user requests help for a graphics scene (QHelpEvent).

    QEvent::GraphicsSceneHoverEnter

    160

    The mouse cursor enters a hover item in a graphics scene (QGraphicsSceneHoverEvent).

    QEvent::GraphicsSceneHoverLeave

    162

    The mouse cursor leaves a hover item in a graphics scene (QGraphicsSceneHoverEvent).

    QEvent::GraphicsSceneHoverMove

    161

    The mouse cursor moves inside a hover item in a graphics scene (QGraphicsSceneHoverEvent).

    QEvent::GraphicsSceneMouseDoubleClick

    158

    Mouse press again (double click) in a graphics scene (QGraphicsSceneMouseEvent).

    QEvent::GraphicsSceneMouseMove

    155

    Move mouse in a graphics scene (QGraphicsSceneMouseEvent).

    QEvent::GraphicsSceneMousePress

    156

    Mouse press in a graphics scene (QGraphicsSceneMouseEvent).

    QEvent::GraphicsSceneMouseRelease

    157

    Mouse release in a graphics scene (QGraphicsSceneMouseEvent).

    QEvent::GraphicsSceneMove

    182

    Widget was moved (QGraphicsSceneMoveEvent).

    QEvent::GraphicsSceneResize

    181

    Widget was resized (QGraphicsSceneResizeEvent).

    QEvent::GraphicsSceneWheel

    168

    Mouse wheel rolled in a graphics scene (QGraphicsSceneWheelEvent).

    QEvent::Hide

    18

    Widget was hidden (QHideEvent).

    QEvent::HideToParent

    27

    A child widget has been hidden.

    QEvent::HoverEnter

    127

    The mouse cursor enters a hover widget (QHoverEvent).

    QEvent::HoverLeave

    128

    The mouse cursor leaves a hover widget (QHoverEvent).

    QEvent::HoverMove

    129

    The mouse cursor moves inside a hover widget (QHoverEvent).

    QEvent::IconDrag

    96

    The main icon of a window has been dragged away (QIconDragEvent).

    QEvent::IconTextChange

    101

    Widget's icon text has been changed. (Deprecated)

    QEvent::InputMethod

    83

    An input method is being used (QInputMethodEvent).

    QEvent::InputMethodQuery

    207

    A input method query event (QInputMethodQueryEvent)

    QEvent::KeyboardLayoutChange

    169

    The keyboard layout has changed.

    QEvent::KeyPress

    6

    Key press (QKeyEvent).

    QEvent::KeyRelease

    7

    Key release (QKeyEvent).

    QEvent::LanguageChange

    89

    The application translation changed.

    QEvent::LayoutDirectionChange

    90

    The direction of layouts changed.

    QEvent::LayoutRequest

    76

    Widget layout needs to be redone.

    QEvent::Leave

    11

    Mouse leaves widget's boundaries.

    QEvent::LeaveEditFocus

    151

    An editor widget loses focus for editing. QT_KEYPAD_NAVIGATION must be defined.

    QEvent::LeaveWhatsThisMode

    125

    Send to toplevel widgets when the application leaves "What's This?" mode.

    QEvent::LocaleChange

    88

    The system locale has changed.

    QEvent::NonClientAreaMouseButtonDblClick

    176

    A mouse double click occurred outside the client area (QMouseEvent).

    QEvent::NonClientAreaMouseButtonPress

    174

    A mouse button press occurred outside the client area (QMouseEvent).

    QEvent::NonClientAreaMouseButtonRelease

    175

    A mouse button release occurred outside the client area (QMouseEvent).

    QEvent::NonClientAreaMouseMove

    173

    A mouse move occurred outside the client area (QMouseEvent).

    QEvent::MacSizeChange

    177

    The user changed his widget sizes (macOS only).

    QEvent::MetaCall

    43

    An asynchronous method invocation via QMetaObject::invokeMethod().

    QEvent::ModifiedChange

    102

    Widgets modification state has been changed.

    QEvent::MouseButtonDblClick

    4

    Mouse press again (QMouseEvent).

    QEvent::MouseButtonPress

    2

    Mouse press (QMouseEvent).

    QEvent::MouseButtonRelease

    3

    Mouse release (QMouseEvent).

    QEvent::MouseMove

    5

    Mouse move (QMouseEvent).

    QEvent::MouseTrackingChange

    109

    The mouse tracking state has changed.

    QEvent::Move

    13

    Widget's position changed (QMoveEvent).

    QEvent::NativeGesture

    197

    The system has detected a gesture (QNativeGestureEvent).

    QEvent::OrientationChange

    208

    The screens orientation has changes (QScreenOrientationChangeEvent).

    QEvent::Paint

    12

    Screen update necessary (QPaintEvent).

    QEvent::PaletteChange

    39

    Palette of the widget changed.

    QEvent::ParentAboutToChange

    131

    The widget parent is about to change.

    QEvent::ParentChange

    21

    The widget parent has changed.

    QEvent::PlatformPanel

    212

    A platform specific panel has been requested.

    QEvent::PlatformSurface

    217

    A native platform surface has been created or is about to be destroyed (QPlatformSurfaceEvent).

    QEvent::Polish

    75

    The widget is polished.

    QEvent::PolishRequest

    74

    The widget should be polished.

    QEvent::QueryWhatsThis

    123

    The widget should accept the event if it has "What's This?" help (QHelpEvent).

    QEvent::ReadOnlyChange

    106

    Widget's read-only state has changed (since Qt 5.4).

    QEvent::RequestSoftwareInputPanel

    199

    A widget wants to open a software input panel (SIP).

    QEvent::Resize

    14

    Widget's size changed (QResizeEvent).

    QEvent::ScrollPrepare

    204

    The object needs to fill in its geometry information (QScrollPrepareEvent).

    QEvent::Scroll

    205

    The object needs to scroll to the supplied position (QScrollEvent).

    QEvent::Shortcut

    117

    Key press in child for shortcut key handling (QShortcutEvent).

    QEvent::ShortcutOverride

    51

    Key press in child, for overriding shortcut key handling (QKeyEvent). When a shortcut is about to trigger, ShortcutOverride is sent to the active window. This allows clients (e.g. widgets) to signal that they will handle the shortcut themselves, by accepting the event. If the shortcut override is accepted, the event is delivered as a normal key press to the focus widget. Otherwise, it triggers the shortcut action, if one exists.

    QEvent::Show

    17

    Widget was shown on screen (QShowEvent).

    QEvent::ShowToParent

    26

    A child widget has been shown.

    QEvent::SockAct

    50

    Socket activated, used to implement QSocketNotifier.

    QEvent::StateMachineSignal

    192

    A signal delivered to a state machine (QStateMachine::SignalEvent).

    QEvent::StateMachineWrapped

    193

    The event is a wrapper for, i.e., contains, another event (QStateMachine::WrappedEvent).

    QEvent::StatusTip

    112

    A status tip is requested (QStatusTipEvent).

    QEvent::StyleChange

    100

    Widget's style has been changed.

    QEvent::TabletMove

    87

    Wacom tablet move (QTabletEvent).

    QEvent::TabletPress

    92

    Wacom tablet press (QTabletEvent).

    QEvent::TabletRelease

    93

    Wacom tablet release (QTabletEvent).

    QEvent::TabletEnterProximity

    171

    Wacom tablet enter proximity event (QTabletEvent), sent to QApplication.

    QEvent::TabletLeaveProximity

    172

    Wacom tablet leave proximity event (QTabletEvent), sent to QApplication.

    QEvent::TabletTrackingChange

    219

    The Wacom tablet tracking state has changed (since Qt 5.9).

    QEvent::ThreadChange

    22

    The object is moved to another thread. This is the last event sent to this object in the previous thread. See QObject::moveToThread().

    QEvent::Timer

    1

    Regular timer events (QTimerEvent).

    QEvent::ToolBarChange

    120

    The toolbar button is toggled on macOS.

    QEvent::ToolTip

    110

    A tooltip was requested (QHelpEvent).

    QEvent::ToolTipChange

    184

    The widget's tooltip has changed.

    QEvent::TouchBegin

    194

    Beginning of a sequence of touch-screen or track-pad events (QTouchEvent).

    QEvent::TouchCancel

    209

    Cancellation of touch-event sequence (QTouchEvent).

    QEvent::TouchEnd

    196

    End of touch-event sequence (QTouchEvent).

    QEvent::TouchUpdate

    195

    Touch-screen event (QTouchEvent).

    QEvent::UngrabKeyboard

    189

    Item loses keyboard grab (QGraphicsItem only).

    QEvent::UngrabMouse

    187

    Item loses mouse grab (QGraphicsItemQQuickItem).

    QEvent::UpdateLater

    78

    The widget should be queued to be repainted at a later time.

    QEvent::UpdateRequest

    77

    The widget should be repainted.

    QEvent::WhatsThis

    111

    The widget should reveal "What's This?" help (QHelpEvent).

    QEvent::WhatsThisClicked

    118

    A link in a widget's "What's This?" help was clicked.

    QEvent::Wheel

    31

    Mouse wheel rolled (QWheelEvent).

    QEvent::WinEventAct

    132

    A Windows-specific activation event has occurred.

    QEvent::WindowActivate

    24

    Window was activated.

    QEvent::WindowBlocked

    103

    The window is blocked by a modal dialog.

    QEvent::WindowDeactivate

    25

    Window was deactivated.

    QEvent::WindowIconChange

    34

    The window's icon has changed.

    QEvent::WindowStateChange

    105

    The window's state (minimized, maximized or full-screen) has changed (QWindowStateChangeEvent).

    QEvent::WindowTitleChange

    33

    The window title has changed.

    QEvent::WindowUnblocked

    104

    The window is unblocked after a modal dialog exited.

    QEvent::WinIdChange

    203

    The window system identifer for this native widget has changed.

    QEvent::ZOrderChange

    126

    The widget's z-order has changed. This event is never sent to top level windows.

    3.QEvetnt使用和捕捉

         QObject的类(和继承类),可以使用QObject::event(), QObject::installEventFilter(),QCoreApplication::sendEvent(), QCoreApplication::postEvent(), 和 QCoreApplication::processEvents()等机制发送事件和和捕捉事件。

         上面2所属事件均可被使用和捕捉。

         提供样例如下:

         头文件:

       

    #ifndef MAINWINDOW_H
    #define MAINWINDOW_H
    
    #include <QMainWindow>
    #include <QEvent>
    
    
    namespace Ui
    {
    class MainWindow;
    }
    
    class MainWindow : public QMainWindow
    {
        Q_OBJECT
    
    public:
        explicit MainWindow(QWidget *parent = 0);
        ~MainWindow();
    
        virtual bool eventFilter(QObject *object, QEvent *event) override;
    
    private:
        Ui::MainWindow *ui;
    };
    
    #endif // MAINWINDOW_H

        源文件:

      

    #include <QDebug>
    
    #include "mainwindow.h"
    #include "ui_mainwindow.h"
    
    
    MainWindow::MainWindow(QWidget *parent) :
        QMainWindow(parent),
        ui(new Ui::MainWindow)
    {
        ui->setupUi(this);
        installEventFilter(this);
    }
    
    MainWindow::~MainWindow()
    {
        delete ui;
    }
    
    bool MainWindow::eventFilter(QObject *object, QEvent *event)
    {
        switch (event->type())
        {
        case QEvent::KeyPress:
            event->ignore();
            return true;
    
        default:
            qDebug() << event->type();
            break;
        }
    
        return QObject::eventFilter(object, event);
    }
    

          可以打印出相关事件。

          发送事件源文件如下:

         

    void MainWindow::on_pushButton_clicked()
    {
        int key = Qt::Key_Delete;
    
         QKeyEvent EventPress(QEvent::KeyPress, key, Qt::NoModifier);
         QApplication::sendEvent(ui->textEdit, &EventPress);   //发送键盘按下事件
    
         QKeyEvent EventRelease(QEvent::KeyRelease, key, Qt::NoModifier);
         QApplication::sendEvent(ui->textEdit, &EventRelease); //发送键盘松开事件
    }

       具体代码见GitHub:

       https://github.com/diziqian/QEvnetTest

    展开全文
  • QEvent: QT事件处理

    2021-08-19 13:44:08
    #include class A:public QObject{ public: //该类的对象用作过滤器对象,使用事件过滤器需继承QObject bool eventFilter(QObject *w, QEvent *e){ if(e->type()==QEvent::MouseButtonPress) { cout<<w->objectName...

    原理

    观察者模式:首先使用S的成员函数installEventFilter函数把G1,G2,G3设置为S的观察者,所有本应传递给S的事件E,则先传递给观察者G1,G2,G3,然后观察者调用其成员函数eventFilter对传递进来的事件进行处理,若eventFilter返回true表示事件处理完毕,返回false则返回给被观察者S进行处理。

    QT信号槽机制 VS 事件

    1. 信号由具体的对象发出,然后会马上交给由connect()函数连接的槽进行处理;
    2. 而对于事件,Qt 使用一个事件队列对所有发出的事件进行维护,当新的事件产生时,会被追加到事件队列的尾部。前一个事件完成后,取出后面的事件进行处理。但是,必要的时候,Qt 的事件也可以不进入事件队列,而是直接处理。

    QT事件总述

    1. Qt 程序在main()函数创建一个QCoreApplication对象,然后调用它的exec()函数开始 Qt 的事件循环

    2. 在执行exec()函数之后,程序将进入事件循环来监听应用程序的事件

    3. 当事件发生时,Qt 将创建一个事件对象
      3.1 Qt 中所有事件类都继承于QEvent。在事件对象创建完毕后,Qt 将这个事件对象传递给QObject的event()函数。event()函数并不直接处理事件,而是按照事件对象的类型分派给特定的事件处理函数(event handler)

    4. 在所有组件的父类QWidget中,定义了很多事件处理的回调函数,如keyPressEvent()、keyReleaseEvent()、mouseDoubleClickEvent()、mouseMoveEvent()、mousePressEvent()、mouseReleaseEvent()等。这些函数都是 protected virtual 的,也就是说,我们可以在子类中重写这些函数。

    事件(event)的accept()、ignore()

    1. 普通pushButton函数响应方式:clicked()信号发射后,onButtonClicked()槽函数接收信号并处理。

    // custombutton.h
    class CustomButton : public QPushButton
    {
        Q_OBJECT
    public:
        CustomButton(QWidget *parent = 0);
    private slot:
        void onButtonClicked();
    };
    
    // custombutton.cpp
    CustomButton::CustomButton(QWidget *parent) :
        QPushButton(parent)
    {
        connect(this, &CustomButton::clicked,
                this, &CustomButton::onButtonClicked);
    }
    
    void CustomButton::onButtonCliecked()
    {
        qDebug() << "You clicked this!";
    }
    
    // main.cpp
    int main(int argc, char *argv[])
    {
        QApplication a(argc, argv);
        CustomButton btn;
        btn.setText("This is a Button!");
        btn.show();
        return a.exec();
    }
    

    2. 若向CustomButton类添加一个事件函数(重写CustomButton中继承自QPushButton的mousePressEvent()函数)

    // custombutton.cpp
    void CustomButton::mousePressEvent(QMouseEvent *event)  //  protected 
    {
        if (event->button() == Qt::LeftButton) {
            qDebug() << "left";
        } else {
            QPushButton::mousePressEvent(event);
        }
    }
    

    =》鼠标按下左键,则只打印出来“left”字符串。该方法把父类的实现mousePressEvent()覆盖掉了(子类事件均继承自父类),clicked()信号永远不会发生,连接到这个信号的槽函数onButtonClicked()不会被执行。
    =》当重写事件回调函数时,时刻注意是否需要通过调用父类的同名函数来确保原有实现仍能进行

    ps: Qt 中的事件都是 protected 的,因此,重写的函数必定存在着其父类中的响应函数

    3. 通过调用父类的同名函数,我们可以把 Qt 的事件传递看成链状:如果子类没有处理这个事件,就会继续向其父类传递。

    • accept():这个类的事件处理函数想要处理这个事件,这个事件就不会被继续传播给其父组件。
    • ignore():这个类的事件处理函数不想要处理这个事件,Qt 会从其父组件中寻找另外的接受者,继续传播。
    • isAccepted():查询这个事件是不是已经被接收。

    4. 事件对象默认是 accept 的,而作为所有组件的父类QWidget的默认实现则是调用ignore()。

    • 因为我们无法确认父类中的这个处理函数有没有额外的操作。如果我们在子类中直接忽略事件,Qt 会去寻找其他的接收者,该子类的父类的操作会被忽略(因为没有调用父类的同名函数),这可能会有潜在的危险。

    =》很少会直接使用accept()和ignore()函数,除closeEvent()中。
    =》如果你自己实现事件处理函数,不调用QWidget的默认实现,你就等于是接受了事件;如果你要忽略事件,只需调用QWidget的默认实现。

    4.1 直接调用accept() \ ignore()风险

    void QWidget::mousePressEvent(QMouseEvent *event)
    {
        event->ignore();
        if ((windowType() == Qt::Popup)) {
            .....
        }
    }
    

    如果子类都没有重写这个函数,Qt 会默认忽略这个事件,继续寻找下一个事件接收者。如果我们在子类的mousePressEvent()函数中直接调用了accept()或者ignore(),而没有调用父类的同名函数,QWidget::mousePressEvent()函数中关于Popup判断的那段代码就不会被执行,因此可能会出现默认其妙的怪异现象。

    4.2 closeEvent()中调用ignore()阻止窗口关闭

    //!!! Qt5
    ...
    textEdit = new QTextEdit(this);
    setCentralWidget(textEdit);
    connect(textEdit, &QTextEdit::textChanged, [=]() {
        this->setWindowModified(true);
    });
    
    setWindowTitle("TextPad [*]");
    ...
    
    void MainWindow::closeEvent(QCloseEvent *event)
    {
        if (isWindowModified()) {
            bool exit = QMessageBox::question(this, tr("Quit"), tr("Are you sure to quit this application?"), 
            QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::Yes;
            if (exit) {
                event->accept();
            } else {
                event->ignore();
            }
        } else {
            event->accept();
        }
    }
    

    a. 调用accept()意味着 Qt 会停止事件的传播,窗口关闭;
    b. 调用ignore()则意味着事件继续传播,即阻止窗口关闭

    5. 事件的传播是在组件层次上面的,而不是依靠类继承机制。

    class CustomButton : public QPushButton
    {
        Q_OBJECT
    public:
        CustomButton(QWidget *parent) : QPushButton(parent)
        {
        }
    protected:
        void mousePressEvent(QMouseEvent *event)
        {
            qDebug() << "CustomButton";
        }
    };
    
    class CustomButtonEx : public CustomButton
    {
        Q_OBJECT
    public:
        CustomButtonEx(QWidget *parent) : CustomButton(parent)
        {
        }
    protected:
        void mousePressEvent(QMouseEvent *event)
        {
            qDebug() << "CustomButtonEx";
        }
    };
    
    class CustomWidget : public QWidget
    {
        Q_OBJECT
    public:
        CustomWidget(QWidget *parent) : QWidget(parent)
        {
        }
    protected:
        void mousePressEvent(QMouseEvent *event)
        {
            qDebug() << "CustomWidget";
        }
    };
    
    class MainWindow : public QMainWindow
    {
        Q_OBJECT
    public:
        MainWindow(QWidget *parent = 0) : QMainWindow(parent)
        {
            CustomWidget *widget = new CustomWidget(this);
            CustomButton *cbex = new CustomButton(widget);
            cbex->setText(tr("CustomButton"));
            CustomButtonEx *cb = new CustomButtonEx(widget);
            cb->setText(tr("CustomButtonEx"));
            QVBoxLayout *widgetLayout = new QVBoxLayout(widget);
            widgetLayout->addWidget(cbex);
            widgetLayout->addWidget(cb);
            this->setCentralWidget(widget);
        }
    protected:
        void mousePressEvent(QMouseEvent *event)
        {
            qDebug() << "MainWindow";
        }
    };
    

    a. CustomButtonEx的mousePressEvent() 默认是accept的,是否调用event->accept()没有区别,运行结果如下:

    CustomButtonEx
    

    b. CustomButtonEx的mousePressEvent() 中增加 event->ignore(),运行结果如下:

    CustomButtonEx
    CustomWidget
    

    =》CustomButtonEx的事件传播给了父组件CustomWidget,而不是它的父类CustomButton

    event(): 事件分发

    事件对象创建完毕后,Qt 将这个事件对象传递给QObject的event()函数
    event()函数并不直接处理事件,而是将这些事件对象按照它们不同的类型,分发给不同的事件处理器(event handler: timerEvent() 、mouseMoveEvent()、…)。

    bool CustomWidget::event(QEvent *e)
    {
        if (e->type() == QEvent::KeyPress) {
            QKeyEvent *keyEvent = static_cast<QKeyEvent *>(e);
            if (keyEvent->key() == Qt::Key_Tab) {
                qDebug() << "You press tab.";
                return true;
            }
        }
        return QWidget::event(e);
    }
    
    1. CustomWidget是一个普通的QWidget子类。我们重写了它的event()函数,这个函数有一个QEvent对象作为参数,也就是需要转发的事件对象
    • 函数返回值是 bool 类型。如果传入的事件已被识别并且处理,则需要返回 true,否则返回 false。如果返回值是 true,并且,该事件对象设置了accept(),那么 Qt 会认为这个事件已经处理完毕,不会再将这个事件发送给其它对象,而是会继续处理事件队列中的下一事件。
    • 注意,在event()函数中,调用事件对象的accept()和ignore()函数是没有作用的,不会影响到事件的传播。
    1. 使用QEvent::type()函数可以检查事件的实际类型,其返回值是QEvent::Type类型的枚举。我们处理过自己感兴趣的事件之后,可以直接返回 true,表示我们已经对此事件进行了处理;对于其它我们不关心的事件,则需要调用父类的event()函数继续转发
    • Qt 也是使用QEvent::type()判断事件类型,然后调用了特定的事件处理器。
    • event()函数中实际是通过事件处理器来响应一个具体的事件。这相当于event()函数将具体事件的处理“委托”给具体的事件处理器。而这些事件处理器是 protected virtual 的,因此,我们重写了某一个事件处理器,即可让 Qt 调用我们自己实现的版本。

    整理自:https://www.devbean.net/2012/09/qt-study-road-2-events-accept-reject/

    EventFilter事件过滤器: 实现步骤

    installEventFilter():filterObj对象安装(或注册)为事件过滤器

    void QObject::installEventFilter (QObject* filterObj);
    

    eventFilter()拦截到的事件处理

    bool QObject::eventFilter(QObject* obj, QEvent* e);
    
    • 过滤器对象的eventFilter()函数接受或拒绝拦截到的事件。
    • 若该函数返回false,则表示事件需要作进一步处理,此时事件会被发送到目标对象本身进行处理(注意:这里并未向父对象进行传递)。
    • 若evetnFilter()返回true,则表示停止处理该事件,此时目标对象和后面安装的事件过滤器就无法获得该事件。
    #include<QMouseEvent>
    class A:public QObject{
    public:  //该类的对象用作过滤器对象,使用事件过滤器需继承QObject
        bool eventFilter(QObject *w, QEvent *e){
            if(e->type()==QEvent::MouseButtonPress)
            {
                cout<<w->objectName().toStdString(); //验证w为事件本应到达的目标对象
                cout<<"=Ak"<<endl;
                return 1;  //返回1表示该事件不再进一步处理
            }
            return 0;
        }
    };  /*返回0表示其余事件交还给目标对象处理,本例应返回0,否则添加了该过滤器的安钮会无法显示。*/
    
    class B:public A{
    public:   //继承自类A
        bool eventFilter(QObject *w, QEvent *e){
            if(e->type()==QEvent::MouseButtonPress){
                cout<<w->objectName().toStdString()<<"=Bk"<<endl;
                return 0;
            }
            return 0;
        }
    };
    class C:public QWidget{
    public:
        void mousePressEvent(QMouseEvent *e){
            cout<<"Ck"<<endl;
        }
    };
    class D:public QPushButton{
    public:
        void mousePressEvent(QMouseEvent *e){
            cout<<"DK"<<endl;
        }
    };
    
    int main(int argc, char *argv[]){
        QApplication a(argc,argv);
        //创建对象,注意:本例父对象应先创建,以避免生命期过早结束
        A ma;
        B mb;
        C mc;
        D *pd=new D;
        D *pd1=new D;
        pd->setText("AAA");
        pd->move(22,22);
        pd1->setText("BBB");
        pd1->move(99,22);
        //设置对象名
        ma.setObjectName("ma");
        mb.setObjectName("mb");
        mc.setObjectName("mc");
        pd->setObjectName("pd");
        pd1->setObjectName("pd1");
        //设置父对象
        pd->setParent(&mb);
        pd1->setParent(&mc);
        mb.setParent(&ma);    //①
        //注册过滤器对象
        pd->installEventFilter(&mb);  //②
        pd1->installEventFilter(&ma); //③
    
        mc.resize(333,222);    mc.show();    a.exec();
        return 0;
    }
    

    removeEventFilter():删除事件过滤器

    QObject::removeEventFilter(QObject *obj)
    

    Example

    ButtonHoverWatcher * watcher = new ButtonHoverWatcher(this);
    ui->pushButton->installEventFilter(watcher);
    
    #include <QObject>
    #include <QPushButton>
    #include <QEvent>
    class ButtonHoverWatcher : public QObject
    {
        Q_OBJECT
    public:
        explicit ButtonHoverWatcher(QObject * parent = Q_NULLPTR);
        virtual bool eventFilter(QObject * watched, QEvent * event) Q_DECL_OVERRIDE;
    };
    
    ButtonHoverWatcher::ButtonHoverWatcher(QObject * parent) :
        QObject(parent)
    {}
    
    bool ButtonHoverWatcher::eventFilter(QObject * watched, QEvent * event)
    {
        QPushButton * button = qobject_cast<QPushButton*>(watched);
        if (!button) {
            return false;
        }
    
        if (event->type() == QEvent::Enter) {
            // The push button is hovered by mouse
            button->setIcon(QIcon(":/images/start_hov.png"));
            return true;
        }
    
        if (event->type() == QEvent::Leave){
            // The push button is not hovered by mouse
            button->setIcon(QIcon(":/images/start.png"));
            return true;
        }
    
        return false;
    }
    

    https://blog.csdn.net/hyongilfmmm/article/details/83015541

    https://stackoverflow.com/questions/40318759/change-qpushbutton-icon-on-hover-and-pressed

    QMouseEvent

    mouseMoveEvent(QMouseEvent *event)

    在MainWindow构造函数中对需要跟踪鼠标位置的组件,及其所属的各级父类和容器setMouseTracking(true),否则只有在按住左键或右键时才会捕捉鼠标位置。

    展开全文
  • Qt-QEvent

    2022-04-21 17:36:16
    按键事件 #include "qeventtest.h" #include <QDebug> #include<QEvent> #include <QKeyEvent>...QEventTest::QEventTest(QWidget* parent) ...bool QEventTest::event(QEvent* ev

    按键事件

    #include "qeventtest.h"
    #include <QDebug>
    #include<QEvent>
    #include <QKeyEvent>
    QEventTest::QEventTest(QWidget* parent)
    	: QWidget(parent)
    {
    	ui.setupUi(this);
    	//this->setMouseTracking(true);
    }
    bool QEventTest::event(QEvent* ev)
    {
    	if (ev->type() == QEvent::KeyPress)
    	{
    		QKeyEvent* ke = static_cast<QKeyEvent*>(ev);
    		if (ke->key() == 'A')
    		{
    			//自动连按事件,不处理
    			if (!ke->isAutoRepeat())
    				qDebug() << "aaaaaaaaaaaaaaaaaaa";
    			return true;
    		}
    	}
    	return QWidget::event(ev);
    }
    void QEventTest::keyPressEvent(QKeyEvent* ev)
    {
    	//自动连按事件,不处理
    	if (ev->isAutoRepeat()) return;
    	if (ev->key() == Qt::Key_F1)
    	{
    		qDebug() << "Key_F1";
    	}
    
    	qDebug() << "keyPressEvent = " << ev->key();
    }
    
    //键盘松开
    void QEventTest::keyReleaseEvent(QKeyEvent* ev)
    {
    	//自动连按事件,不处理
    	if (ev->isAutoRepeat()) return;
    	qDebug() << "keyReleaseEvent = " << ev->key();
    }

    鼠标位置坐标 & 鼠标按键事件

            提示QLabel为XLabel

    .h

    #include <QLabel>
    #include <QDebug>
    #include <QMouseEvent>
    #include<QMenu>
    class XLabel : public QLabel
    {
    	Q_OBJECT
    
    public:
    	QMenu menu;
    	XLabel(QWidget *parent);
    	~XLabel();
    	bool event(QEvent *ev);
    	virtual void enterEvent(QEvent *event)
    	{
    		qDebug() << "enterEvent";
    	}
    	virtual void leaveEvent(QEvent *event)
    	{
    		qDebug() << "leaveEvent";
    	}
    	virtual void mouseDoubleClickEvent(QMouseEvent *event)
    	{
    		qDebug() << "mouseDoubleClickEvent "<<event->pos().x()<<":" << event->pos().y();
    	}
    	virtual void mouseMoveEvent(QMouseEvent *event)
    	{
    		qDebug() << "mouseMoveEvent " << event->pos().x() << ":" << event->pos().y();
    	}
    	virtual void mousePressEvent(QMouseEvent *event)
    	{
    		qDebug() << "mousePressEvent " << event->pos().x() << ":" << event->pos().y();
    	}
    	virtual void mouseReleaseEvent(QMouseEvent *event)
    	{
    		qDebug() << "mouseReleaseEvent " << event->pos().x() << ":" << event->pos().y();
    	}
    
    };
    

    .cpp

    #include "xlabel.h"
    #include <QEvent>
    #include<QMouseEvent>
    #include <QDebug>
    XLabel::XLabel(QWidget *parent)
    	: QLabel(parent)
    {
    	this->setMouseTracking(true);
    	menu.addAction(QStringLiteral("菜单1"));
    	menu.addAction(QStringLiteral("菜单2"));
    	menu.addAction(QStringLiteral("菜单3"));
    }
    
    XLabel::~XLabel()
    {
    }
    bool XLabel::event(QEvent *ev)
    {
    	if (ev->type() == QEvent::MouseButtonPress)
    	{
    		QMouseEvent *me = static_cast<QMouseEvent*> (ev);
    		相对坐标
    		qDebug() << "LocalPos " << me->x() << ":" << me->y();
    		//程序坐标
    		qDebug() << "windowPos " << me->windowPos().x() << ":" << me->windowPos().y();
    		//屏幕坐标
    		qDebug() << "screenPos " << me->screenPos().x() << ":" << me->screenPos().y();
    
    		//本地坐标转全局(屏幕坐标)
    		QPoint gpos = mapToGlobal(me->pos());
    		qDebug() << "mapToGlobal " << gpos.x() << ":" << gpos.y();
    
    		//获取鼠标的屏幕坐标
    		qDebug() << "QCursor " << QCursor::pos().x() <<":"  << QCursor::pos().y();
    
    		//鼠标按键事件
    		if (me->buttons() & Qt::LeftButton)
    		{
    			qDebug() << "LeftButton";
    			setCursor(Qt::ArrowCursor);
    		}
    		if (me->buttons() & Qt::RightButton)
    		{
    			qDebug() << "RightButton";
    			//右键菜单
    			menu.exec(gpos);
    
    		}
    		if (me->buttons() & Qt::MidButton)
    		{
    			qDebug() << "MidButton";
    		}
    
    		//左右键同时按下
    		if ( (me->buttons() & Qt::LeftButton) && (me->buttons() & Qt::RightButton) )
    		{
    			qDebug() << "LeftButton&RightButton";
    			//鼠标图标替换 -1 -1 热点中间
    			QPixmap pix("cursor.png");
    			QCursor cur = QCursor(pix, -1, -1);
    			setCursor(cur);
    		}
    	}
    	return QWidget::event(ev);
    }

    窗体大小重载事件

    .h

    #include <QtWidgets/QWidget>
    #include "ui_TestQResizeEvent.h"
    
    class TestQResizeEvent : public QWidget
    {
    	Q_OBJECT
    
    public:
    	TestQResizeEvent(QWidget *parent = Q_NULLPTR);
    	bool event(QEvent *e);
    	void resizeEvent(QResizeEvent *ev) 
    	{
    		ui.label->resize(width(), height() - ui.label->y());
    	}
    private:
    	Ui::TestQResizeEventClass ui;
    };
    

    .cpp

    #include "TestQResizeEvent.h"
    #include <QResizeEvent>
    #include <QDebug>
    TestQResizeEvent::TestQResizeEvent(QWidget *parent)
    	: QWidget(parent)
    {
    	ui.setupUi(this);
    }
    bool TestQResizeEvent::event(QEvent *e)
    {
    	if (e->type() == QEvent::Resize)
    	{
    		QResizeEvent *re = static_cast<QResizeEvent *>(e);
    		qDebug() << "Resize old" << re->oldSize().width() << ":" << re->oldSize().height()
    			<< " new size" << re->size().width() << ":" << re->size().height();
    	}
    	return QWidget::event(e);
    }

    展开全文
  • Qt之QEvent(所有事件的翻译)

    千次阅读 2019-10-18 20:16:47
    Qt之QEvent(所有事件的翻译) QEvent 类是所有事件类的基类,事件对象包含事件参数。 Qt 的主事件循环(QCoreApplication::exec())从事件队列中获取本地窗口系统事件,将它们转化为 QEvents,然后将转换后的事件...
  • QEvent 类是所有事件类的基类,事件对象包含事件参数。 Qt 的主事件循环(QCoreApplication::exec())从事件队列中获取本地窗口系统事件,将它们转化为 QEvents,然后将转换后的事件发送给 QObjects。 一般来说,...
  • Qevent

    千次阅读 2016-08-09 17:41:55
    为了进行转发,必定需要有一系列的类型判断,这就可以调用QEvent的type()函数,其返回值是QEvent::Type类型的枚举。我们处理过自己需要的事件后,可以直接return回去,对于其他我们不关心的事件,需要调用父类的...
  • 重写QApplication类,从notify函数中截获指定消息完成业务逻辑,demo中展示了键盘输入在没有输入焦点的时候输出到指定地方,有输入焦点则不做处理
  • Qt 之 QEvent

    万次阅读 2016-10-21 18:32:34
    QEvent类是所有事件类的基类,事件对象包含事件参数。 Qt的主事件循环(QCoreApplication::exec())从事件队列中获取本地窗口系统事件,将它们转化为QEvents,然后将转换后的事件发送给QObjects。 一般来说,事件...
  • 【QT】 自定义事件QEvent 继承QEvent // 实现在myevent.h中 #include <QEvent> class MyEvent: public QEvent { public: MyEvent(int value1, double value2) : QEvent(Type(eventType)), _value1(value1), ...
  • QT QEvent事件

    2020-09-10 19:08:40
    一、QEvent机制 1、main函数开启事件循环后QCoreApplication::exec(),会从事件队列中截取本机的窗口系统事件,并将其转化为QEvents,然后再分发给OBjects 执行过程-》QApplIction::notify-》QMainWindow::event-...
  • Qt5的事件类QEvent

    2020-09-02 16:47:20
    QEvent类 继承关系: Qt5.QEvent.QTimerEvent 定时器事件 QMouseEvent 鼠标事件 QWheelEvent 滑动鼠标滑轮事件 QTabletEvent QKeyEvent 键盘事件 QFocusEvent 焦点事件 QPaintEvent 绘画事件 QMoveEvent ...
  • 如何使用自定义的QEvent事件 自定义事件对于特定的操作是很有用的 MyQEvent.h #ifndef MYQEVENT_H #define MYQEVENT_H #include <QEvent> class MyQEvent : public QEvent { public: MyQEvent(); MyQEvent...
  • QEvent 初学

    2019-05-09 17:48:32
    QEvent 学习一个概念大致 步骤应该是: 1.从这个概念是什么 2.然后指着一个东西问 这东西是 这个概念吗? 为什么是为什么不是? 3.然后拿着东西去用 用的 步骤 或者顺序 用的时候注意的坑 4.然后不断地去深入...
  • QT QEvent 事件调用的来龙去脉

    千次阅读 2020-09-03 14:03:40
    :sendSpontaneousEvent(QObject *receiver, QEvent *event) bool QCoreApplication::notifyInternal(QObject *receiver, QEvent *event) bool QApplication::notify(QObject *receiver, QEvent *e) bool ...
  • QEvent的accept()和ignore()一般不会用到,因为不如直接调用QWidget类的事件处理函数直接,而且作用是一样的,见下面的例子。 推荐直接调用QWidget的事件处理函数。而不是调用accept()和ignore()。 只有一...
  • QT中的事件 QEvent

    2021-04-23 23:05:04
    QT中所有的事件都继承自QEvent,每个 widget 都有一个总的事件处理函数,通过覆写这个基类中虚函数来处理某个事件消息: bool QWidget::event(QEvent *event); { if( event->type() == QEvent::MouseButtonPress ) {...
  • Qt之自定义QEvent

    千次阅读 2019-01-24 08:59:49
    1、要创建自定义类型的事件,首先需要定义一个类似于QEvent::KeyPress、QEvent::KeyRelease事件类型,并且该事件类型的值必须大于QEvent::User。然后再子类化QEvent,在子类中实现相关的函数。最后再调用...
  • QEvent::ChildAdded 需求 在QWebEngineView加载网页后,模拟一个点击,直接创建一个QMouseEvent,通过QApplication::SendEvent或者QApplication::PostEvent发给QWebEngineView, 发现QWebEngineView中没有执行...
  • setAttribute(Qt::WA_Hover, true);
  • Qt事件类 QEvent

    千次阅读 2017-03-22 11:48:46
    QEvent是Qt中所有事件的基类,事件对象包含了该次事件所携带的相关参数。
  • QT4中 QEvent::RequestSoftwarelnputPanel和QEvent::CloseSoftwareInputPanel无法捕捉的破解方法。 ...
  • QEvent> #include <QMouseEvent> #include <QKeyEvent> 使用示例: QKeyEvent *keyEvent = static_cast<QKeyEvent *>(event); QMouseEvent *mouseEvent = static_cast<QMouseEvent *>...
  • EC中的QEvent

    2020-12-16 11:13:39
    当EC检测到一个需要host注意的事件时,EC会将EC的状态寄存器的SCI_EVT置位,EC会通过引脚ECSCI向host发送一个SCI(System Control Interface)中断,其实就是通过一个脉冲来实现。此时EC等待host的一个查询命令QR_EC...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 9,301
精华内容 3,720
关键字:

qevent