Make the pause screen "transparent"

When paused (ESC or back), you now see the paused game below, darkened,
instead of the usual menu background.

Not enabled in VR mode for now because it could get weird.
Also not trivial in skip-buffered mode (would require taking a screenshot) so
disabled in that case too.
This commit is contained in:
Henrik Rydgård 2022-11-20 12:22:50 +01:00
parent a3874ebcef
commit 63cbd9c79b
3 changed files with 37 additions and 6 deletions

View File

@ -1105,7 +1105,6 @@ void EmuScreen::update() {
}
}
}
}
void EmuScreen::checkPowerDown() {
@ -1356,8 +1355,7 @@ void EmuScreen::preRender() {
// We only bind it in FramebufferManager::CopyDisplayToOutput (unless non-buffered)...
// We do, however, start the frame in other ways.
bool useBufferedRendering = !g_Config.bSkipBufferEffects;
if ((!useBufferedRendering && !g_Config.bSoftwareRendering) || Core_IsStepping()) {
if ((g_Config.bSkipBufferEffects && !g_Config.bSoftwareRendering) || Core_IsStepping()) {
// We need to clear here already so that drawing during the frame is done on a clean slate.
if (Core_IsStepping() && gpuStats.numFlips != 0) {
draw->BindFramebufferAsRenderTarget(nullptr, { RPAction::KEEP, RPAction::DONT_CARE, RPAction::DONT_CARE }, "EmuScreen_BackBuffer");
@ -1393,6 +1391,18 @@ void EmuScreen::render() {
if (!thin3d)
return; // shouldn't really happen but I've seen a suspicious stack trace..
// We can still render behind the pause screen.
bool paused = screenManager()->topScreen() != this;
if (paused) {
// If we're paused and PauseScreen is transparent (will only be in buffered rendering mode), we just copy display to output.
thin3d->BindFramebufferAsRenderTarget(nullptr, { RPAction::CLEAR, RPAction::DONT_CARE, RPAction::DONT_CARE }, "EmuScreen_Paused");
if (PSP_IsInited()) {
gpu->CopyDisplayToOutput(true);
}
return;
}
if (invalid_) {
// Loading, or after shutdown?
if (loadingTextView_->GetVisibility() == UI::V_VISIBLE)

View File

@ -364,6 +364,24 @@ GamePauseScreen::~GamePauseScreen() {
__DisplaySetWasPaused();
}
bool GamePauseScreen::isTransparent() const {
// We don't support transparent pause screen in skipbuffereffects mode.
return !g_Config.bSkipBufferEffects && !IsVREnabled();
}
void GamePauseScreen::DrawBackground(UIContext &dc) {
if (isTransparent()) {
// Darken the game screen coming from below, so the UI on top stands out.
dc.Flush();
uint32_t color = blackAlpha(0.45f);
dc.FillRect(UI::Drawable(color), dc.GetBounds());
dc.Flush();
return;
}
UIDialogScreenWithGameBackground::DrawBackground(dc);
}
void GamePauseScreen::CreateViews() {
static const int NUM_SAVESLOTS = 5;

View File

@ -31,15 +31,18 @@ public:
GamePauseScreen(const Path &filename) : UIDialogScreenWithGameBackground(filename), gamePath_(filename) {}
virtual ~GamePauseScreen();
virtual void dialogFinished(const Screen *dialog, DialogResult dr) override;
void dialogFinished(const Screen *dialog, DialogResult dr) override;
const char *tag() const override { return "GamePause"; }
protected:
virtual void CreateViews() override;
virtual void update() override;
void CreateViews() override;
void update() override;
void CallbackDeleteConfig(bool yes);
bool isTransparent() const override;
void DrawBackground(UIContext &dc) override;
private:
UI::EventReturn OnGameSettings(UI::EventParams &e);
UI::EventReturn OnExitToMenu(UI::EventParams &e);