Add fade out effect to the loading screen
This commit is contained in:
parent
3740adb6f5
commit
3ca0af8bb3
@ -5,6 +5,7 @@
|
||||
#include <unordered_map>
|
||||
#include <QBuffer>
|
||||
#include <QByteArray>
|
||||
#include <QGraphicsOpacityEffect>
|
||||
#include <QHBoxLayout>
|
||||
#include <QIODevice>
|
||||
#include <QImage>
|
||||
@ -13,6 +14,7 @@
|
||||
#include <QPalette>
|
||||
#include <QPixmap>
|
||||
#include <QProgressBar>
|
||||
#include <QPropertyAnimation>
|
||||
#include <QStyleOption>
|
||||
#include <QTime>
|
||||
#include <QtConcurrent/QtConcurrentRun>
|
||||
@ -71,6 +73,25 @@ LoadingScreen::LoadingScreen(QWidget* parent)
|
||||
ui->setupUi(this);
|
||||
setMinimumSize(1280, 720);
|
||||
|
||||
// Create a fade out effect to hide this loading screen widget.
|
||||
// When fading opacity, it will fade to the parent widgets background color, which is why we
|
||||
// create an internal widget named fade_widget that we use the effect on, while keeping the
|
||||
// loading screen widget's background color black. This way we can create a fade to black effect
|
||||
opacity_effect = new QGraphicsOpacityEffect(this);
|
||||
opacity_effect->setOpacity(1);
|
||||
ui->fade_parent->setGraphicsEffect(opacity_effect);
|
||||
fadeout_animation = std::make_unique<QPropertyAnimation>(opacity_effect, "opacity");
|
||||
fadeout_animation->setDuration(500);
|
||||
fadeout_animation->setStartValue(1);
|
||||
fadeout_animation->setEndValue(0);
|
||||
fadeout_animation->setEasingCurve(QEasingCurve::OutBack);
|
||||
|
||||
// After the fade completes, hide the widget and reset the opacity
|
||||
connect(fadeout_animation.get(), &QPropertyAnimation::finished, [this] {
|
||||
hide();
|
||||
opacity_effect->setOpacity(1);
|
||||
emit Hidden();
|
||||
});
|
||||
connect(this, &LoadingScreen::LoadProgress, this, &LoadingScreen::OnLoadProgress,
|
||||
Qt::QueuedConnection);
|
||||
qRegisterMetaType<VideoCore::LoadCallbackStage>();
|
||||
@ -115,9 +136,14 @@ void LoadingScreen::Prepare(Loader::AppLoader& loader) {
|
||||
ui->logo->setPixmap(map);
|
||||
}
|
||||
|
||||
slow_shader_compile_start = false;
|
||||
OnLoadProgress(VideoCore::LoadCallbackStage::Prepare, 0, 0);
|
||||
}
|
||||
|
||||
void LoadingScreen::OnLoadComplete() {
|
||||
fadeout_animation->start(QPropertyAnimation::KeepWhenStopped);
|
||||
}
|
||||
|
||||
void LoadingScreen::OnLoadProgress(VideoCore::LoadCallbackStage stage, std::size_t value,
|
||||
std::size_t total) {
|
||||
using namespace std::chrono;
|
||||
@ -125,6 +151,7 @@ void LoadingScreen::OnLoadProgress(VideoCore::LoadCallbackStage stage, std::size
|
||||
// reset the timer if the stage changes
|
||||
if (stage != previous_stage) {
|
||||
ui->progress_bar->setStyleSheet(progressbar_style[stage]);
|
||||
// Hide the progress bar during the prepare stage
|
||||
if (stage == VideoCore::LoadCallbackStage::Prepare) {
|
||||
ui->progress_bar->hide();
|
||||
} else {
|
||||
|
@ -27,7 +27,9 @@ enum class LoadCallbackStage;
|
||||
|
||||
class QBuffer;
|
||||
class QByteArray;
|
||||
class QGraphicsOpacityEffect;
|
||||
class QMovie;
|
||||
class QPropertyAnimation;
|
||||
|
||||
class LoadingScreen : public QWidget {
|
||||
Q_OBJECT
|
||||
@ -45,14 +47,21 @@ public:
|
||||
/// used resources such as the logo and banner.
|
||||
void Clear();
|
||||
|
||||
/// Slot used to update the status of the progress bar
|
||||
void OnLoadProgress(VideoCore::LoadCallbackStage stage, std::size_t value, std::size_t total);
|
||||
|
||||
/// Hides the LoadingScreen with a fade out effect
|
||||
void OnLoadComplete();
|
||||
|
||||
// In order to use a custom widget with a stylesheet, you need to override the paintEvent
|
||||
// See https://wiki.qt.io/How_to_Change_the_Background_Color_of_QWidget
|
||||
void paintEvent(QPaintEvent* event) override;
|
||||
|
||||
signals:
|
||||
void LoadProgress(VideoCore::LoadCallbackStage stage, std::size_t value, std::size_t total);
|
||||
/// Signals that this widget is completely hidden now and should be replaced with the other
|
||||
/// widget
|
||||
void Hidden();
|
||||
|
||||
private:
|
||||
#ifndef YUZU_QT_MOVIE_MISSING
|
||||
@ -64,6 +73,9 @@ private:
|
||||
std::size_t previous_total = 0;
|
||||
VideoCore::LoadCallbackStage previous_stage;
|
||||
|
||||
QGraphicsOpacityEffect* opacity_effect = nullptr;
|
||||
std::unique_ptr<QPropertyAnimation> fadeout_animation = nullptr;
|
||||
|
||||
// Definitions for the differences in text and styling for each stage
|
||||
std::unordered_map<VideoCore::LoadCallbackStage, const char*> progressbar_style;
|
||||
std::unordered_map<VideoCore::LoadCallbackStage, QString> stage_translations;
|
||||
|
@ -30,59 +30,77 @@
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QLabel" name="logo">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
|
||||
</property>
|
||||
<property name="margin">
|
||||
<number>30</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout" stretch="1,0,1">
|
||||
<property name="spacing">
|
||||
<number>15</number>
|
||||
</property>
|
||||
<property name="sizeConstraint">
|
||||
<enum>QLayout::SetNoConstraint</enum>
|
||||
</property>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignBottom">
|
||||
<widget class="QLabel" name="stage">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Minimum" vsizetype="Minimum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black; color: white;
|
||||
<widget class="QWidget" name="fade_parent" native="true">
|
||||
<layout class="QVBoxLayout" name="verticalLayout_2">
|
||||
<property name="spacing">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item alignment="Qt::AlignLeft|Qt::AlignTop">
|
||||
<widget class="QLabel" name="logo">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
|
||||
</property>
|
||||
<property name="margin">
|
||||
<number>30</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="verticalLayout" stretch="1,0,1">
|
||||
<property name="spacing">
|
||||
<number>15</number>
|
||||
</property>
|
||||
<property name="sizeConstraint">
|
||||
<enum>QLayout::SetNoConstraint</enum>
|
||||
</property>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignBottom">
|
||||
<widget class="QLabel" name="stage">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Minimum" vsizetype="Minimum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black; color: white;
|
||||
font: 75 20pt "Arial";</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Loading Shaders 387 / 1628</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignTop">
|
||||
<widget class="QProgressBar" name="progress_bar">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>500</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">QProgressBar {
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Loading Shaders 387 / 1628</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignTop">
|
||||
<widget class="QProgressBar" name="progress_bar">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>500</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">QProgressBar {
|
||||
color: white;
|
||||
border: 2px solid white;
|
||||
outline-color: black;
|
||||
@ -92,45 +110,48 @@ QProgressBar::chunk {
|
||||
background-color: white;
|
||||
border-radius: 15px;
|
||||
}</string>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>50</number>
|
||||
</property>
|
||||
<property name="textVisible">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="format">
|
||||
<string>Loading Shaders %v out of %m</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignTop">
|
||||
<widget class="QLabel" name="value">
|
||||
<property name="toolTip">
|
||||
<string notr="true"/>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black; color: white;
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>50</number>
|
||||
</property>
|
||||
<property name="textVisible">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="format">
|
||||
<string>Loading Shaders %v out of %m</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item alignment="Qt::AlignHCenter|Qt::AlignTop">
|
||||
<widget class="QLabel" name="value">
|
||||
<property name="toolTip">
|
||||
<string notr="true"/>
|
||||
</property>
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black; color: white;
|
||||
font: 75 15pt "Arial";</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Stage 1 of 2. Estimate Time 5m 4s</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item alignment="Qt::AlignRight|Qt::AlignBottom">
|
||||
<widget class="QLabel" name="banner">
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black;</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="margin">
|
||||
<number>30</number>
|
||||
</property>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Stage 1 of 2. Estimate Time 5m 4s</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item alignment="Qt::AlignRight|Qt::AlignBottom">
|
||||
<widget class="QLabel" name="banner">
|
||||
<property name="styleSheet">
|
||||
<string notr="true">background-color: black;</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="margin">
|
||||
<number>30</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
|
@ -415,6 +415,13 @@ void GMainWindow::InitializeWidgets() {
|
||||
loading_screen = new LoadingScreen(this);
|
||||
loading_screen->hide();
|
||||
ui.horizontalLayout->addWidget(loading_screen);
|
||||
connect(loading_screen, &LoadingScreen::Hidden, [&] {
|
||||
loading_screen->Clear();
|
||||
if (emulation_running) {
|
||||
render_window->show();
|
||||
render_window->setFocus();
|
||||
}
|
||||
});
|
||||
|
||||
// Create status bar
|
||||
message_label = new QLabel();
|
||||
@ -1513,10 +1520,7 @@ void GMainWindow::OnStopGame() {
|
||||
}
|
||||
|
||||
void GMainWindow::OnLoadComplete() {
|
||||
loading_screen->hide();
|
||||
loading_screen->Clear();
|
||||
render_window->show();
|
||||
render_window->setFocus();
|
||||
loading_screen->OnLoadComplete();
|
||||
}
|
||||
|
||||
void GMainWindow::OnMenuReportCompatibility() {
|
||||
|
Loading…
Reference in New Issue
Block a user