如何使用Qt QPainter绘制线性渐变圆弧?
我正在尝试开发一个定制的如何使用Qt QPainter绘制线性渐变圆弧?,qt,linear-gradients,qpainter,Qt,Linear Gradients,Qpainter,我正在尝试开发一个定制的QProgressBar,它将如下图所示: 我创建了一个扩展QProgressBar的类并实现了paintEvent(): 这非常适合绘制圆形进度条,但我在绘制进度条的线性渐变颜色时遇到了问题。我尝试使用QLinearGradient对象创建QPen,并尝试将QPainter笔刷设置为QLinearGradient对象,但两种策略都不起作用。是否可以使用具有线性渐变颜色的QPainter绘制圆弧?此解决方案并不完全符合您的要求;渐变从上到下,而不是围绕圆: #inclu
QProgressBar
,它将如下图所示:
我创建了一个扩展QProgressBar的类并实现了paintEvent():
这非常适合绘制圆形进度条,但我在绘制进度条的线性渐变颜色时遇到了问题。我尝试使用
QLinearGradient
对象创建QPen
,并尝试将QPainter
笔刷设置为QLinearGradient
对象,但两种策略都不起作用。是否可以使用具有线性渐变颜色的QPainter
绘制圆弧?此解决方案并不完全符合您的要求;渐变从上到下,而不是围绕圆:
#include <QtWidgets>
class Widget : public QWidget
{
public:
Widget() {
resize(200, 200);
}
void paintEvent(QPaintEvent *) {
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
const QRectF bounds(0, 0, width(), height());
painter.fillRect(bounds, "#1c1c1c");
QPen pen;
pen.setCapStyle(Qt::RoundCap);
pen.setWidth(20);
QLinearGradient gradient;
gradient.setStart(bounds.width() / 2, 0);
gradient.setFinalStop(bounds.width() / 2, bounds.height());
gradient.setColorAt(0, "#1c1c1c");
gradient.setColorAt(1, "#28ecd6");
QBrush brush(gradient);
pen.setBrush(brush);
painter.setPen(pen);
QRectF rect = QRectF(pen.widthF() / 2.0, pen.widthF() / 2.0, width() - pen.widthF(), height() - pen.widthF());
painter.drawArc(rect, 90 * 16, 0.65 * -360 * 16);
}
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
Widget w;
w.show();
return app.exec();
}
#包括
类Widget:publicqwidget
{
公众:
Widget(){
调整大小(200200);
}
无效paintEvent(QPaintEvent*){
油漆工(本);
painter.setRenderInt(QPainter::抗锯齿);
常量QRectF边界(0,0,width(),height());
painter.fillRect(边界“#1c1c”);
QPen笔;
pen.setCapStyle(Qt::RoundCap);
笔设置宽度(20);
线性梯度;
gradient.setStart(bounds.width()/2,0);
gradient.setFinalStop(bounds.width()/2,bounds.height());
梯度。设置颜色为(0,#1c1c”);
梯度。设置颜色(1,#28ecd6”);
QBrush刷(梯度);
钢笔、毛笔;
画师:画笔;
QRectF rect=QRectF(pen.widthF()/2.0,pen.widthF()/2.0,width()-pen.widthF(),height()-pen.widthF());
绘制弧(矩形,90*16,0.65*-360*16);
}
};
int main(int argc,char*argv[])
{
QApplication应用程序(argc、argv);
小部件w;
w、 show();
返回app.exec();
}
但是,它是一个具有线性渐变的圆弧!:p我知道这是一个老问题,但几天前我遇到了它,我想我有一个解决办法。你要做的是创建一个圆锥形渐变并剪辑你想用作圆形加载条的圆盘。以下是一个例子: widget.h:
#ifndef小部件
#定义小部件
#包括
类事件;
类Widget:publicqwidget
{
Q_对象
公众:
显式小部件(QWidget*parent=0);
~Widget();
无效设置加载角(内部加载角);
int loadingAngle()常量;
void setDiscWidth(int-width);
int discWidth()常量;
受保护的:
无效油漆事件(QPaintEvent*);
私人:
内m_装载角;
国际货币单位宽度;
};
#endif//WIDGET\u H
widget.cpp:
#包括“widget.h”
#包括
#包括
#包括
#包括
Widget::Widget(QWidget*父项):
QWidget(母公司),
m_加载角(0),
m_宽度(0)
{
}
小部件::~Widget()
{
}
void小部件::setLoadingAngle(int-loadingAngle)
{
m_loadingAngle=loadingAngle;
}
int Widget::loadingAngle()常量
{
返回m_装载角;
}
void小部件::setDiscWidth(int-width)
{
m_宽度=宽度;
}
int小部件::discWidth()常量
{
返回m_宽度;
}
void小部件::paintEvent(QPaintEvent*)
{
QRect drawingRect;
drawingRect.setX(rect().x()+m_宽度);
drawingRect.setY(rect().y()+m_宽度);
drawingRect.setWidth(rect().width()-m_width*2);
drawingRect.setHeight(rect().height()-m_width*2);
油漆工(本);
painter.setRenderInt(QPainter::抗锯齿);
准锥梯度;
gradient.setCenter(drawingRect.center());
梯度。设定角(90);
梯度。setColorAt(0,QColor(178255,246));
梯度色(1,QColor(5,44,50));
int弧长近似值=m_宽度+m_宽度/3;
QPen笔(QBrush(梯度),m_宽度);
pen.setCapStyle(Qt::RoundCap);
画师:画笔;
绘制弧(绘制弧长,90*16-弧长近似值,-m_加载角*16);
}
main.cpp:
#包括“widget.h”
#包括
int main(int argc,char*argv[])
{
质量保证申请a(argc、argv);
小部件w;
w、 设置盘宽(20);
w、 设置加载角度(270);
w、 show();
返回a.exec();
}
结果是:
当然,这不是一个完整而精确的解决方案,但我认为这是你需要知道的一切,以实现你想要的。其余的细节不难实施
#include <QtWidgets>
class Widget : public QWidget
{
public:
Widget() {
resize(200, 200);
}
void paintEvent(QPaintEvent *) {
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
const QRectF bounds(0, 0, width(), height());
painter.fillRect(bounds, "#1c1c1c");
QPen pen;
pen.setCapStyle(Qt::RoundCap);
pen.setWidth(20);
QLinearGradient gradient;
gradient.setStart(bounds.width() / 2, 0);
gradient.setFinalStop(bounds.width() / 2, bounds.height());
gradient.setColorAt(0, "#1c1c1c");
gradient.setColorAt(1, "#28ecd6");
QBrush brush(gradient);
pen.setBrush(brush);
painter.setPen(pen);
QRectF rect = QRectF(pen.widthF() / 2.0, pen.widthF() / 2.0, width() - pen.widthF(), height() - pen.widthF());
painter.drawArc(rect, 90 * 16, 0.65 * -360 * 16);
}
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
Widget w;
w.show();
return app.exec();
}
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
class QPaintEvent;
class Widget : public QWidget
{
Q_OBJECT
public:
explicit Widget(QWidget *parent = 0);
~Widget();
void setLoadingAngle(int loadingAngle);
int loadingAngle() const;
void setDiscWidth(int width);
int discWidth() const;
protected:
void paintEvent(QPaintEvent *);
private:
int m_loadingAngle;
int m_width;
};
#endif // WIDGET_H
#include "widget.h"
#include <QPaintEvent>
#include <QPainter>
#include <QConicalGradient>
#include <QPen>
Widget::Widget(QWidget *parent) :
QWidget(parent),
m_loadingAngle(0),
m_width(0)
{
}
Widget::~Widget()
{
}
void Widget::setLoadingAngle(int loadingAngle)
{
m_loadingAngle = loadingAngle;
}
int Widget::loadingAngle() const
{
return m_loadingAngle;
}
void Widget::setDiscWidth(int width)
{
m_width = width;
}
int Widget::discWidth() const
{
return m_width;
}
void Widget::paintEvent(QPaintEvent *)
{
QRect drawingRect;
drawingRect.setX(rect().x() + m_width);
drawingRect.setY(rect().y() + m_width);
drawingRect.setWidth(rect().width() - m_width * 2);
drawingRect.setHeight(rect().height() - m_width * 2);
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
QConicalGradient gradient;
gradient.setCenter(drawingRect.center());
gradient.setAngle(90);
gradient.setColorAt(0, QColor(178, 255, 246));
gradient.setColorAt(1, QColor(5, 44, 50));
int arcLengthApproximation = m_width + m_width / 3;
QPen pen(QBrush(gradient), m_width);
pen.setCapStyle(Qt::RoundCap);
painter.setPen(pen);
painter.drawArc(drawingRect, 90 * 16 - arcLengthApproximation, -m_loadingAngle * 16);
}
#include "widget.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Widget w;
w.setDiscWidth(20);
w.setLoadingAngle(270);
w.show();
return a.exec();
}