Qt 进度条与多线程应用、基于 Qt 的文件复制工具开发

练习1:Qt 进度条与多线程应用

题目描述

开发一个基于 Qt 的应用程序,该应用程序包含一个水平进度条(QSlider),并且需要通过多线程来更新进度条的值。请根据以下要求完成代码:

  1. 界面设计

    • 使用 QSlider 控件作为进度条。

    • 设置 QSlider 的样式

  2. 多线程更新

    • 创建一个自定义线程类 mythread,该线程类继承自 QThread

    • 使主线程接收到信号后,更新 QSlider 的值。

  3. 信号与槽

    • 使用信号与槽机制实现线程与主线程之间的通信。

    • 当线程中的值发生变化时,通过信号通知主线程更新进度条。

1.mythread.h 

#ifndef MYTHREAD_H
#define MYTHREAD_H
#include<QThread>

class mythread : public QThread
{
    Q_OBJECT
public:

    explicit mythread(QObject *parent = nullptr);
    void run() override; // 线程的执行函数

signals:
    void updateValue(int value); // 发送信号更新进度条
};


#endif // MYTHREAD_H

2.mythread.cpp 

#include "mythread.h"
#include<QThread>

mythread::mythread(QObject *parent){}
void mythread::run()
{
    int value = 0;
    while (true) {
        emit updateValue(value);
        value = (value + 1) % 101;  // 0 ~ 100 循环
        QThread::msleep(100);  // 休眠 100ms
    }
}

3.widget.h 

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include <QWidget>
#include <QMovie>
#include <QThread>
#include <QTextEdit>
#include <QWidget>
#include <QThread>
#include<QScreen>
#include<QLabel>
#include<QDebug>
#include<QPixmap>
#include<QApplication>
#include<QPushButton>
#include "mythread.h"

QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE

class Widget : public QWidget
{
    Q_OBJECT
public slots:
    void setSliderValue(int value); // 更新进度条

public:
    Widget(QWidget *parent = nullptr);
    ~Widget();

private:
    Ui::Widget *ui;
    mythread *thread;
};
#endif // WIDGET_H

4.widget.cpp 

#include "widget.h"
#include "ui_widget.h"


Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);

    QString qss = "QSlider { background: transparent; }"//设置 QSlider 的背景为透明
                  "QSlider::groove:horizontal { border: 1px solid gray; background: lightgray; height: 15px; border-radius: 5px; }"
                  "QSlider::sub-page:horizontal { background: #B5E61D; border-radius: 5px; }"
                  "QSlider::handle:horizontal { background:#5A730E; width: 10px;border-radius: 5px }";


    ui->horizontalSlider->setStyleSheet(qss);

    // 创建并启动线程
        thread = new mythread(this);
        connect(thread, &mythread::updateValue, this, &Widget::setSliderValue);
        thread->start();
    }


Widget::~Widget()
{
    delete ui;
}

// 槽函数:更新进度条
void Widget::setSliderValue(int value)
{
    ui->horizontalSlider->setValue(value);
}

练习2:基于 Qt 的文件复制工具开发

开发一个基于 Qt 的文件复制工具,要求实现以下功能:

  1. 文件选择

    • 使用 QFileDialog 选择源文件和目标文件。

    • 支持选择大文件(超过 800MB)。

  2. 文件复制

    • 使用 Qt 的文件 IO 操作(QFile)实现文件复制功能。

    • 支持分块读取和写入文件,避免一次性加载大文件到内存中。

  3. 多线程处理

    • 使用 QThread 在后台执行文件复制操作,避免阻塞主线程。

    • 通过信号与槽机制,将复制进度实时传递给主线程。

  4. 进度显示

    • 使用自定义的 QSlider 作为进度条,显示文件复制的进度。

    • 自定义 QSlider 的样式,使其外观美观。

  5. 错误处理

    • 如果文件打开失败或复制失败,弹出错误提示框。

    • 如果复制完成,弹出提示框显示“文件复制完成”。

1.mythread.h

#ifndef MYTHREAD_H
#define MYTHREAD_H

#include <QThread>
#include <QString>

class MyThread : public QThread
{
    Q_OBJECT

public:
    explicit MyThread(const QString &source, const QString &destination, QObject *parent = nullptr);

signals:
    void progressUpdated(int value); // 信号:用于更新进度条的值

protected:
    void run() override; // 线程执行函数

private:
    QString sourcePath;  // 源文件路径
    QString destinationPath; // 目标文件路径
};

#endif // MYTHREAD_H

2.mythread.cpp 

#include "mythread.h"
#include <QFile>
#include <QDebug>

MyThread::MyThread(const QString &source, const QString &destination, QObject *parent)
    : QThread(parent), sourcePath(source), destinationPath(destination)
{
}

void MyThread::run()
{
    QFile sourceFile(sourcePath);
    QFile destinationFile(destinationPath);

    // 打开源文件
    if (!sourceFile.open(QIODevice::ReadOnly)) {
        emit progressUpdated(-1); // 发送错误信号
        return;
    }

    // 打开目标文件
    if (!destinationFile.open(QIODevice::WriteOnly)) {
        emit progressUpdated(-1); // 发送错误信号
        return;
    }

    qint64 fileSize = sourceFile.size(); // 获取文件大小
    qint64 bytesCopied = 0; // 已复制的字节数
    char buffer[4096]; // 缓冲区

    // 分块读取和写入文件
    while (!sourceFile.atEnd()) {
        qint64 bytesRead = sourceFile.read(buffer, sizeof(buffer)); // 读取数据
        destinationFile.write(buffer, bytesRead); // 写入数据
        bytesCopied += bytesRead; // 更新已复制的字节数
        int progress = static_cast<int>((bytesCopied * 100) / fileSize); // 计算进度
        emit progressUpdated(progress); // 发送进度信号
    }

    // 关闭文件
    sourceFile.close();
    destinationFile.close();
}

3.widget.h 

#ifndef WIDGET_H
#define WIDGET_H

#include <QWidget>
#include <QSlider>
#include <QFileDialog>
#include <QMessageBox>
#include "mythread.h"

QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE

class Widget : public QWidget
{
    Q_OBJECT

public:
    Widget(QWidget *parent = nullptr);
    ~Widget();

private slots:
    void updateProgress(int value); // 槽函数:更新进度条

private:
    Ui::Widget *ui;
    MyThread *thread; // 文件复制线程
};

#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)
{
    ui->setupUi(this);

    // 设置 QSlider 的样式
    QString qss = "QSlider { background: transparent; }" // 设置 QSlider 的背景为透明
                  "QSlider::groove:horizontal { border: 1px solid gray; background: lightgray; height: 15px; border-radius: 5px; }"
                  "QSlider::sub-page:horizontal { background: #B5E61D; border-radius: 5px; }"
                  "QSlider::handle:horizontal { background:#5A730E; width: 10px; border-radius: 5px; }";

    ui->horizontalSlider->setStyleSheet(qss);
    ui->horizontalSlider->setRange(0, 100); // 设置进度条范围
    ui->horizontalSlider->setValue(0); // 初始值为 0

    // 选择源文件
    QString sourceFile = QFileDialog::getOpenFileName(this, "选择要复制的文件");
    if (sourceFile.isEmpty()) {
        QMessageBox::warning(this, "警告", "未选择源文件");
        return;
    }

    // 选择目标文件
    QString destinationFile = QFileDialog::getSaveFileName(this, "选择保存位置");
    if (destinationFile.isEmpty()) {
        QMessageBox::warning(this, "警告", "未选择目标文件");
        return;
    }

    // 创建并启动线程
    thread = new MyThread(sourceFile, destinationFile, this);
    connect(thread, &MyThread::progressUpdated, this, &Widget::updateProgress);
    thread->start();
}

Widget::~Widget()
{
    if (thread) {
        thread->quit(); // 停止线程
        thread->wait(); // 等待线程结束
        delete thread; // 释放线程对象
    }
    delete ui;
}

// 槽函数:更新进度条
void Widget::updateProgress(int value)
{
    if (value == -1) {
        QMessageBox::critical(this, "错误", "文件复制失败");
        return;
    }
    ui->horizontalSlider->setValue(value); // 更新 QSlider 的值
    if (value == 100) {
        QMessageBox::information(this, "完成", "文件复制完成");
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/982492.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C语言100天练习题【记录本】

C语言经典100题&#xff08;手把手 编程&#xff09; 可以在哔哩哔哩找到 已解决的天数&#xff1a;一&#xff0c;二&#xff0c;五&#xff0c;六 下面的都是模模糊糊的 可以学学这些算法&#xff0c;我是算法白痴&#xff0c;但是我不是白痴&#xff0c;可以学&#xff…

L1G5000XTuner 微调个人小助手认知

环境配置与数据准备 本节中&#xff0c;我们将演示如何安装 XTuner。 推荐使用 Python-3.10 的 conda 虚拟环境安装 XTuner。 步骤 0. 使用 conda 先构建一个 Python-3.10 的虚拟环境 cd ~ #git clone 本repo git clone https://github.com/InternLM/Tutorial.git -b camp4 mk…

【JavaEE】阻塞队列

【JavaEE】阻塞队列 一、什么是阻塞队列&#xff1f;二、阻塞队列的特点三、阻塞队列的常用方法3.1 抛出异常3.2 有返回结果&#xff0c;不会抛出异常3.3 阻塞 四、常见的阻塞队列4.1 ArrayBlockingQueue4.2 LinkedBlockingQueue4.3 SynchronousQueue4.4 PriorityBlockingQueue…

【Python项目】基于深度学习的车辆特征分析系统

【Python项目】基于深度学习的车辆特征分析系统 技术简介&#xff1a;采用Python技术、MySQL数据库、卷积神经网络&#xff08;CNN&#xff09;等实现。 系统简介&#xff1a;该系统基于深度学习技术&#xff0c;特别是卷积神经网络&#xff08;CNN&#xff09;&#xff0c;用…

蓝桥杯备赛:每日一题

只学习不思考不记笔记假把式 这道题目的难度很难&#xff0c;当然主要的原因在于模型的转化&#xff0c;刚看的这道题也是一脸懵&#xff0c;但是转换成覆盖模型后就好了很多&#xff0c;归跟接地就是每块区域的中取最大的最少的牛覆盖天数&#xff0c;然后根据这个天数求每一块…

7. 机器人记录数据集(具身智能机器人套件)

1. 树莓派启动机器人 conda activate lerobotpython lerobot/scripts/control_robot.py \--robot.typelekiwi \--control.typeremote_robot2. huggingface平台配置 huggingface官网 注册登录申请token&#xff08;要有写权限&#xff09;安装客户端 # 安装 pip install -U …

突破极限:高性能ROCK 220A-M 工业级无人机电调深度测评 —— 无人机动力系统的核心守护者

引言 在无人机技术高速发展的今天&#xff0c;动力系统的稳定性与效率成为决定任务成败的关键。作为工业级电调领域的标杆产品&#xff0c;ROCK 220A-M 凭借其卓越的性能与多重安全设计&#xff0c;为专业级无人机应用提供了可靠的动力解决方案。本文将从技术架构、防护…

OceanBase-obcp-v3考试资料梳理

集群架构 基本概念 集群: 集群由一个或多个Region组成,Region 由一个或多个Zone组成,Zone由一个或多个OBServer组成,每个OBServer里有若干个partition的Replica。 Region: 对应物理上的一个城市或地域,当OB集群由多个Region组成时, 数据库的数据和服务能力就具备地域…

深度学习PyTorch之13种模型精度评估公式及调用方法

深度学习pytorch之22种损失函数数学公式和代码定义 深度学习pytorch之19种优化算法&#xff08;optimizer&#xff09;解析 深度学习pytorch之4种归一化方法&#xff08;Normalization&#xff09;原理公式解析和参数使用 深度学习pytorch之简单方法自定义9类卷积即插即用 实时…

Gartner发布2025年网络安全六大预测

文章目录 前言趋势1&#xff1a;生成式AI推动数据安全计划趋势2&#xff1a;管理机器身份趋势3&#xff1a;战术型AI趋势4&#xff1a;优化网络安全技术趋势5&#xff1a;扩大安全行为与文化计划的价值趋势6&#xff1a;应对网络安全倦怠 前言 Gartner发布2025年网络安全六大预…

WPS Word中英文混杂空格和行间距不一致调整方案

文章目录 问题1&#xff1a;在两端对齐的情况下&#xff0c;如何删除参考文献&#xff08;英文&#xff09;的空格问题2&#xff1a;中英文混杂行间距不一致问题问题3&#xff1a;设置中文为固定字体&#xff0c;设置西文为固定字体参考 问题1&#xff1a;在两端对齐的情况下&a…

代码随想录算法训练营第22天 | 组合 组合总和 电话号码的字母组合

77. 组合 77. 组合 - 力扣&#xff08;LeetCode&#xff09; class Solution {List<Integer> path new ArrayList<>();List<List<Integer>> result new ArrayList<>();public void backTracking(int n,int k,int startIndex){if(path.size() …

Hadoop、Hive、Spark的关系

Part1&#xff1a;Hadoop、Hive、Spark关系概览 1、MapReduce on Hadoop 和spark都是数据计算框架&#xff0c;一般认为spark的速度比MR快2-3倍。 2、mapreduce是数据计算的过程&#xff0c;map将一个任务分成多个小任务&#xff0c;reduce的部分将结果汇总之后返回。 3、HIv…

从0开始的操作系统手搓教程21:进程子系统的一个核心功能——简单的进程切换

目录 具体说说我们的简单RR调度 处理时钟中断处理函数 调度器 schedule switch_to 我们下面&#xff0c;就要开始真正的进程切换了。在那之前&#xff0c;笔者想要说的是——我们实现的进程切换简单的无法再简单了——也就是实现一个超级简单的轮询调度器。 每一个进程按照…

EP 架构:未来主流方向还是特定场景最优解?

DeepSeek MoE架构采用跨节点专家并行&#xff08;EP&#xff09;架构&#xff0c;在提升推理系统性能方面展现出巨大潜力。这一架构在发展进程中也面临诸多挑战&#xff0c;其未来究竟是会成为行业的主流方向&#xff0c;还是仅适用于特定场景&#xff0c;成为特定领域的最优解…

win11编译llama_cpp_python cuda128 RTX30/40/50版本

Geforce 50xx系显卡最低支持cuda128&#xff0c;llama_cpp_python官方源只有cpu版本&#xff0c;没有cuda版本&#xff0c;所以自己基于0.3.5版本源码编译一个RTX 30xx/40xx/50xx版本。 1. 前置条件 1. 访问https://developer.download.nvidia.cn/compute/cuda/12.8.0/local_…

前端到AI,LangChain.Js(五)

学习地址&#xff1a; 学习小册 实战 基于前面的RAG模块&#xff0c;可以通过构建本地存储向量数据库&#xff0c;本地存储聊天记录&#xff0c;部署成stream API&#xff0c;做一个chat bot。 Agents模块&#xff0c;可以通过tools进行数据标签和信息提取&#xff0c;通过RU…

使用 Arduino 和 Wi-Fi 控制 RGB LED

通过 WiFi 的 Arduino RGb LED 控制器 &#xff0c;在本文中&#xff0c;我们将介绍下一个基于 IOT 的项目 - 使用 Wi-Fi 的 RGB LED 闪光灯。在这里&#xff0c;我们使用 Arduino 和 ESP8266 Wi-Fi 模块通过 Android 手机通过 Wi-Fi 控制 RGB LED 的颜色。 在这个 RGB Flash…

C# 开发工具Visual Studio下载和安装

开发环境与工具 C#的主要开发环境是Visual Studio&#xff0c;这是一个功能强大的集成开发环境&#xff08;IDE&#xff09;&#xff0c;集成了代码编辑、调试、项目管理、版本控制等功能。此外&#xff0c;Visual Studio Code也是一个轻量级的跨平台代码编辑器&#xff0c;支…

HTML + CSS 题目

1.说说你对盒子模型的理解? 一、是什么 对一个文档进行布局的时候&#xff0c;浏览器渲染引擎会根据标准之一的css基础盒模型&#xff0c;将所有元素表示为一个个矩形的盒子。 一个盒子由四个部分组成: content&#xff0c;padding&#xff0c;border&#xff0c;margin 下…