Qt绘制圆环(渐变圆环)

Qt绘制圆环(渐变圆环)_第1张图片

在这里插入图片描述
Qt绘制圆环(渐变圆环)_第2张图片
这里先介绍两种其它网友的方法。
方法一:
通过drawPie和底色来控制。

void Widget::paintEvent(QPaintEvent *event)
{
    QPainter painter(this);
    painter.setPen(QPen(Qt::transparent,4,Qt::SolidLine));
    painter.setBrush(QBrush(QColor("red")));
    QRect rect(0,0,200,200);
    QRect rect1(50, 50, 100, 100);
    painter.drawPie(rect,270*16,-90*16);
    painter.setBrush(QBrush(QColor("white")));
    painter.drawPie(rect1,270*16,-90*16);
}

方法二:
通过QRegion 的subtracted来控制圆环的区域,此方法比较巧妙。

void MainWindow::paintEvent(QPaintEvent* event)
{
    QPainter painter(this);
    painter.save();
    //设置反锯齿
    painter.setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform | QPainter::Qt4CompatiblePainting);
    QRect drawRect = event->rect();
    QRegion region(drawRect.adjusted(10,10,-10,-10),QRegion::Ellipse);
    drawRect.setSize(QSize(drawRect.width()/2,drawRect.height()/2));
    drawRect.moveTopLeft(QPoint((event->rect().width() - drawRect.width())/2,(event->rect().height() - drawRect.height())/2));
    QRegion region2(drawRect,QRegion::Ellipse);
    QPainterPath painterPath;
    painterPath.addRegion(region.subtracted(region2));
    painter.fillPath(painterPath,Qt::red);
    event->accept();
    painter.restore();
}

但是以上两种方法都无法实现绘制透明的任意角度的圆环,且还需要支持渐变色。
我绘制圆环实现逻辑:
通过Qt的QPainterPath来实现,通过三角函数计算x,y坐标点围成一个环形区域。

.h

class MGradientLabel : public QLabel
{
    Q_OBJECT
public:
    MGradientLabel(QWidget* parent = nullptr);
    ~MGradientLabel();


    void setPipeWidth(int num);  //设置环道宽度
    void setAngleRange(int staAng, int endAng); //设置环道范围
    void setPipeColor(QColor staColor = QColor("#ffffff"), QColor endColor = QColor("#000000"), double stop1 = 0, double stop2 = 0); //设置环道颜色
protected:
    void paintEvent(QPaintEvent *);

private:
    int m_pipeWidth = 20;
    int m_staAng = 210;
    int m_endAng = 330;
    QColor m_staColor = QColor("#ffffff");
    QColor m_endColor = QColor("#000000");
    double m_stop1 = 0;
    double m_stop2 = 0;
};

.cpp

MGradientLabel::MGradientLabel(QWidget *parent):QLabel(parent)
{

}

MGradientLabel::~MGradientLabel()
{

}

void MGradientLabel::setPipeColor(QColor staColor, QColor endColor, double stop1, double stop2)
{
    m_staColor = staColor;
    m_endColor = endColor;
    m_stop1 = stop1;
    m_stop2 = stop2;
}

void MGradientLabel::setPipeWidth(int num)
{
    m_pipeWidth = num;
}

void MGradientLabel::setAngleRange(int staAng,int endAng)
{
    m_staAng = staAng;
    m_endAng = endAng;
}

void MGradientLabel::paintEvent(QPaintEvent *)
{
    QPainter p(this);

    // 反走样
    p.setRenderHints(QPainter::SmoothPixmapTransform|QPainter::Antialiasing);

    // 设置画笔颜色、宽度
    p.setPen(Qt::NoPen);

    p.translate(width()/2,height()/2);
    // 设置渐变色
    QConicalGradient conical(0, 0, m_staAng);
    conical.setColorAt(0, m_staColor);
    conical.setColorAt(m_stop1, m_staColor);
    conical.setColorAt(m_stop2, m_endColor);
    // 设置画刷填充
    p.setBrush(conical);

    QPainterPath painterPath;
    painterPath.moveTo((width()/2-m_pipeWidth)*qSin((m_staAng+90)*(M_PI/180)),(width()/2-m_pipeWidth)*qCos((m_staAng+90)*(M_PI/180)));
    painterPath.lineTo(width()/2*qSin((m_staAng+90)*(M_PI/180)),width()/2*qCos((m_staAng+90)*(M_PI/180)));
    painterPath.arcTo(QRect(-width()/2,-height()/2,width(),height()),m_staAng,m_endAng - m_staAng);
    painterPath.lineTo((width()/2-m_pipeWidth)*qSin((m_endAng - 270)*(M_PI/180)),(height()/2-m_pipeWidth)*qCos((m_endAng - 270)*(M_PI/180)));
    painterPath.arcTo(QRect(-width()/2 + m_pipeWidth,-height()/2 + m_pipeWidth,width() - m_pipeWidth*2,height() - m_pipeWidth*2),m_endAng,-(m_endAng - m_staAng));

    p.drawPath(painterPath);
}

你可能感兴趣的:(QT,qt,开发语言,c++)