QT5 C++项目中实现倒计时自动关闭QMessageBox
- 在Windows下的QT5 C++ qmake项目中,希望实现倒计时自动关闭QMessageBox。
- 以下是基于 Qt5 C++ qmake 项目的完整实现,通过自定义
CountdownMessageBox类(继承自QMessageBox),实现“倒计时显示+自动关闭”功能,包含.h头文件和.cpp源文件,支持自定义倒计时时长、提示文本和按钮类型。效果见下面图片。
1. 头文件:CountdownMessageBox.h
定义自定义对话框类,核心逻辑包括:倒计时定时器、动态更新按钮文本(显示剩余时间)、自动关闭触发。
#ifndef COUNTDOWNMESSAGEBOX_H
#define COUNTDOWNMESSAGEBOX_H
#include <QMessageBox>
#include <QTimer>
#include <QString>
// 继承 QMessageBox,实现倒计时自动关闭
class CountdownMessageBox : public QMessageBox
{
Q_OBJECT
public:
// 构造函数:支持自定义标题、内容、倒计时秒数、按钮类型
// 参数说明:
// - title: 对话框标题
// - text: 对话框内容(会自动追加倒计时提示)
// - countdownSec: 倒计时秒数(默认3秒)
// - buttons: 对话框按钮(默认只有“确定”按钮)
explicit CountdownMessageBox(const QString& title,
const QString& text,
int countdownSec = 3,
StandardButtons buttons = Ok,
QWidget *parent = nullptr);
// 显示对话框(重写 show(),确保倒计时启动时机正确)
void show() override;
private slots:
// 倒计时定时器触发的槽函数:更新剩余时间,到0时关闭对话框
void onCountdownTimeout();
private:
QTimer* m_countdownTimer; // 倒计时定时器
int m_remainingSec; // 剩余倒计时秒数
QString m_originalText; // 原始对话框内容(用于拼接倒计时文本)
StandardButton m_defaultBtn;// 默认按钮(倒计时结束后自动触发该按钮的点击事件)
};
#endif // COUNTDOWNMESSAGEBOX_H
2. 源文件:CountdownMessageBox.cpp
实现定时器初始化、倒计时更新、自动关闭逻辑,兼容 Windows 平台的对话框行为。
#include "CountdownMessageBox.h"
CountdownMessageBox::CountdownMessageBox(const QString& title,
const QString& text,
int countdownSec,
StandardButtons buttons,
QWidget *parent)
: QMessageBox(parent)
, m_remainingSec(countdownSec) // 初始化倒计时秒数
, m_originalText(text) // 保存原始内容(避免重复拼接)
, m_defaultBtn(standardButton(buttons)) // 获取默认按钮(如 Ok)
{
// 1. 初始化对话框基础属性(标题、按钮、图标等)
setWindowTitle(title);
setStandardButtons(buttons);
setDefaultButton(m_defaultBtn); // 设置默认按钮(按 Enter 可触发)
// 2. 初始化倒计时定时器
m_countdownTimer = new QTimer(this);
m_countdownTimer->setInterval(1000); // 定时器间隔:1秒(1000毫秒)
m_countdownTimer->setSingleShot(false); // 非单次触发(循环计时)
// 3. 连接定时器信号与槽函数(每秒触发一次倒计时更新)
connect(m_countdownTimer, &QTimer::timeout,
this, &CountdownMessageBox::onCountdownTimeout);
// 4. 初始显示:拼接原始文本和倒计时提示(如“操作成功,3秒后自动关闭...”)
updateText();
}
// 重写 show() 函数:显示对话框时启动倒计时
void CountdownMessageBox::show()
{
m_countdownTimer->start(); // 启动定时器
QMessageBox::show(); // 调用父类 show(),显示对话框
}
// 倒计时定时器槽函数:更新剩余时间,到0时关闭对话框
void CountdownMessageBox::onCountdownTimeout()
{
// 1. 减少剩余秒数
m_remainingSec--;
// 2. 更新对话框文本(显示最新剩余时间)
updateText();
// 3. 倒计时结束:停止定时器 + 触发默认按钮点击 + 关闭对话框
if (m_remainingSec <= 0)
{
m_countdownTimer->stop(); // 停止定时器
// 模拟点击默认按钮(触发对话框的 accept/reject 逻辑,确保信号正常发射)
clickButton(m_defaultBtn);
// 关闭对话框(若 clickButton 未触发关闭,手动关闭)
close();
}
}
// 辅助函数:更新对话框文本(拼接原始内容和剩余时间)
void CountdownMessageBox::updateText()
{
// 格式:原始文本 + “(X秒后自动关闭)”
QString newText = QString("%1(%2秒后自动关闭)")
.arg(m_originalText)
.arg(m_remainingSec);
setText(newText);
}
3. 使用示例(main.cpp)
在项目中调用自定义的 CountdownMessageBox,支持不同场景(如成功提示、警告提示)。
#include <QApplication>
#include "CountdownMessageBox.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
// 示例1:基础用法(3秒自动关闭,默认“确定”按钮)
CountdownMessageBox msg1(
"操作成功", // 标题
"文件已成功保存到 D:\\Temp\\", // 内容
3, // 倒计时3秒
QMessageBox::Ok // 按钮类型
);
msg1.setIcon(QMessageBox::Information); // 设置图标(信息图标)
msg1.exec(); // 模态显示(也可使用 show() 非模态,根据需求选择)
// 示例2:自定义倒计时+多按钮(5秒自动关闭,“确定”+“取消”按钮)
CountdownMessageBox msg2(
"警告", // 标题
"检测到未保存的修改,是否放弃?", // 内容
5, // 倒计时5秒
QMessageBox::Ok | QMessageBox::Cancel // 多按钮
);
msg2.setIcon(QMessageBox::Warning); // 设置图标(警告图标)
// 监听按钮点击结果(即使自动关闭,也能获取默认按钮的结果)
int result = msg2.exec();
if (result == QMessageBox::Ok)
{
qDebug() << "用户选择:放弃修改(或倒计时自动触发)";
}
else if (result == QMessageBox::Cancel)
{
qDebug() << "用户选择:取消操作";
}
return a.exec();
}
4. 项目配置(.pro 文件)
确保 qmake 项目配置正确,仅需依赖 Qt 核心模块(无需额外第三方库)。
QT += core gui widgets # 依赖 widgets 模块(QMessageBox 属于 widgets)
TARGET = CountdownMsgDemo # 项目名称
TEMPLATE = app # 应用程序模板
SOURCES += main.cpp # 源文件
CountdownMessageBox.cpp
HEADERS += CountdownMessageBox.h # 头文件
5. 关键特性说明(Windows 平台适配)
- 定时器稳定性:使用
QTimer而非sleep,避免阻塞 UI 线程,确保对话框可正常交互(用户可手动点击按钮提前关闭)。 - 按钮事件兼容:倒计时结束时通过
clickButton(m_defaultBtn)模拟按钮点击,而非直接close(),确保exec()的返回值(如QMessageBox::Ok)正常,与原生QMessageBox行为一致。 - 文本动态更新:通过
updateText()函数实时刷新倒计时文本,用户可清晰看到剩余时间。 - 模态/非模态支持:支持
exec()(模态,阻塞后续代码)和show()(非模态,不阻塞),根据业务场景选择(如后台操作提示用非模态,关键确认用模态)。
浙公网安备 33010602011771号