qt作业day5
1:是进度条通过线程自己动起来
头文件 (mythread.h
)
#ifndef MYTHREAD_H
#define MYTHREAD_H#include <QThread>
#include <QSlider>class mythread : public QThread {Q_OBJECTpublic:explicit mythread(QSlider* slider, QObject* parent = nullptr);void stop(); // 停止线程protected:void run() override;private:QSlider* slider; // 需要控制的滑块bool stopped; // 线程停止标志
};#endif // MYTHREAD_H
2. 实现文件 (mythread.cpp
)
#include "mythread.h"
#include <QThread>mythread::mythread(QSlider* slider, QObject* parent): QThread(parent), slider(slider), stopped(false) {// 初始化
}void mythread::stop() {stopped = true; // 设置停止标志
}void mythread::run() {while (!stopped) {int value = slider->value();int maximum = slider->maximum();if (value < maximum) {slider->setValue(value + 1); // 增加滑块的值} else {break; // 如果滑块达到最大值,退出循环}QThread::msleep(100); // 休眠 100 毫秒}
}
头文件 (widget.h
)
#ifndef WIDGET_H
#define WIDGET_H#include <QWidget>
#include <QSlider>
#include <QPushButton>
#include "mythread.h"QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACEclass Widget : public QWidget {Q_OBJECTpublic:Widget(QWidget* parent = nullptr);~Widget();private slots:void on_ok_button_clicked();void onSliderReleased();private:Ui::Widget* ui;mythread* sliderThread; // 滑块自动滑动线程
};#endif // WIDGET_H
实现文件 (widget.cpp
)
#include "widget.h"
#include "ui_widget.h"
#include <QInputDialog>Widget::Widget(QWidget* parent): QWidget(parent), ui(new Ui::Widget) {ui->setupUi(this);// 设置滑块的样式ui->horizontalSlider->setStyleSheet(R"(QSlider::groove:horizontal {background: #CCCCCC; /* 没有滑过的部分(右侧)为灰色 */height: 10px;border-radius: 5px;}QSlider::sub-page:horizontal {background: #0078D7; /* 滑过的部分(左侧)为蓝色 */height: 10px;border-radius: 5px;}QSlider::handle:horizontal {background: #FFFFFF; /* 滑块的背景颜色 */width: 20px;height: 20px;margin: -5px 0; /* 调整滑块的位置 */border-radius: 10px;border: 2px solid #000000; /* 滑块的边框 */})");// 创建滑块自动滑动线程sliderThread = new mythread(ui->horizontalSlider, this);// 连接滑块的释放信号到槽函数connect(ui->horizontalSlider, &QSlider::sliderReleased, this, &Widget::onSliderReleased);// 启动线程sliderThread->start();
}Widget::~Widget() {delete ui;
}void Widget::on_ok_button_clicked() {// 示例:打开输入对话框QInputDialog::getText(this, "请输入", "请输入");
}void Widget::onSliderReleased() {// 停止线程sliderThread->stop();sliderThread->quit();sliderThread->wait();
}
2:使用QFileDialog 或者 拖放事件 + QT文件IO + QT线程
实现一个文件复制功能,要求能够复制大小超过800mb的文件
额外要求:可以在文件拷贝的时候,追加一个进度条显示拷贝了多少文件内容
1. 头文件 (filecopier.h
)
#ifndef FILECOPIER_H
#define FILECOPIER_H#include <QThread>
#include <QFile>class FileCopier : public QThread {Q_OBJECTpublic:FileCopier(const QString& sourcePath, const QString& destinationPath, QObject* parent = nullptr);protected:void run() override;private:QString sourcePath; // 源文件路径QString destinationPath; // 目标文件路径
signals:void error();void progressChanged();void finished();
};#endif // FILECOPIER_H
2. 实现文件 (filecopier.cpp
)
#include "filecopier.h"
#include <QFile>
#include <QDataStream>FileCopier::FileCopier(const QString& sourcePath, const QString& destinationPath, QObject* parent): QThread(parent), sourcePath(sourcePath), destinationPath(destinationPath) {// 初始化
}void FileCopier::run() {QFile sourceFile(sourcePath);QFile destinationFile(destinationPath);if (!sourceFile.open(QIODevice::ReadOnly)) {emit error("无法打开源文件");return;}if (!destinationFile.open(QIODevice::WriteOnly)) {emit error("无法创建目标文件");sourceFile.close();return;}qint64 fileSize = sourceFile.size();qint64 bytesCopied = 0;const qint64 bufferSize = 1024 * 1024; // 每次复制 1MBQDataStream in(&sourceFile);QDataStream out(&destinationFile);while (bytesCopied < fileSize) {QByteArray buffer = sourceFile.read(bufferSize);if (buffer.isEmpty()) {break;}out.writeRawData(buffer.constData(), buffer.size());bytesCopied += buffer.size();}sourceFile.close();destinationFile.close();emit finished();
}
3. 主窗口类 (widget.h
)
#ifndef WIDGET_H
#define WIDGET_H#include <QWidget>
#include "filecopier.h"QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACEclass Widget : public QWidget {Q_OBJECTpublic:Widget(QWidget* parent = nullptr);~Widget();private slots:void onCopyClicked();private:Ui::Widget* ui;FileCopier* fileCopier; // 文件复制线程
};#endif // WIDGET_H
4. 实现文件 (widget.cpp
)
#include "widget.h"
#include "ui_widget.h"
#include <QFileDialog>
#include <QMessageBox>Widget::Widget(QWidget* parent): QWidget(parent), ui(new Ui::Widget), fileCopier(nullptr) {ui->setupUi(this);// 连接按钮点击事件connect(ui->copyButton, &QPushButton::clicked, this, &Widget::onCopyClicked);
}Widget::~Widget() {delete ui;
}void Widget::onCopyClicked() {QString sourceFilePath = QFileDialog::getOpenFileName(this, "选择源文件", "", "所有文件 (*.*)");if (sourceFilePath.isEmpty()) {return;}QString destinationFilePath = QFileDialog::getSaveFileName(this, "选择目标文件", "", "所有文件 (*.*)");if (destinationFilePath.isEmpty()) {return;}// 创建文件复制线程fileCopier = new FileCopier(sourceFilePath, destinationFilePath, this);// 连接信号和槽connect(fileCopier, &FileCopier::finished, this, [this]() {QMessageBox::information(this, "完成", "文件复制完成");fileCopier->deleteLater();fileCopier = nullptr;});connect(fileCopier, &FileCopier::error, this, [this](const QString& message) {QMessageBox::critical(this, "错误", message);fileCopier->deleteLater();fileCopier = nullptr;});// 启动线程fileCopier->start();
}