Skip to content

Commit

Permalink
Add custom error display for platforms
Browse files Browse the repository at this point in the history
Implemented currently for 3DS and SDL2. Switch and Vita are possible,
however an Error report might be generated on Switch (bad, could get
send to big N) and for Vita one would need to match framebuffer format
and such when dealing with GXM for dialog display. This is not worth
currently, since we likely migrate away from vita2d library in the
future.
Go through platform teardown code. While this may not work for every
case (e.g. out of memory on Wii), this should be cleaner.
  • Loading branch information
carstene1ns committed Mar 30, 2024
1 parent 4bdfb75 commit 8eb1ff5
Show file tree
Hide file tree
Showing 16 changed files with 140 additions and 24 deletions.
1 change: 1 addition & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,7 @@ add_library(${PROJECT_NAME} OBJECT
src/instrumentation.cpp
src/instrumentation.h
src/keys.h
src/main.h
src/main_data.cpp
src/main_data.h
src/maniac_patch.cpp
Expand Down
1 change: 1 addition & 0 deletions Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,7 @@ libeasyrpg_player_a_SOURCES = \
src/instrumentation.cpp \
src/instrumentation.h \
src/keys.h \
src/main.h \
src/main_data.cpp \
src/main_data.h \
src/maniac_patch.cpp \
Expand Down
8 changes: 8 additions & 0 deletions src/baseui.h
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,14 @@ class BaseUi {
*/
virtual bool ShowCursor(bool /* flag */) { return true; };

/**
* Outputs the error message in a custom way depending on platform
*
* @param message message string.
* @return wether error has been handled
*/
virtual bool HandleErrorOutput(const std::string & /* message */) { return false; }

/**
* Gets if fullscreen mode is active.
*
Expand Down
33 changes: 33 additions & 0 deletions src/main.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/*
* This file is part of EasyRPG Player.
*
* EasyRPG Player 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.
*
* EasyRPG Player 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 EasyRPG Player. If not, see <http://www.gnu.org/licenses/>.
*/

#ifndef EP_MAIN_H
#define EP_MAIN_H

namespace Platform {

/**
* Run Platform teardown code and set return status code when
* program terminates.
*
* @param without_error Whether to set an error exit code
*/
int Exit(bool without_error = true);

}

#endif
27 changes: 13 additions & 14 deletions src/output.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,6 @@
#include <fmt/ostream.h>
#ifdef EMSCRIPTEN
# include "platform/emscripten/interface.h"
#elif defined(__vita__)
# include <psp2/kernel/processmgr.h>
#endif

#include "output.h"
Expand All @@ -42,6 +40,7 @@
#include "message_overlay.h"
#include "font.h"
#include "baseui.h"
#include "main.h"

// fmt 7 has renamed the namespace
#if FMT_VERSION < 70000
Expand Down Expand Up @@ -203,10 +202,7 @@ static void HandleErrorOutput(const std::string& err) {
BitmapRef surface = DisplayUi->GetDisplaySurface();
surface->FillRect(surface->GetRect(), Color(255, 0, 0, 128));

std::string error = "Error:\n";
error += err;

error += "\n\nEasyRPG Player will close now.\nPress [ENTER] key to exit...";
std::string error = err + "\nPress [ENTER] key to exit...";

Text::Draw(*surface, 11, 11, *Font::DefaultBitmapFont(), Color(0, 0, 0, 255), error);
Text::Draw(*surface, 10, 10, *Font::DefaultBitmapFont(), Color(255, 255, 255, 255), error);
Expand Down Expand Up @@ -294,16 +290,18 @@ void Output::ToggleLog() {

void Output::ErrorStr(std::string const& err) {
WriteLog(LogLevel::Error, err);
std::string error = "Error:\n" + err + "\n\nEasyRPG Player will close now.";

static bool recursive_call = false;
if (!recursive_call && DisplayUi) {
recursive_call = true;
HandleErrorOutput(err);
// Try platform handler first
if (!DisplayUi->HandleErrorOutput(error))
HandleErrorOutput(error);
DisplayUi.reset();
} else {
// Fallback to Console if the display is not ready yet
std::cout << err << std::endl;
std::cout << std::endl;
std::cout << "EasyRPG Player will close now.";
std::cout << error << std::endl;
#if defined (PLAYER_NINTENDO) || defined(__vita__)
// stdin is non-blocking
Game_Clock::SleepFor(5s);
Expand All @@ -316,11 +314,12 @@ void Output::ErrorStr(std::string const& err) {
#endif
}

// FIXME: This does not go through platform teardown code
#ifdef __vita__
sceKernelExitProcess(EXIT_FAILURE);
#endif
#ifdef USE_LIBRETRO
// FIXME
exit(EXIT_FAILURE);
#else
exit(Platform::Exit(false));
#endif
}

void Output::WarningStr(std::string const& warn) {
Expand Down
9 changes: 8 additions & 1 deletion src/platform/3ds/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
#include <cstdio>

#include "player.h"
#include "main.h"
#include <string>
#include <sys/stat.h>
#include <unistd.h>
Expand Down Expand Up @@ -178,6 +179,11 @@ int main(int argc, char* argv[]) {
Player::Init(std::move(args));
Player::Run();

// Close
return Platform::Exit();
}

int Platform::Exit(bool without_error) {
romfsExit();
stop3DSLink();
gfxExit();
Expand All @@ -186,5 +192,6 @@ int main(int argc, char* argv[]) {
APT_SetAppCpuTimeLimit(old_time_limit);
}

return EXIT_SUCCESS;
if(without_error) return EXIT_SUCCESS;
return EXIT_FAILURE;
}
12 changes: 12 additions & 0 deletions src/platform/3ds/ui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -428,3 +428,15 @@ void CtrUi::vGetConfig(Game_ConfigVideo& cfg) const {
cfg.touch_ui.SetDescription("Toggle the backlight of the bottom screen");
cfg.touch_ui.Set(bottom_state != screen_state::off);
}

bool CtrUi::HandleErrorOutput(const std::string &message) {
errorConf errCnf;
std::string error = Player::GetFullVersionString();
error += "\n\n" + message;

errorInit(&errCnf, ERROR_TEXT_WORD_WRAP, CFG_LANGUAGE_EN);
errorText(&errCnf, error.c_str());
errorDisp(&errCnf);

return true;
}
1 change: 1 addition & 0 deletions src/platform/3ds/ui.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ class CtrUi final : public BaseUi {
void ToggleStretch() override;
void ToggleTouchUi() override;
void vGetConfig(Game_ConfigVideo& cfg) const override;
bool HandleErrorOutput(const std::string &message) override;

#ifdef SUPPORT_AUDIO
AudioInterface& GetAudio();
Expand Down
12 changes: 10 additions & 2 deletions src/platform/psvita/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
#include <psp2/appmgr.h>
#include "player.h"
#include "output.h"
#include "main.h"

int _newlib_heap_size_user = 330 * 1024 * 1024;

Expand Down Expand Up @@ -107,6 +108,13 @@ int main(int argc, char* argv[]) {
Player::Run();

// Close
sceKernelExitProcess(EXIT_SUCCESS);
return EXIT_SUCCESS;
return Platform::Exit();
}

int Platform::Exit(bool without_error) {
if(without_error) return sceKernelExitProcess(EXIT_SUCCESS);
sceKernelExitProcess(EXIT_FAILURE);

// Does not matter
return 0;
}
9 changes: 8 additions & 1 deletion src/platform/sdl/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include "player.h"
#include "utils.h"
#include "output.h"
#include "main.h"

#ifdef USE_SDL // This is needed on Windows, SDL wraps main()
# include <SDL.h>
Expand Down Expand Up @@ -86,5 +87,11 @@ extern "C" int main(int argc, char* argv[]) {
Player::Init(std::move(args));
Player::Run();

return EXIT_SUCCESS;
// Close
return Platform::Exit();
}

int Platform::Exit(bool without_error) {
if(without_error) return EXIT_SUCCESS;
return EXIT_FAILURE;
}
18 changes: 18 additions & 0 deletions src/platform/sdl/sdl2_ui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -656,6 +656,24 @@ bool Sdl2Ui::ShowCursor(bool flag) {
#endif
}

bool Sdl2Ui::HandleErrorOutput(const std::string &message) {
std::string title = Player::GetFullVersionString();

// Manually Restore window from fullscreen, since message would not be visible otherwise
if ((current_display_mode.flags & SDL_WINDOW_FULLSCREEN_DESKTOP)
== SDL_WINDOW_FULLSCREEN_DESKTOP) {
SDL_SetWindowFullscreen(sdl_window, 0);
SDL_SetWindowSize(sdl_window, 0, 0);
}

if(SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, title.c_str(),
message.c_str(), sdl_window) != 0) {
return false;
}

return true;
}

void Sdl2Ui::ProcessEvent(SDL_Event &evnt) {
switch (evnt.type) {
case SDL_WINDOWEVENT:
Expand Down
1 change: 1 addition & 0 deletions src/platform/sdl/sdl2_ui.h
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ class Sdl2Ui final : public BaseUi {
void ToggleVsync() override;
void vGetConfig(Game_ConfigVideo& cfg) const override;
Rect GetWindowMetrics() const override;
bool HandleErrorOutput(const std::string &message) override;

#ifdef SUPPORT_AUDIO
AudioInterface& GetAudio() override;
Expand Down
12 changes: 10 additions & 2 deletions src/platform/switch/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include <vector>
#include "player.h"
#include "output.h"
#include "main.h"

namespace {
int nxlinkSocket = -1;
Expand Down Expand Up @@ -48,7 +49,7 @@ int main(int argc, char* argv[]) {

appletLockExit();

// yuzu/nso
// suyu/nso
is_nro = envHasArgv();
Output::SetLogCallback(LogCallback);

Expand Down Expand Up @@ -89,6 +90,11 @@ int main(int argc, char* argv[]) {
Player::Init(std::move(args));
Player::Run();

// Close
return Platform::Exit();
}

int Platform::Exit(bool without_error) {
romfsExit();

// Close debug log
Expand All @@ -101,5 +107,7 @@ int main(int argc, char* argv[]) {
// HOS will close us immediately afterwards, if requested by home menu.
// So no further cleanup possible.
appletUnlockExit();
return EXIT_SUCCESS;

if(without_error) return EXIT_SUCCESS;
return EXIT_FAILURE;
}
8 changes: 7 additions & 1 deletion src/platform/wii/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -114,5 +114,11 @@ extern "C" int main(int argc, char* argv[]) {
Player::Init(std::move(args));
Player::Run();

return EXIT_SUCCESS;
// Close
return Platform::Exit();
}

int Platform::Exit(bool without_error) {
if(without_error) return EXIT_SUCCESS;
return EXIT_FAILURE;
}
5 changes: 2 additions & 3 deletions src/player.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -106,9 +106,8 @@ namespace Player {
int menu_offset_y = (screen_height - MENU_HEIGHT) / 2;
int message_box_offset_x = (screen_width - MENU_WIDTH) / 2;
bool has_custom_resolution = false;

bool exit_flag;
bool reset_flag;
bool exit_flag = false;
bool reset_flag = false;
bool debug_flag;
bool hide_title_flag;
int load_game_id;
Expand Down
7 changes: 7 additions & 0 deletions tests/test_main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@
#include <emscripten.h>
#endif

#include "main.h"

int main(int argc, char** argv) {
#ifdef EMSCRIPTEN
EM_ASM({
Expand All @@ -21,3 +23,8 @@ int main(int argc, char** argv) {

return doctest::Context(argc, argv).run();
}

int Platform::Exit(bool) {
// Empty on purpose
return 0;
}

0 comments on commit 8eb1ff5

Please sign in to comment.