Qt 给窗口绘制阴影

前言

最近自定义一个消息弹框,但是没加阴影之前,觉得有点扁平。然后仔细看了Qt自带的消息弹框,发现是没有加上阴影的问题。所以就在网上搜索怎么加阴影,有多种方法。写这个博客的目的是记录一下这几种方法,并且加上我对于这些方法的理解。

具体的方法有

  1. 重载paintEvent,调用drawRect或者drawRoundedRect或者drawPath来手绘阴影

  2. 使用QGraphicsDropShadowEffect类,来绘制阴影

  3. 使用九图拼凑法

  4. 九宫格缩放阴影法

但是不管是哪种方法,都需要设置窗口的背景透明

    this->setWindowFlags(Qt::FramelessWindowHint);
this->setAttribute(Qt::WA_TranslucentBackground);

重载paintEvent

这个方法就是重载paintEvent,然后自己设置绘图的区域,根据阴影的大小、根据阴影的颜色,一圈一圈的去画阴影。

然后又分有三个函数来进行阴影的绘制

  1. drawPath
    这个函数的作用是绘制一个路线,路线可以由很多不同的曲线或者直线组成,这个可以绘制多边形。

    绘制代码如下:
void Waiting::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event) // 1. 初始化一个QPainter对象用来绘制
// 2. QPainter::Antialiasing,让引擎尽可能的消除锯齿
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing, true); QColor color(0, 0, 0, 50);
// 此处循环次数为10,目的是绘制宽度为10的阴影
for(int i=0; i<10; i++)
{
// 3. 初始化一个QPainterPath对象
QPainterPath path;
// 4. 设置填充规则
path.setFillRule(Qt::WindingFill);
// 5. 添加一个矩形
path.addRect(10-i, 10-i, this->width()-(10-i)*2, this->height()-(10-i)*2);
// 6. 设置颜色的透明度
color.setAlpha(150 - qSqrt(i)*50);
painter.setPen(color);
// 7. 绘制线路
painter.drawPath(path);
}
}

绘制效果如下:

Tips:

  1. drawRectdrawRoundedRect
    这两个函数分别是画矩形阴影和画带圆角的阴影,除了最后绘制的时候锁调用的函数不一样,其余都是一样的。drawRect是绘制矩形的,drawRoundedRect是绘制带圆角的。


代码如下:

void Waiting::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event) QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing, true); QColor color(0, 0, 0, 50);
for(int i=0; i<10; i++)
{
color.setAlpha(150 - qSqrt(i)*50);
painter.setPen(color);
// drawRect 绘制矩形
// painter.drawRect(10-i, 10-i, this->width()-(10-i)*2, this->height()-(10-i)*2);
// drawRoundedRect 绘制带原角
painter.drawRoundedRect(10-i, 10-i, this->width()-(10-i)*2, this->height()-(10-i)*2, 20, 20);
}
}

效果图如下:

QGraphicsDropShadowEffect方法

这个类就直接用就好了,代码如下:

m_pEffect = new QGraphicsDropShadowEffect(m_background);
m_pEffect->setOffset(0, 0);
m_pEffect->setColor(QColor(QStringLiteral("black")));
m_pEffect->setBlurRadius(30);
m_background->setGraphicsEffect(m_pEffect);

Tips:

  1. setOffser这个是设置阴影的起始点位于窗口的哪个位置

  2. setBlurRadius这个是设置阴影的模糊程度,越大就越模糊

具体对比请看下图:

使用九图拼凑法

这个方法参考一去二三里大佬的博客:Qt之阴影边框_一去二三里_新浪博客

九宫格缩放阴影法

这里是另外以为大佬的博客:Qt之使用QPainter自绘实现窗口阴影边框_前行之路还需前行-CSDN博客

我这里只对大佬的代码进行一个自我的理解,具体内容,请移步去大佬的博客。
Tips:

  1. ninePatchScalePixmap函数

    iHorzSplitiVertSplit这两个变量分别代表对原始的图片进行九宫格分之后的高和宽。

    DstWidthDstHeight这个两个变量则代表最后需要的图片的高和宽

如下图:

Qt 给窗口绘制阴影的更多相关文章

  1. 给QT不规则窗口添加阴影

    在家休息,试着用QT去模仿各类管家软件的界面,做到自绘阴影的时候,蛋疼了. 网上搜到的基本都是一篇文章转来转去,一开始也被思路限制了. 尝试重载paintEvent,然后自己绘制矩形阴影,但是绘制的算 ...

  2. qt中窗口绘制——图片的绘制

    在qt 中,QPixmap 用于表示一张图片,支持png,jpg格式的加载. QPixmap pm("c:/test.png"); 或者 QPixmap pm; pm.load(& ...

  3. qt 自定义窗口绘制正弦曲线

    circlewidget.h #ifndef CIRCLAWIDGET_H #define CIRCLAWIDGET_H #include <QFrame> #include<QVe ...

  4. QT笔记之实现阴影窗口

    方法一: 代码实现 在窗口构造函数中加入:setAttribute(Qt::WA_TranslucentBackground),保证不被绘制上的部分透明 重写void paintEvent(QPain ...

  5. [Qt5] 使用Qt设计器绘制主窗口

    实践代码: git clone https://github.com/dilexliu/learn_qt5.git Step1: Qt设计器绘制窗口 保存会得到一个文件: mainwindow.ui ...

  6. C++框架_之Qt的窗口部件系统的详解-上

    C++框架_之Qt的窗口部件系统的详解-上 第一部分概述 第一次建立helloworld程序时,曾看到Qt Creator提供的默认基类只有QMainWindow.QWidget和QDialog三种. ...

  7. QT 基本图形绘制

    QT 基本图形绘制 1.告诉绘制引擎一些东西 QPainter::Antialiasing 在可能的情况下,反锯齿       QPainter::TextAntialiasing 在可能的情况下,文 ...

  8. Qt多窗口编程详解

    常用的窗体基类是 QWidget.QDialog 和 QMainWindow,在创建 GUI 应用程序时选择窗体基类就是从这 3 个类中选择. QWidget 直接继承于 QObject,是 QDia ...

  9. [转] - 使用Qt作窗口截屏(含源码)

    截屏(screenshot),就是将屏幕上的东西拷贝下来存成图片文件.介绍的好像有点多余:(,那我们就直接切入正题. QPixmap提供了两个函数grabWidget和grabWindow可以将屏幕上 ...

  10. QT源码解析(一) QT创建窗口程序、消息循环和WinMain函数

    QT源码解析(一) QT创建窗口程序.消息循环和WinMain函数 分类: QT2009-10-28 13:33 17695人阅读 评论(13) 收藏 举报 qtapplicationwindowse ...

随机推荐

  1. Qt开发经验小技巧266-270

    从Qt6.4版本开始多媒体模块提供了ffmpeg作为后端解码使用(6.5版本默认就是ffmpeg),可以通过设置环境变量来更改使用哪种后端解码,在main函数的第一行 qputenv("QT ...

  2. Qt编写地图综合应用11-动态添加

    一.前言 在添加设备点或者区域形状的时候,会考虑是直接静态的方式写入到网页中加载,还是动态js函数异步加载的方式,这个需要根据现场的实际需求来,如果只需要一次加载的话建议静态即可,如果运行期间还需要动 ...

  3. Qt编写的项目作品32-定制化安装包工具(雨田哥作品)

    一.功能特点 纯Qt编写,跨平台. 支持自定义安装目录等. 安装和卸载界面可自定义. 一键式脚本build.bat,生成安装包EXE. 兼容XP系统. 支持配置文件填充安装包信息. 指定应用程序中文名 ...

  4. 【Java 温故而知新系列】基础知识-03 基本类型对应之包装类

    1.包装类都有哪些? 基本类型都有对应的包装类型,这些包装类提供了一种面向对象的方式来处理基本数据类型,允许它们被用于需要对象的场景,如集合框架.泛型等. 对应关系: 基本类型 包装类型 boolea ...

  5. TNN-linux编译测试记录

    Github: https://github.com/Tencent/TNN docs: https://github.com/Tencent/TNN/blob/master/doc/cn/user/ ...

  6. Centos8 BAD错误

    signature hdr data: BAD, no. of bytes(127884) out of range error: /var/cache/dnf/os-86dc4ac5eda5a39e ...

  7. Solution -「NOI 2017」「洛谷 P3823」蚯蚓排队

    \(\mathscr{Description}\)   Link.   (自己看题, 我总不能让题意比题解还长吧?) \(\mathscr{Solution}\)   下一组我一定写成 solutio ...

  8. Note -「广义二项级数」浅赏

      上回 说到拉反和扩展拉反,那么这里先给几个小小变形或推广.   基础 ver: \[\begin{align} [x^n]G(x) &= \frac{1}{n}[x^{n-1}](F(x) ...

  9. 题解:AT_abc385_f [ABC385F] Visible Buildings

    小学二年级就会的基本一次函数知识. 抽象一下题意: 求 \(n\) 个点 \((X_i, H_i)\) 中任意两个点组成的直线的截距的最大值(不小于 \(0\),\(X_i\) 递增). 先说结论:先 ...

  10. WordPress产品导入后内容出现乱码,以及附属一些别的功能

    效果图如下 该插件附带了一个可以把产品描述里面的超链接给去掉,以及有的产品图片点击会在地址栏上面显示图片的路径,在该插件可以进行关闭,并且替换成一个模态窗,还有对产品邮费展示进行了处理,到金额到达包邮 ...