Qt的事件循环(QEventLoop)到底是什么?

📅 2026/7/8 9:15:35
Qt的事件循环(QEventLoop)到底是什么?
非AI生成觉得有用就请您帮忙点赞转发收藏吧您的鼓励是我创作的动力多谢看官。目录前言细说事件循环事件分类事件循环的作用事件循环的启动方式事件循环和信号槽的关系事件循环和定时器的关系总结参考链接前言在Qt中事件循环Event Loop是一个关键的组成部分它负责管理应用程序的事件处理。在Qt框架中事件循环通常由QCoreApplication、QApplication或QGuiApplication类管理。这些类提供了事件循环的实现允许应用程序接收和响应各种事件如用户输入、窗口系统事件、定时器事件等。事件循环是 Qt 对象之间“事件型交互”的中枢调度器没有事件循环所有依赖事件派发的机制都将失效。几乎可以说Qt框架 对象树 事件循环 信号槽细说事件循环事件分类用户输入事件Input Events由用户硬件输入触发是 GUI 交互的核心统一继承自 QInputEvent。鼠标事件QMouseEvent按下、释放、移动、双击、QWheelEvent滚轮键盘事件QKeyEvent按键按下、释放、文本输入触摸事件QTouchEvent多点触控 Begin/Update/End平板事件QTabletEvent绘图板笔触移动、压力原生手势QNativeGestureEvent缩放、旋转、智能捏合悬停事件QHoverEvent鼠标悬停进入/移动/离开输入法事件QInputMethodEvent中文、日文等输入法组合框窗口与控件生命周期事件Window / Widget Events与窗口系统、控件显示状态相关由系统或 show()/ hide()等调用触发。显示与隐藏QShowEventShow、QHideEventHide几何变化QResizeEventResize、QMoveEventMove关闭事件QCloseEventClose可拦截阻止窗口关闭激活与状态WindowActivate/ WindowDeactivate、WindowStateChange曝光事件QExposeEvent窗口从遮挡中露出需重绘内容进入/离开QEnterEvent鼠标进入部件、Leave绘制与刷新事件Paint Events绘制事件QPaintEventPaint当控件需要重绘首次显示、被遮挡后恢复、手动 update()时由事件循环派发是自定义绘图 paintEvent()的源头。定时器事件Timer Events定时器事件QTimerEventTimer由 QTimer或 startTimer()触发事件循环在指定间隔后将其放入队列携带 timerId()区分多个定时器。焦点与键盘导航事件Focus / Shortcut Events焦点事件QFocusEventFocusIn/ FocusOut/ FocusAboutToChange控件获焦或失焦快捷键事件QShortcutEventShortcut/ ShortcutOverride按键组合匹配拖放与上下文菜单事件Drag Drop / Context Events拖放系列QDragEnterEvent、QDragMoveEvent、QDragLeaveEvent、QDropEvent上下文菜单QContextMenuEventContextMenu右键菜单提示事件QHelpEventToolTip / WhatsThis 请求对象系统与应用级事件Object / Application Events不直接与界面绘制相关而是 Qt 对象模型和应用程序状态的底层事件。子对象变化QChildEventChildAdded/ Removed/ Polished属性变化QDynamicPropertyChangeEvent延迟删除DeferredDelete由 deleteLater()投递下一轮事件循环处理应用状态ApplicationStateChange、ActivationChange、PaletteChange等元调用事件MetaCall跨线程信号槽的 QueuedConnection本质就是封装成此事件投递到目标线程事件循环平台/原生事件QPlatformSurfaceEvent、Expose、FileOpen等自定义事件Custom Events开发者通过继承 QEvent并使用 QEvent::User1000到 QEvent::MaxUser65535​ 之间的类型值或通过 QCoreApplication::registerEventType()注册来创建业务事件通过 postEvent()/ sendEvent()投递。此外还有 Graphics Scene 专用事件如 QGraphicsSceneMouseEvent、QGraphicsSceneDragDropEvent等以及 手势事件QGestureEvent它们大多可归入上述输入或交互大类中。事件循环的作用事件循环的主要作用负责从从系统 / 内部获取事件将事件派发到QObject执行回调event / slot / timer / paint事件循环的启动方式1. QApplication::exec()最常用#include mainwindow.h #include QApplication int main(int argc, char *argv[]) { QApplication a(argc, argv); MainWindow w; w.show(); return a.exec();//启动主事件循环没有这行代码程序就无法正常运行 }2. QEventLoop::exec()局部事件循环void MainWindow::startSyncRequest(QString reqUrl,ReplyCallback callback) { // 创建事件循环用于阻塞等待 QEventLoop loop; QUrl url(reqUrl); QNetworkRequest request(url); //QNetworkReply是在你调用QNetworkAccessManager::get()/post()等请求函数的那一瞬间、在调用该函数的线程中同步创建的 QNetworkReply* reply m_network_mngr-get(request); // 设置超时定时器 QTimer timer; timer.setSingleShot(true); QObject::connect(timer, QTimer::timeout, []() { reply-abort(); // 超时中止请求 loop.quit(); // 退出事件循环 }); timer.setTimerType(Qt::PreciseTimer); //保持毫秒级精度 timer.start(5000);//设置5秒超时 // 连接请求完成信号 QObject::connect(reply, QNetworkReply::finished, []() { timer.stop(); // 停止定时器 loop.quit(); // 退出事件循环 }); // 阻塞等待请求完成 loop.exec();//阻塞了当前的代码执行流,但它并没有阻塞Qt的事件分发;所以网络传输照常进行,只是代码停在了loop.exec()这一行 callback(reply); reply-deleteLater(); // 务必清理QNetworkReply对象否则会出现内存泄漏 }事件循环和信号槽的关系QueuedConnection 是“事件循环驱动的函数调用远程过程调用RPC”​信号是接口事件是载体事件循环是调度中心slot 是最终执行体。事件循环和定时器的关系QTimer *timer new QTimer; QThread *thread new QThread; timer-moveToThread(thread); thread-start(); QObject::connect(timer, QTimer::timeout, [](){ qDebug() timeout; }); QObject::connect(thread, QThread::started, []() { timer-start(1000); });总结Qt程序中几乎感觉不到事件循环的存在但事件循环这个“大管家”一直在默默为Qt程序的运行而服务。深刻理解事件循环有助于编写更加健壮的Qt程序。参考链接1.Qt事件循环