渐变色QGradient

渐变色QGradient

1 QLinearGradient

void MainWindow::paintEvent(QPaintEvent * )
{
    QPainter painter(this);
	//从左上角填充到右下角
    QLinearGradient linearGradient(100, 100, 300, 300);
    //填充过程中插入的颜色
    linearGradient.setColorAt(0, QColor(133, 132, 76));
    linearGradient.setColorAt(0.5, QColor(122, 32, 57));
    linearGradient.setColorAt(1, QColor(12, 32, 157));

    QBrush brush(linearGradient);
    //使填充无边界
    painter.setPen(Qt::NoPen);
    painter.setBrush(brush);
    //矩形
    painter.drawRect(100, 100, 200, 200);
}

此时,我们已经规定填充的方向,从左上角的(100, 100)到右下角的(300, 300);填充的颜色从(100, 100)的颜色1到(200, 200)的颜色2,最后到(300, 300)处的颜色3。而此次选择的封闭区域刚好是我们初始化填充的区域,能看到三个颜色的渐变过程。如下图所示:

如果将填充的区域改变呢?可以看到,此时封闭范围内只有两种渐变颜色了

painter.drawRect(200, 200, 300, 300);

如果将封闭区域扩大至整个窗口呢?由图可知,我们创建的填充并不是只填充了一个小的封闭区域,而是将整个窗口都填充了。之前创建的小封闭区域,更像是在这整个大窗口上移动选取一部份。

painter.drawRect(0, 0, size().width(), size().height());

在我们设置的小封闭区域外,是否都是这样填充呢?答案是否定的,Qt中有多种传播方式,默认的传播方式为:

linearGradient.setSpread(QGradient::PadSpread);

效果如上图所示。第二种传播方式,在整个窗口中不断重复我们给定的填充方式,如下图所示:

linearGradient.setSpread(QGradient::RepeatSpread);

第三种是镜像地将设置的填充方式填满整个窗口,如下图所示:

linearGradient.setSpread(QGradient::ReflectSpread);

QLinearGradient linearGradient(100, 100, 300, 300);中的两个点的坐标就是填充的方向,大家可以根据需求更改

2 QRadialGradien

1 简单径向渐变
	//需要渐变色的范围,渐变色的圆心,圆形的半径
	QRadialGradient(qreal cx, qreal cy, qreal radius)
	QRadialGradient(const QPointF &center, qreal radius)
	//圆形的左上角,圆形的半径,焦点坐标
	QRadialGradient(qreal cx, qreal cy, qreal radius, qreal fx, qreal fy)
	QRadialGradient(const QPointF &center, qreal radius, const QPointF &focalPoint)
void MainWindow::paintEvent(QPaintEvent * )
{

    QPainter painter(this);
    painter.translate(size().width()/2, size().height()/2);
    QPen pen;
    pen.setWidth(4);
    painter.setPen(pen);
    painter.setRenderHint(QPainter::Antialiasing, true);

    //保存绘图对象
    painter.save();
    //设置填充无边界
    painter.setPen(Qt::NoPen);

    //设置渐变色,圆心与焦点重合,都是原点
    QRadialGradient radialGradient(0,0,200,0,0);
    radialGradient.setColorAt(1,QColor(0,82,199));
    //中间渐变为透明
    radialGradient.setColorAt(0.5,Qt::transparent);
    radialGradient.setColorAt(0,QColor(145, 12, 98));
    //设置画刷
    painter.setBrush(radialGradient);
	
    painter.drawEllipse(-200,-200, 400, 400);

    painter.restore();

}

注:画圆是通过一个矩形的左上角和矩形的长宽确定;渐变范围的参数是圆心和半径


这里有两个圆心,第一个是渐变色的圆心,第二个是焦点的圆心。如果设置两个颜色渐变,焦点是你设定的第一种颜色,圆周就是设定的第二种颜色。

想一个问题,渐变色的填充范围比封闭区间大,是什么效果呢?

    //保存绘图对象
    painter.save();
    //设置填充无边界
    painter.setPen(Qt::NoPen);

    //设置渐变色,圆心与焦点重合,都是原点
    QRadialGradient radialGradient(0,0,200,0,0);
    radialGradient.setColorAt(1,QColor(0,82,199));
    radialGradient.setColorAt(0,QColor(145, 12, 98));
    //设置画刷
    painter.setBrush(radialGradient);

    painter.drawEllipse(-200,-200, 400, 400);
    //painter.drawEllipse(-100,-100, 200, 200);
    painter.restore();

这是渐变范围和封闭范围相同时的情况:

我们将上图的圆形封闭区间变小,结果如下图所示:

painter.drawEllipse(-100,-100, 200, 200);

可以看到,封闭区间变小后,相当于只截取了中间一小部分的区域

那么渐变色的填充范围比封闭区间小呢?将封闭 区域变大后,效果如下图所示:

painter.drawEllipse(-400,-400, 800, 800);

将封闭区域改为矩形,效果如下图所示:

painter.drawRect( -size().width()/2, -size().height()/2, size().width(), size().height());

这就和线性填充的道理相同。

我们还可以改变焦点和渐变中心的位置:

QRadialGradient radialGradient(0,0,200,100,300);

渐变中心为原点,焦点是(100, 300),渐变圆半径为200,焦点在渐变圆的外部,但通过下图可知,焦点被强制放到了圆周上

与线性填充相同,还可以改变扩散方式:

radialGradient.setSpread(QGradient::RepeatSpread);


每相邻的两个重复传播的图形间的半径差都是之前设置的半径

改变焦点位置:

radialGradient.setSpread(QGradient::ReflectSpread);

改变焦点位置后

2 扩展径向渐变

扩展渐变只是在简单渐变上多加了一个焦点的半径,焦点就不再只是一个点了,可以是一个圆

QRadialGradient(qreal cx, qreal cy, qreal centerRadius, qreal fx, qreal fy, qreal focalRadius);

QRadialGradient(const QPointF &center, qreal centerRadius, const QPointF &focalPoint, qreal focalRadius);
    //保存绘图对象
    painter.save();
    //设置填充无边界
    painter.setPen(Qt::NoPen);

    //设置渐变色,圆心与焦点重合,都是原点
    QRadialGradient radialGradient(0,0,300,0,0,150);
    radialGradient.setColorAt(1,QColor(19,82,199));
    radialGradient.setColorAt(0,QColor(15, 82, 108));
    //radialGradient.setSpread(QGradient::ReflectSpread);
    //设置画刷
    painter.setBrush(radialGradient);

    //painter.drawEllipse(-200,-200, 400, 400);
    painter.drawRect( -size().width()/2, -size().height()/2, size().width(), size().height());
    painter.restore();

3 QConicalGradient

锥形渐变,本身就是360°全方位填充,所以说就不存在填充方式Spread,无论填哪个参数,结果都一样

// QConicalGradient ctor
QConicalGradient(qreal cx, qreal cy, qreal angle)
QConicalGradient(const QPointF &center, qreal angle)
  • 初始化的角度是逆时针定位,就和极坐标一样;而旋转填充时,是顺时针填充。
void MainWindow::paintEvent(QPaintEvent * )
{

    QPainter painter(this);
    painter.translate(size().width()/2, size().height()/2);
    QPen pen;
    pen.setWidth(4);
    painter.setPen(pen);
    painter.setRenderHint(QPainter::Antialiasing, true);

    //保存绘图对象
    painter.save();
    //设置填充无边界
    painter.setPen(Qt::NoPen);

    //设置渐变色,锥形的中心是原点,起始角度为90°
    QConicalGradient conicalGradient(0,0,90);
    conicalGradient.setColorAt(1,QColor(19,82,199));
    conicalGradient.setColorAt(0,QColor(15, 202, 108));
    //radialGradient.setSpread(QGradient::ReflectSpread);
    //设置画刷
    painter.setBrush(conicalGradient);

    //painter.drawEllipse(-200,-200, 400, 400);
    painter.drawRect( -size().width()/2, -size().height()/2, size().width(), size().height());
    painter.restore();

}

绘制的封闭区域为整个窗口

绘制的封闭区域为某一个圆

移动圆的位置,出现的情况和前两种填充方式一样


至此,三种渐变填充方式介绍完毕

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值