qt-material-widgets/components/circularprogress.cpp

223 lines
4.9 KiB
C++
Raw Normal View History

2016-06-18 09:12:20 +00:00
#include "circularprogress.h"
2016-06-18 09:36:40 +00:00
#include <QPainter>
2016-06-19 09:17:47 +00:00
#include <QPropertyAnimation>
#include <QSequentialAnimationGroup>
#include <QParallelAnimationGroup>
#include "circularprogress_p.h"
2016-06-19 09:17:47 +00:00
#include "circularprogress_internal.h"
#include "lib/style.h"
CircularProgressPrivate::CircularProgressPrivate(CircularProgress *q)
2016-06-19 09:17:47 +00:00
: q_ptr(q),
delegate(0),
progressType(Material::IndeterminateProgress),
2016-06-19 09:17:47 +00:00
size(64),
penWidth(6.25),
useThemeColors(true)
{
}
CircularProgressPrivate::~CircularProgressPrivate()
{
}
void CircularProgressPrivate::init()
{
2016-06-19 09:17:47 +00:00
Q_Q(CircularProgress);
delegate = new CircularProgressDelegate(q);
QSizePolicy policy(QSizePolicy::MinimumExpanding,
QSizePolicy::MinimumExpanding);
q->setSizePolicy(policy);
QParallelAnimationGroup *group = new QParallelAnimationGroup(q);
group->setLoopCount(-1);
QPropertyAnimation *animation;
animation = new QPropertyAnimation(q);
animation->setPropertyName("dashLength");
animation->setTargetObject(delegate);
animation->setEasingCurve(QEasingCurve::InOutQuad);
animation->setStartValue(0.1);
animation->setKeyValueAt(0.15, 0.2);
animation->setKeyValueAt(0.6, 20);
animation->setKeyValueAt(0.7, 20);
animation->setEndValue(20);
animation->setDuration(2050);
group->addAnimation(animation);
animation = new QPropertyAnimation(q);
animation->setPropertyName("dashOffset");
animation->setTargetObject(delegate);
animation->setEasingCurve(QEasingCurve::InOutSine);
animation->setStartValue(0);
animation->setKeyValueAt(0.15, 0);
animation->setKeyValueAt(0.6, -7);
animation->setKeyValueAt(0.7, -7);
animation->setEndValue(-25);
animation->setDuration(2050);
group->addAnimation(animation);
animation = new QPropertyAnimation(q);
animation->setPropertyName("angle");
animation->setTargetObject(delegate);
animation->setStartValue(0);
animation->setEndValue(719);
animation->setDuration(2050);
group->addAnimation(animation);
2016-06-19 09:17:47 +00:00
group->start();
}
CircularProgress::CircularProgress(QWidget *parent)
2016-06-19 09:17:47 +00:00
: QProgressBar(parent),
d_ptr(new CircularProgressPrivate(this))
{
d_func()->init();
}
CircularProgress::~CircularProgress()
{
}
2016-06-18 09:36:40 +00:00
2016-06-19 09:17:47 +00:00
void CircularProgress::setProgressType(Material::ProgressType type)
{
Q_D(CircularProgress);
d->progressType = type;
update();
}
Material::ProgressType CircularProgress::progressType() const
{
Q_D(const CircularProgress);
return d->progressType;
}
void CircularProgress::setUseThemeColors(bool state)
{
Q_D(CircularProgress);
d->useThemeColors = state;
update();
}
bool CircularProgress::useThemeColors() const
{
Q_D(const CircularProgress);
return d->useThemeColors;
}
void CircularProgress::setLineWidth(qreal width)
{
Q_D(CircularProgress);
d->penWidth = width;
update();
}
qreal CircularProgress::lineWidth() const
{
Q_D(const CircularProgress);
return d->penWidth;
}
void CircularProgress::setSize(int size)
{
Q_D(CircularProgress);
d->size = size;
update();
}
int CircularProgress::size() const
{
Q_D(const CircularProgress);
return d->size;
}
void CircularProgress::setColor(const QColor &color)
{
Q_D(CircularProgress);
d->color = color;
setUseThemeColors(false);
}
QColor CircularProgress::color() const
{
Q_D(const CircularProgress);
if (d->useThemeColors || !d->color.isValid()) {
return Style::instance().themeColor("primary1");
} else {
return d->color;
}
}
QSize CircularProgress::sizeHint() const
{
Q_D(const CircularProgress);
const qreal s = d->size+d->penWidth+8;
return QSize(s, s);
}
2016-06-18 09:36:40 +00:00
void CircularProgress::paintEvent(QPaintEvent *event)
{
2016-06-19 09:17:47 +00:00
Q_UNUSED(event)
Q_D(CircularProgress);
2016-06-18 09:36:40 +00:00
QPainter painter(this);
2016-06-19 09:17:47 +00:00
painter.setRenderHint(QPainter::Antialiasing);
2016-06-18 09:36:40 +00:00
2016-06-19 10:34:10 +00:00
if (Material::IndeterminateProgress == d->progressType) {
painter.translate(width()/2, height()/2);
painter.rotate(d->delegate->angle());
}
2016-06-19 09:17:47 +00:00
QPen pen;
pen.setCapStyle(Qt::RoundCap);
pen.setWidthF(d->penWidth);
pen.setColor(color());
if (Material::IndeterminateProgress == d->progressType)
{
QVector<qreal> pattern;
pattern << d->delegate->dashLength()*d->size/50 << 30*d->size/50;
pen.setDashOffset(d->delegate->dashOffset()*d->size/50);
pen.setDashPattern(pattern);
2016-06-19 09:17:47 +00:00
painter.setPen(pen);
2016-06-19 09:17:47 +00:00
painter.drawEllipse(QPoint(0, 0), d->size/2, d->size/2);
}
else
{
2016-06-19 10:34:10 +00:00
painter.setPen(pen);
const qreal x = (width()-d->size)/2;
const qreal y = (height()-d->size)/2;
const qreal a = 360*(value()-minimum())/(maximum()-minimum());
QPainterPath path;
path.arcMoveTo(x, y, d->size, d->size, 0);
path.arcTo(x, y, d->size, d->size, 0, a);
2016-06-19 09:17:47 +00:00
2016-06-19 10:34:10 +00:00
painter.drawPath(path);
}
2016-06-19 09:17:47 +00:00
}