Qt5 与 Qt4 的点点差别------事件

Qt5相对于Qt4 增长对事件accept()和ignore()函数。web

Qt 中有不少种事件:鼠标事件、键盘事件、大小改变的事件、位置移动的事件等等。对于事件的处理,咱们Qt 中使用相对应的机制。
event()函数
1. event()函数是一个 protected 的函数,这意味着咱们要想重写event(),必须继承一个已有的类。
2. 各个组件对事件处理是并发修改,仍是挨个修改呢?并发

bool Test::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);
}

 

eventFilter()函数
app

virtual bool QObject::eventFilter ( QObject * watched, QEvent * event );
bool Test::eventFilter(QObject *object, QEvent *event)
{
    if (object == target && event->type() == QEvent::KeyPress) {
        QKeyEvent *keyEvent = static_cast<QKeyEvent *>(event);
        if (keyEvent->key() == Qt::Key_Tab) {
            qDebug() << "You press tab.";
            return true;
        } else {
            return false;
        }
    }
    return false;
}

总结Qt 的事件处理
1.  重写paintEvent()、mousePressEvent()等事件处理函数。这是最普通、最简单的形式,同时功能也最简单。
2. 重写event()函数。event()函数是全部对象的事件入口,QObject和QWidget中的实现,默认是把事件传递给特定的事件处理函数。
3. 在特定对象上面安装事件过滤器。该过滤器仅过滤该对象接收到的事件。
4. 在QCoreApplication::instance()上面安装事件过滤器。该过滤器将过滤全部对象的全部事件,所以和notify()函数同样强大,可是它更灵活,由于能够安装多个过滤器。全局的事件过滤器能够看到 disabled 组件上面发出的鼠标事件。全局过滤器有一个问题:只能用在主线程。(受线程影响)
5. 重写QCoreApplication::notify()函数。这是最强大的,和全局事件过滤器同样提供彻底控制,而且不受线程的限制。可是全局范围内只能有一个被使用(由于QCoreApplication是单例的)。函数

 

class Label : public QWidget
{
public:
    Label()
    {
        installEventFilter(this);
    }
    bool eventFilter(QObject *watched, QEvent *event)
    {
        if (watched == this) {
            if (event->type() == QEvent::MouseButtonPress) {
                qDebug() << "eventFilter";
            }
        }
        return false;
    }
protected:
    void mousePressEvent(QMouseEvent *)
    {
        qDebug() << "mousePressEvent";
    }
    bool event(QEvent *e)
    {
        if (e->type() == QEvent::MouseButtonPress) {
            qDebug() << "event";
        }
        return QWidget::event(e);
    }
};
class EventFilter : public QObject
{
public:
    EventFilter(QObject *watched, QObject *parent = 0) :
        QObject(parent),
        m_watched(watched)
    {
    }
    bool eventFilter(QObject *watched, QEvent *event)
    {
        if (watched == m_watched) {
            if (event->type() == QEvent::MouseButtonPress) {
                qDebug() << "QApplication::eventFilter";
            }
        }
        return false;
    }
private:
    QObject *m_watched;
};
int main(int argc, char *argv[])
{
    QApplication app(argc, argv);
    Label label;
    app.installEventFilter(new EventFilter(&label, &label));
    label.show();
    return app.exec();
}

输出结果是:post

QApplication::eventFilter 
eventFilter 
event 
mousePressEvent

所以能够知道,全局事件过滤器被第一个调用,以后是该对象上面的事件过滤器,其次是event()函数,最后是特定的事件处理函数。this

 

registerEventType()函数   ------- 用于自定义事件的注册spa

static int QEvent::registerEventType ( int hint = -1 );

发送方式:.net

static bool QCoreApplication::sendEvent(QObject *receiver,QEvent *event);

例子:线程

QMouseEvent event(QEvent::MouseButtonPress, pos, 0, 0, 0);
QApplication::sendEvent(mainWindow, &event); 
static void QCoreApplication::postEvent(QObject *receiver,QEvent *event);

注意:在事件被发送的时候,event对象并不会被销毁。一般咱们会在栈上建立event对象code

 

参考资料:

http://www.devbean.net/2012/10/qt-study-road-2-event-summary/

相关文章
相关标签/搜索