添加链接
link之家
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接

这个程序可以实现把图片、动图、视频当成壁纸显示在图标图层之下,软件会保存上一次关闭时的选择 重启时恢复,有什么问题评论区看到会回复

有问题欢迎指出,需要编译好的程序 可以私信或留下联系方式发送

废话不多说先上 效果 再上 代码 ,核心代码我都打上了“关键”两字

静态图片:

动画壁纸:

视频壁纸 带有音频的话可以勾选壁纸音乐:

.pro文件内容

QT       += core gui multimediawidgets
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
CONFIG += c++17
RC_ICONS = ../image/tubiao.ico
# You can make your code fail to compile if it uses deprecated APIs.
# In order to do so, uncomment the following line.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0
SOURCES += \
    main.cpp \
    widget.cpp
HEADERS += \
    widget.h
FORMS += \
    widget.ui
# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QMenu>
#include <QMovie>
#include <QTimer>
#include <qlabel.h>
#include <QSettings>
#include <windows.h>
#include <QFileDialog>
#include <QVideoWidget>
#include <QMediaPlayer>
#include <QAudioOutput>
#include <QSystemTrayIcon>
QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE
class Widget : public QWidget
    Q_OBJECT
public:
    Widget(QWidget *parent = nullptr);
    ~Widget();
    HWND winwallpaper();
    HWND winwallpaper_send();
    static inline BOOL CALLBACK enumwin(HWND han,LPARAM lp);
    void mp4(QString fine); //显示视频
    void gif(QString fine); //显示图片
    //最小化托盘信号处理
    void sys(QSystemTrayIcon::ActivationReason r);
    QSystemTrayIcon* system;
    //图片、视频类
    QLabel* label;
    QVideoWidget* vid;
    QMediaPlayer* med;
    QAudioOutput* aud = new QAudioOutput;
    //使用此类记录使用状态
    QSettings* ConfigFile;
private:
    Ui::Widget *ui;
#endif // WIDGET_H
#include "widget.h"
#include "ui_widget.h"
int if_sum = 1;
HWND win;
Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
    this->setWindowFlags(Qt::FramelessWindowHint);//去掉窗口边框
    //this->setWindowTitle("动态壁纸");                 //窗口标题 已去掉边框所以没有意义
    //this->setWindowIcon(QIcon("image/tubiao.ico")); //窗口图标 已去掉边框所以没有意义
    ConfigFile = new QSettings("config.cfg",QSettings::IniFormat);
    //最小化托盘类指针
    system = new QSystemTrayIcon(this);
    ui->setupUi(this);
    //动态壁纸按钮信号处理
    connect(ui->gifButton,&QPushButton::clicked,this,[=]()
       //获取文件路径与文件类型过滤器,返回文件路径
       QString gifFile = QFileDialog::getOpenFileName(this,"打开动态图片","/","image(*.png *.jpg *.jpeg *.gif)");
       //先关掉上一个窗口,不然无法在退出程序时关闭窗口
       if(ConfigFile->value("GIF") == "正在使用")
           label->close();
       else if(ConfigFile->value("MP4") == "正在使用")
           vid->close();
       //将信息写入配置文件,待下次启动时初始化程序
       ConfigFile->setValue("GIF","正在使用");
       ConfigFile->setValue("GIF图片路径",gifFile);
       ConfigFile->setValue("MP4","暂停使用");
       //将文件路径传递给自定义图片显示函数
       gif(ConfigFile->value("GIF图片路径").toString());
    //视频壁纸按钮信号处理,同上
    connect(ui->mp4Button,&QPushButton::clicked,this,[=]()
       QString mp4File = QFileDialog::getOpenFileName(this,"打开视频文件","/","MV(*.mp4 *.wav *.mp3)");
       if(ConfigFile->value("GIF") == "正在使用")
           label->close();
       else if(ConfigFile->value("MP4") == "正在使用")
           vid->close();
       ConfigFile->setValue("MP4","正在使用");
       ConfigFile->setValue("MP4视频路径",mp4File);
       ConfigFile->setValue("GIF","暂停使用");
       mp4(ConfigFile->value("MP4视频路径").toString());
    //最小化托盘右键处理
    QAction* show = new QAction("显示",this);
    connect(show,&QAction::triggered,this,[=]()
        this->show();
    QAction* clos = new QAction("退出",this);
    connect(clos,&QAction::triggered,this,[=]()
        //先关闭所有显示窗口,再关闭主程序,(可优化)退出程序时的小卡顿由此产生
        label->close();
        vid->close();
        this->close();
    //只有在第一次运行时显示主窗口,往后启动或 自启动将不显示
    if(ConfigFile->value("显示窗口") == "否")
        QTimer::singleShot(100,this,[=]()
                this->hide();
                QMenu* menu = new QMenu(this);
                menu->addAction(show);
                menu->addAction(clos);
                system->setContextMenu(menu);
                system->setToolTip("动态壁纸");
                system->setIcon(QIcon("image/tubiao.ico"));
                system->show();
    ConfigFile->setValue("显示窗口","否");
    //右上角隐藏程序按钮大小及图标,下方是此按钮信号处理
    ui->closeapp->resize(16,16);
    ui->closeapp->setStyleSheet("border-image:url(image/close.png)");
    connect(ui->closeapp,&QPushButton::clicked,this,[=]()
        this->hide();
        QMenu* menu = new QMenu(this);
        menu->addAction(show);
        menu->addAction(clos);
        system->setContextMenu(menu);
        system->setToolTip("动态壁纸");
        system->setIcon(QIcon("image/tubiao.ico"));
        system->show();
        if(if_sum)
            system->showMessage("动态壁纸","已隐藏到最小化托盘");
            if_sum = 0;
    //最小化托盘左键双击信号处理,功能(显示主窗口)
    connect(system,&QSystemTrayIcon::activated,this,&Widget::sys);
    //壁纸音乐复选框信号处理
    connect(ui->checkBox,&QCheckBox::clicked,this,[=]()
        if(ui->checkBox->isChecked())
           aud->setMuted(false); //这个类方法是实现实时开关音乐的关键
           ConfigFile->setValue("壁纸音乐","开启");
            aud->setMuted(true);
            ConfigFile->setValue("壁纸音乐","关闭");
    //使用上一次关闭时的参数初始化程序
    if(ConfigFile->value("壁纸音乐") == "开启")
       ui->checkBox->setChecked(true);
    if(ConfigFile->value("MP4") == "正在使用")
      mp4(ConfigFile->value("MP4视频路径").toString());
    if(ConfigFile->value("GIF") == "正在使用")
              gif(ConfigFile->value("GIF图片路径").toString());
Widget::~Widget()
    delete ui;
 * 下方三个方法都是实现壁纸的关键
 * 1.获取桌面最顶层窗口句柄
 * 2.发送信号至桌面最顶层窗口
 * 3.遍历WorkerW窗口
HWND Widget::winwallpaper()
    HWND hwnd = ::FindWindow(L"Progman",NULL);
    return hwnd;
HWND Widget::winwallpaper_send()
    int result;
    HWND hwnd = ::FindWindow(L"Progman",NULL);
    SendMessageTimeout(hwnd,0x52c,0,0,SMTO_NORMAL,0x3e8,(PDWORD_PTR)&result);
    return hwnd;
WINBOOL Widget::enumwin(HWND han, LPARAM lp)
    HWND def = ::FindWindowEx(han,0,L"SHELLDLL_DefView",NULL);
    if(def!= 0)
        win = FindWindowEx(0,han,L"WorkerW",0);
    return true;
//关键代码!将窗口至于桌面最顶层窗口之下,随后播放多媒体
void Widget::mp4(QString fine)
    winwallpaper_send();
    EnumWindows(enumwin,(LPARAM)NULL);
    ShowWindow(win,SW_HIDE);
    vid = new QVideoWidget;
    med = new QMediaPlayer;
    med->setVideoOutput(vid);
    vid->setWindowState(Qt::WindowMaximized);
    vid->setWindowFlags(Qt::FramelessWindowHint);
    vid->showFullScreen();
    med->setSource(QUrl::fromLocalFile(fine));
    med->setLoops(QMediaPlayer::Infinite);
    aud->setMuted(true);
    med->setAudioOutput(aud);
    if(ConfigFile->value("壁纸音乐") == "开启")
        aud->setMuted(false);
    med->play();
    SetParent((HWND)vid->winId(),winwallpaper());
    vid->show();
//关键代码!将窗口至于桌面最顶层窗口之下,随后显示图片
void Widget::gif(QString fine)
    winwallpaper_send();
    EnumWindows(enumwin,(LPARAM)NULL);
    ShowWindow(win,SW_HIDE);
    QMovie* movie = new QMovie(fine);
    label = new QLabel;
    label->setWindowState(Qt::WindowMaximized);
    label->setWindowFlags(Qt::FramelessWindowHint);
    label->setMovie(movie);
    label->setScaledContents(true);
    movie->start();
    SetParent((HWND)label->winId(),winwallpaper());
    label->show();
void Widget::sys(QSystemTrayIcon::ActivationReason r)
    if(r == QSystemTrayIcon::DoubleClick)
        this->show();
                                    今天突然想换桌面的壁纸 想换个动态,网上那些桌面壁纸软件不是收费就是广告一大堆,所以决定自己写一个,看到github上有这个代码于是自己动手参照修改了一下这是他的git地址 https://github。
                                    通过Qt做一些GUI项目时,有时需要去展示一些gif动态图至界面,如果将显示动态图的操作一并放置在主线程,即窗口显示线程中时,当需要加载的动态图数量多、尺寸大时,同时拖动窗口有可能产生卡顿的现象,且动态图的显示也有可能会卡顿。因此考虑设置一个子线程专用于动态图的显示。Qt中多线程的实现主要有以下两种方式:(1)继承QThread类,重写run()方法(2)继承QObject类,通过movetoThread()方法实现本案例使用第(1)种方式实现动态图的多线程显示。......
通过实现一个动态的桌面背景程序,来加强对Qt的paintEvent的理解与使用,以及一些小知识。
二.实现过程
1. 初始化,并保存每段圆弧的起始度数和扫过的弧度,便于绘制圆弧。
 //记录二十一个圆的圆弧信息
 for(int i=0;i<21;i++) 
        vector<double>  td;    //存放一个圆里面圆弧的起始度数
        vector<double>  pd;     //存放一个圆里面圆弧扫过的度数