Qt自定义开关按钮
先看实现的效果
可设置开关背景色、圆背景色、动画速度,核心代码如下
//开启鼠标追踪,动态切换鼠标样式setMouseTracking(true);//设置属性,初始化动画setProperty("circlePos", QPointF((float)height() * 0.05, (float)height() * 0.05));m_pAni = new QPropertyAnimation(this);m_pAni->setTargetObject(this);m_pAni->setPropertyName("circlePos");m_pAni->setStartValue(QPointF((float)height() * 0.05, (float)height() * 0.05));m_pAni->setEndValue(QPointF((float)width() - (float)height() * 0.95, (float)height() * 0.05));m_pAni->setDuration(200);connect(m_pAni, &QPropertyAnimation::valueChanged, this, &SwitchButton::onValueChanged);connect(m_pAni, &QPropertyAnimation::finished, this, &SwitchButton::onFinished);
根据动画值改变切换圆的位置、动画完毕再切换开关背景
void SwitchButton::onValueChanged(const QVariant& value){QPointF pos = value.toPointF();m_circleRect.setX(pos.x());m_circleRect.setY(pos.y());m_circleRect.setSize(QSize(m_fRadius * 1.8, m_fRadius * 1.8));update();}void SwitchButton::onFinished(){m_rectCurBrush = m_bOpen ? m_rectOpenBrush : m_rectCloseBrush;update();}
重写鼠标事件,实现点击切换状态
void SwitchButton::mouseReleaseEvent(QMouseEvent *event){QWidget::mouseReleaseEvent(event);if (!inLegalRange(event->pos())){return;}m_bOpen = !m_bOpen;changeState();}void SwitchButton::changeState(){m_pAni->setDirection(m_bOpen ? QPropertyAnimation::Forward : QPropertyAnimation::Backward);m_pAni->start();update();}
最后就是绘制
void SwitchButton::drawRoundRect(QPainter& painter){painter.save();painter.setBrush(m_rectCurBrush);painter.drawRoundedRect(rect(), m_fRadius, m_fRadius);painter.restore();}void SwitchButton::drawCircle(QPainter& painter){painter.save();painter.setBrush(m_circleBrush);painter.drawEllipse(m_circleRect);painter.restore();}
代码下载链接:Qt开关按钮