代码:
#ifndef COLORGRADIENTROUNDEDBUTTON_H#define COLORGRADIENTROUNDEDBUTTON_H#include <QAbstractButton>#include <QTimer>struct doubleColor{doubleColor(QColor frist = Qt::red,QColor second = Qt::blue):fristColor(frist),secondColor(second){}QColor fristColor;QColor secondColor;bool operator !=(const doubleColor & c){return (this->fristColor != c.fristColor) || (this->secondColor != c.secondColor);}};Q_DECLARE_METATYPE(doubleColor)class ColorGradientRoundedButton : public QAbstractButton{Q_OBJECTpublic:ColorGradientRoundedButton(QWidget *parent = nullptr);~ColorGradientRoundedButton()override;protected:void paintEvent(QPaintEvent *event)override;void enterEvent(QEnterEvent *event)override;void leaveEvent(QEvent *event)override;private:void onTimer();doubleColor startColor;doubleColor endColor;enum class ChangeModel{Plus,Minus};QTimer timer;int rectX{0};ChangeModel rectXChangeModel;};#endif // COLORGRADIENTROUNDEDBUTTON_H
#include "colorgradientroundedbutton.h"#include <QPainter>#include <QPaintEvent>#include <QGraphicsDropShadowEffect>#include <QDebug>#include <QPainterPath>#include <QRandomGenerator>QColor getRandomColor(){return QColor(QRandomGenerator::global()->bounded(255),QRandomGenerator::global()->bounded(255),QRandomGenerator::global()->bounded(255));}ColorGradientRoundedButton::ColorGradientRoundedButton(QWidget *parent): QAbstractButton(parent){startColor = doubleColor(getRandomColor(),getRandomColor());endColor = doubleColor(getRandomColor(),getRandomColor());this->setMinimumSize(180,50);setMouseTracking(true);QGraphicsDropShadowEffect * effect = new QGraphicsDropShadowEffect(this);setGraphicsEffect(effect);effect->setOffset(0,0);effect->setBlurRadius(25);effect->setColor(Qt::black);timer.setInterval(40);connect(&timer,&QTimer::timeout,this,&ColorGradientRoundedButton::onTimer);}ColorGradientRoundedButton::~ColorGradientRoundedButton(){}void ColorGradientRoundedButton::paintEvent(QPaintEvent *event){QPainter painter(this);painter.setRenderHint(QPainter::Antialiasing,true);auto rect = event->rect();auto rectWidth = rect.width();QPainterPath path;path.addRoundedRect(rect,25,25);painter.setClipPath(path);painter.drawRect(rect);QLinearGradient linearGradient1(QPoint(-rectX,0),QPoint(rectWidth - rectX,0));linearGradient1.setColorAt(0,startColor.fristColor);linearGradient1.setColorAt(1,startColor.secondColor);painter.fillRect(QRect(-rectX,0,rectWidth,rect.height()),linearGradient1);QLinearGradient linearGradient2(QPoint(rectWidth - rectX,0),QPoint(rectWidth * 2 - rectX,0));linearGradient2.setColorAt(0,endColor.fristColor);linearGradient2.setColorAt(1,endColor.secondColor);painter.fillRect(QRect(rectWidth - rectX,0,rectWidth,rect.height()),linearGradient2);auto font = painter.font();font.setBold(true);font.setPixelSize(20);painter.setFont(font);painter.setPen(Qt::white);painter.drawText(rect,Qt::AlignCenter,text());}void ColorGradientRoundedButton::onTimer(){if(rectXChangeModel == ChangeModel::Plus){rectX += (rect().width() / 6);if(rectX >= rect().width()){rectX = rect().width();timer.stop();}}else{rectX -= (rect().width() / 6);if(rectX <= 0){rectX = 0;timer.stop();}}update();}void ColorGradientRoundedButton::enterEvent(QEnterEvent *event){if(timer.isActive())timer.stop();rectXChangeModel = ChangeModel::Plus;timer.start();QWidget::enterEvent(event);}void ColorGradientRoundedButton::leaveEvent(QEvent *event){if(timer.isActive())timer.stop();rectXChangeModel = ChangeModel::Minus;timer.start();QWidget::leaveEvent(event);}
使用示例:
QWidget w;w.setPalette(Qt::white);auto vb = new QVBoxLayout;vb->setSpacing(15);for(int i = 0;i < 8;++i){auto btn = new ColorGradientRoundedButton;btn->setText(QString("按钮%1").arg(i));vb->addWidget(btn);}w.setLayout(vb);w.show();
效果: