当前位置: 首页 > news >正文

基于Qt实现的窗口半透明流动背景

背景

  • 基于c++ & Qt实现的半透明渐变色窗口背景

先看效果 (gif录制掉帧,请自行编译源码查看,效果比gif流畅)

recording

完整源码

GradientWidget.h

#ifndef GRADIENTWIDGET_H
#define GRADIENTWIDGET_H#include <QWidget>
#include <QColor>
#include <QPointF>class QTimer;
class QParallelAnimationGroup;class GradientWidget : public QWidget
{Q_OBJECTQ_PROPERTY(QColor startColor READ startColor WRITE setStartColor)Q_PROPERTY(QColor endColor READ endColor WRITE setEndColor)Q_PROPERTY(QPointF startPoint READ startPoint WRITE setStartPoint)Q_PROPERTY(QPointF endPoint READ endPoint WRITE setEndPoint)public:GradientWidget(QWidget* parent = nullptr);~GradientWidget();QColor startColor() const;QColor endColor() const;QPointF startPoint() const;QPointF endPoint() const;public slots:void setStartColor(const QColor& color);void setEndColor(const QColor& color);void setStartPoint(const QPointF& point);void setEndPoint(const QPointF& point);protected:void paintEvent(QPaintEvent* event) override;void resizeEvent(QResizeEvent* event) override;// 添加鼠标事件以实现无边框窗口拖动void mousePressEvent(QMouseEvent* event) override;void mouseMoveEvent(QMouseEvent* event) override;private slots:void updateAnimation();private:QColor getRandomSoftColor();QPointF getRandomPointOnEdge();QTimer* m_timer;QParallelAnimationGroup* m_animationGroup;QColor m_startColor;QColor m_endColor;QPointF m_startPoint;QPointF m_endPoint;// 用于窗口拖动的成员变量QPoint m_dragPosition;
};#endif // GRADIENTWIDGET_H

GradientWidget.cpp

#include "gradientwidget.h"
#include <QPainter>
#include <QLinearGradient>
#include <QPaintEvent>
#include <QMouseEvent>
#include <QTimer>
#include <QRandomGenerator>
#include <QPropertyAnimation>
#include <QParallelAnimationGroup>
#include <QEasingCurve>GradientWidget::GradientWidget(QWidget* parent): QWidget(parent)
{// --- 新增:为半透明和无边框进行设置 ---setWindowFlags(Qt::FramelessWindowHint);setAttribute(Qt::WA_TranslucentBackground, true);// 初始化颜色和渐变点m_startColor = getRandomSoftColor();m_endColor = getRandomSoftColor();m_startPoint = getRandomPointOnEdge();m_endPoint = getRandomPointOnEdge();// 创建动画组m_animationGroup = new QParallelAnimationGroup(this);// 为四个属性创建动画auto setupAnimation = [this](const QByteArray& propertyName){QPropertyAnimation* anim = new QPropertyAnimation(this, propertyName, this);anim->setDuration(5000); // 延长动画时间,让变化更柔和anim->setEasingCurve(QEasingCurve::InOutSine);m_animationGroup->addAnimation(anim);return anim;};setupAnimation("startColor");setupAnimation("endColor");setupAnimation("startPoint");setupAnimation("endPoint");// 创建定时器m_timer = new QTimer(this);connect(m_timer, &QTimer::timeout, this, &GradientWidget::updateAnimation);m_timer->start(4500); // 时间比动画时长略短,实现无缝连接updateAnimation(); // 立即开始第一次动画
}GradientWidget::~GradientWidget() {}void GradientWidget::paintEvent(QPaintEvent* event)
{Q_UNUSED(event);QPainter painter(this);painter.setRenderHint(QPainter::Antialiasing);// 注意:由于设置了WA_TranslucentBackground,我们不需要手动清除背景// 直接绘制带Alpha通道的渐变即可QLinearGradient gradient(m_startPoint, m_endPoint);gradient.setColorAt(0, m_startColor);gradient.setColorAt(1, m_endColor);painter.fillRect(rect(), gradient);
}void GradientWidget::resizeEvent(QResizeEvent* event)
{updateAnimation();QWidget::resizeEvent(event);
}// --- 新增:鼠标事件处理 ---
void GradientWidget::mousePressEvent(QMouseEvent* event)
{if (event->button() == Qt::LeftButton){m_dragPosition = event->globalPos() - frameGeometry().topLeft();event->accept();}
}void GradientWidget::mouseMoveEvent(QMouseEvent* event)
{if (event->buttons() & Qt::LeftButton){move(event->globalPos() - m_dragPosition);event->accept();}
}void GradientWidget::updateAnimation()
{m_animationGroup->stop();// 更新起始颜色动画的目标值auto startColorAnim = static_cast<QPropertyAnimation*>(m_animationGroup->animationAt(0));startColorAnim->setStartValue(m_startColor);startColorAnim->setEndValue(getRandomSoftColor()); // 使用新函数// 更新结束颜色动画的目标值auto endColorAnim = static_cast<QPropertyAnimation*>(m_animationGroup->animationAt(1));endColorAnim->setStartValue(m_endColor);endColorAnim->setEndValue(getRandomSoftColor()); // 使用新函数// 更新起始点动画的目标值auto startPointAnim = static_cast<QPropertyAnimation*>(m_animationGroup->animationAt(2));startPointAnim->setStartValue(m_startPoint);startPointAnim->setEndValue(getRandomPointOnEdge());// 更新结束点动画的目标值auto endPointAnim = static_cast<QPropertyAnimation*>(m_animationGroup->animationAt(3));endPointAnim->setStartValue(m_endPoint);endPointAnim->setEndValue(getRandomPointOnEdge());m_animationGroup->start();
}/*** @brief 生成一个柔和的、半透明的随机颜色* RGB分量范围:60 ~ 230* Alpha分量固定:220 (约86%不透明度)*/
QColor GradientWidget::getRandomSoftColor()
{int r = 60 + QRandomGenerator::global()->bounded(171); // 范围 60-230int g = 60 + QRandomGenerator::global()->bounded(171); // 范围 60-230int b = 60 + QRandomGenerator::global()->bounded(171); // 范围 60-230return QColor(r, g, b, 220); // 固定Alpha值
}QPointF GradientWidget::getRandomPointOnEdge()
{if (width() == 0 || height() == 0) return QPointF(0, 0);int edge = QRandomGenerator::global()->bounded(4);switch (edge){case 0: return QPointF(QRandomGenerator::global()->bounded(width()), 0); // Topcase 1: return QPointF(width(), QRandomGenerator::global()->bounded(height())); // Rightcase 2: return QPointF(QRandomGenerator::global()->bounded(width()), height()); // Bottomcase 3:default: return QPointF(0, QRandomGenerator::global()->bounded(height())); // Left}
}// Getters and Setters
QColor GradientWidget::startColor() const { return m_startColor; }
QColor GradientWidget::endColor() const { return m_endColor; }
QPointF GradientWidget::startPoint() const { return m_startPoint; }
QPointF GradientWidget::endPoint() const { return m_endPoint; }void GradientWidget::setStartColor(const QColor& color)
{m_startColor = color;update();
}void GradientWidget::setEndColor(const QColor& color)
{m_endColor = color;update();
}void GradientWidget::setStartPoint(const QPointF& point)
{m_startPoint = point;update();
}void GradientWidget::setEndPoint(const QPointF& point)
{m_endPoint = point;update();
}

main.cpp

include "gradientwidget.h"
#include <QApplication>int main(int argc, char* argv[])
{QApplication a(argc, argv);GradientWidget w;w.setWindowTitle("Dynamic Gradient Background");w.resize(800, 600);w.show();return a.exec();
}
http://www.rkmt.cn/news/51259.html

相关文章:

  • 2025年11月冷媒剂厂家评测榜:从资质到应用全场景解析
  • 分布式计算通信原语的抽象模型
  • 2025/11/16
  • 数据结构——二十四、图(王道408) - 实践
  • C# Avalonia 18- ControlTemplates - ColorPickerUserControlTest
  • Spring AI Alibaba 项目源码学习(九)-其他继承BaseAgent
  • Linux进程状态 - 教程
  • mybatis_generate_demo
  • 换歌换歌
  • GaN 器件第三象限导通特性
  • Why did Hitler become a greater Napoleon?
  • Qt编写28181推流分发服务/统计访问数量/无人观看超时关闭/等待重新点播/复用点播
  • React Native创建AndroidIOS流程完整指南
  • Ducky - BPMN 工作流管理系统
  • 图论建模问题
  • 2025年甘肃广告策划服务综合推荐排行榜
  • 2025年甘肃兰州比较好的广告物料制作服务团队
  • wordpress批量删除文章
  • mivlus:下载all-MiniLM-L6-v2语言模型
  • 单核超 i9、多核追 i5,2024 Mac mini M4
  • 2025年质量好的金属防锈漆行业内口碑厂家排行榜
  • 2025年知名的破碎机厂家选购指南与推荐
  • 2025年优质的光学真空镀膜机厂家实力及用户口碑排行榜
  • 完整教程:OSP-0.3.1开源软件包的解压缩与分析
  • 30.Python自动获取酷狗音乐工具
  • 2025年专业的自动液压压滤机TOP品牌厂家排行榜
  • 2025年靠谱的导热油电加热器厂家最新权威实力榜
  • 2025年比较好的一级净化工程厂家最新TOP实力排行
  • 2025年质量好的不锈钢储物柜厂家实力及用户口碑排行榜
  • 24.Python自动工资表