Add spinner to hide uninitialized layout after login

This commit is contained in:
Konstantinos Sideris 2017-04-26 02:23:12 +03:00
parent 58936cd67b
commit 415ef7e9c7
9 changed files with 494 additions and 9 deletions

View file

@ -25,6 +25,8 @@
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui_(new Ui::MainWindow)
, progress_modal_{nullptr}
, spinner_{nullptr}
{
ui_->setupUi(this);
client_ = QSharedPointer<MatrixClient>(new MatrixClient("matrix.org"));
@ -53,12 +55,40 @@ MainWindow::MainWindow(QWidget *parent)
connect(chat_page_, SIGNAL(close()), this, SLOT(showWelcomePage()));
connect(chat_page_, SIGNAL(changeWindowTitle(QString)), this, SLOT(setWindowTitle(QString)));
connect(client_.data(),
SIGNAL(initialSyncCompleted(const SyncResponse &)),
this,
SLOT(removeOverlayProgressBar()));
connect(client_.data(),
SIGNAL(loginSuccess(QString, QString, QString)),
this,
SLOT(showChatPage(QString, QString, QString)));
}
void MainWindow::removeOverlayProgressBar()
{
QTimer *timer = new QTimer(this);
timer->setSingleShot(true);
connect(timer, &QTimer::timeout, [=]() {
timer->deleteLater();
if (progress_modal_ != nullptr) {
progress_modal_->deleteLater();
progress_modal_->fadeOut();
}
if (progress_modal_ != nullptr)
spinner_->deleteLater();
progress_modal_ = nullptr;
spinner_ = nullptr;
});
timer->start(500);
}
void MainWindow::showChatPage(QString userid, QString homeserver, QString token)
{
QSettings settings;
@ -69,6 +99,17 @@ void MainWindow::showChatPage(QString userid, QString homeserver, QString token)
int index = sliding_stack_->getWidgetIndex(chat_page_);
sliding_stack_->slideInIndex(index, SlidingStackWidget::AnimationDirection::LEFT_TO_RIGHT);
if (spinner_ == nullptr) {
spinner_ = new CircularProgress(this);
spinner_->setColor("#acc7dc");
spinner_->setSize(100);
}
if (progress_modal_ == nullptr) {
progress_modal_ = new OverlayModal(this, spinner_);
progress_modal_->fadeIn();
}
login_page_->reset();
chat_page_->bootstrap(userid, homeserver, token);
}

190
src/ui/CircularProgress.cc Normal file
View file

@ -0,0 +1,190 @@
#include <QPainter>
#include <QParallelAnimationGroup>
#include <QPen>
#include <QPropertyAnimation>
#include "CircularProgress.h"
#include "Theme.h"
CircularProgress::CircularProgress(QWidget *parent)
: QProgressBar{parent}
, progress_type_{ui::ProgressType::IndeterminateProgress}
, width_{6.25}
, size_{64}
{
delegate_ = new CircularProgressDelegate(this);
setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding);
auto group = new QParallelAnimationGroup(this);
group->setLoopCount(-1);
auto length_animation = new QPropertyAnimation(this);
length_animation->setPropertyName("dashLength");
length_animation->setTargetObject(delegate_);
length_animation->setEasingCurve(QEasingCurve::InOutQuad);
length_animation->setStartValue(0.1);
length_animation->setKeyValueAt(0.15, 0.2);
length_animation->setKeyValueAt(0.6, 20);
length_animation->setKeyValueAt(0.7, 20);
length_animation->setEndValue(20);
length_animation->setDuration(2050);
auto offset_animation = new QPropertyAnimation(this);
offset_animation->setPropertyName("dashOffset");
offset_animation->setTargetObject(delegate_);
offset_animation->setEasingCurve(QEasingCurve::InOutSine);
offset_animation->setStartValue(0);
offset_animation->setKeyValueAt(0.15, 0);
offset_animation->setKeyValueAt(0.6, -7);
offset_animation->setKeyValueAt(0.7, -7);
offset_animation->setEndValue(-25);
offset_animation->setDuration(2050);
auto angle_animation = new QPropertyAnimation(this);
angle_animation->setPropertyName("angle");
angle_animation->setTargetObject(delegate_);
angle_animation->setStartValue(0);
angle_animation->setEndValue(719);
angle_animation->setDuration(2050);
group->addAnimation(length_animation);
group->addAnimation(offset_animation);
group->addAnimation(angle_animation);
group->start();
}
void CircularProgress::setProgressType(ui::ProgressType type)
{
progress_type_ = type;
update();
}
void CircularProgress::setLineWidth(qreal width)
{
width_ = width;
update();
updateGeometry();
}
void CircularProgress::setSize(int size)
{
size_ = size;
update();
updateGeometry();
}
ui::ProgressType CircularProgress::progressType() const
{
return progress_type_;
}
qreal CircularProgress::lineWidth() const
{
return width_;
}
int CircularProgress::size() const
{
return size_;
}
void CircularProgress::setColor(const QColor &color)
{
color_ = color;
}
QColor CircularProgress::color() const
{
if (!color_.isValid()) {
return QColor("red");
}
return color_;
}
QSize CircularProgress::sizeHint() const
{
const qreal s = size_ + width_ + 8;
return QSize(s, s);
}
void CircularProgress::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
/*
* If the progress bar is disabled draw an X instead
*/
if (!isEnabled()) {
QPen pen;
pen.setCapStyle(Qt::RoundCap);
pen.setWidthF(lineWidth());
pen.setColor("gray");
auto center = rect().center();
painter.setPen(pen);
painter.drawLine(center - QPointF(20, 20), center + QPointF(20, 20));
painter.drawLine(center + QPointF(20, -20), center - QPointF(20, -20));
return;
}
if (progress_type_ == ui::ProgressType::IndeterminateProgress) {
painter.translate(width() / 2, height() / 2);
painter.rotate(delegate_->angle());
}
QPen pen;
pen.setCapStyle(Qt::RoundCap);
pen.setWidthF(width_);
pen.setColor(color());
if (ui::IndeterminateProgress == progress_type_) {
QVector<qreal> pattern;
pattern << delegate_->dashLength() * size_ / 50 << 30 * size_ / 50;
pen.setDashOffset(delegate_->dashOffset() * size_ / 50);
pen.setDashPattern(pattern);
painter.setPen(pen);
painter.drawEllipse(QPoint(0, 0), size_ / 2, size_ / 2);
} else {
painter.setPen(pen);
const qreal x = (width() - size_) / 2;
const qreal y = (height() - size_) / 2;
const qreal a = 360 * (value() - minimum()) / (maximum() - minimum());
QPainterPath path;
path.arcMoveTo(x, y, size_, size_, 0);
path.arcTo(x, y, size_, size_, 0, a);
painter.drawPath(path);
}
}
CircularProgress::~CircularProgress()
{
}
CircularProgressDelegate::CircularProgressDelegate(CircularProgress *parent)
: QObject(parent)
, progress_(parent)
, dash_offset_(0)
, dash_length_(89)
, angle_(0)
{
Q_ASSERT(parent);
}
CircularProgressDelegate::~CircularProgressDelegate()
{
}

72
src/ui/OverlayModal.cc Normal file
View file

@ -0,0 +1,72 @@
/*
* nheko Copyright (C) 2017 Konstantinos Sideris <siderisk@auth.gr>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <QDebug>
#include <QPainter>
#include <QVBoxLayout>
#include "OverlayModal.h"
OverlayModal::OverlayModal(QWidget *parent, QWidget *content)
: OverlayWidget(parent)
, duration_{500}
, color_{QColor(55, 55, 55)}
{
setAttribute(Qt::WA_TranslucentBackground);
auto layout = new QVBoxLayout();
layout->addWidget(content);
layout->setAlignment(Qt::AlignCenter);
setLayout(layout);
opacity_ = new QGraphicsOpacityEffect(this);
setGraphicsEffect(opacity_);
opacity_->setOpacity(1);
animation_ = new QPropertyAnimation(opacity_, "opacity", this);
animation_->setStartValue(1);
animation_->setEndValue(0);
animation_->setDuration(duration_);
animation_->setEasingCurve(QEasingCurve::Linear);
connect(animation_, &QPropertyAnimation::finished, [this]() {
if (animation_->direction() == QAbstractAnimation::Forward)
this->close();
});
}
void OverlayModal::paintEvent(QPaintEvent *event)
{
Q_UNUSED(event);
QPainter painter(this);
painter.fillRect(rect(), color_);
}
void OverlayModal::fadeIn()
{
animation_->setDirection(QAbstractAnimation::Backward);
animation_->start();
show();
}
void OverlayModal::fadeOut()
{
animation_->setDirection(QAbstractAnimation::Forward);
animation_->start();
}

View file

@ -4,12 +4,11 @@
OverlayWidget::OverlayWidget(QWidget *parent)
: QWidget(parent)
{
if (parent)
if (parent) {
parent->installEventFilter(this);
}
OverlayWidget::~OverlayWidget()
{
setGeometry(overlayGeometry());
raise();
}
}
bool OverlayWidget::event(QEvent *event)