diff --git a/include/PICA/gpu.hpp b/include/PICA/gpu.hpp index 0bf5941b..2336493c 100644 --- a/include/PICA/gpu.hpp +++ b/include/PICA/gpu.hpp @@ -88,6 +88,7 @@ class GPU { GPU(Memory& mem, EmulatorConfig& config); void display() { renderer->display(); } void screenshot(const std::string& name) { renderer->screenshot(name); } + void deinitGraphicsContext() { renderer->deinitGraphicsContext(); } #if defined(PANDA3DS_FRONTEND_SDL) void initGraphicsContext(SDL_Window* window) { renderer->initGraphicsContext(window); } diff --git a/include/emulator.hpp b/include/emulator.hpp index a5b1d768..2b96b0cf 100644 --- a/include/emulator.hpp +++ b/include/emulator.hpp @@ -112,6 +112,7 @@ class Emulator { RomFS::DumpingResult dumpRomFS(const std::filesystem::path& path); void setOutputSize(u32 width, u32 height) { gpu.setOutputSize(width, height); } + void deinitGraphicsContext() { gpu.deinitGraphicsContext(); } EmulatorConfig& getConfig() { return config; } ServiceManager& getServiceManager() { return kernel.getServiceManager(); } diff --git a/include/renderer.hpp b/include/renderer.hpp index 10890e56..8888b41e 100644 --- a/include/renderer.hpp +++ b/include/renderer.hpp @@ -62,6 +62,9 @@ class Renderer { virtual void drawVertices(PICA::PrimType primType, std::span vertices) = 0; // Draw the given vertices virtual void screenshot(const std::string& name) = 0; + // Some frontends and platforms may require that we delete our GL or misc context and obtain a new one for things like exclusive fullscreen + // This function does things like write back or cache necessary state before we delete our context + virtual void deinitGraphicsContext() = 0; // Functions for initializing the graphics context for the Qt frontend, where we don't have the convenience of SDL_Window #ifdef PANDA3DS_FRONTEND_QT diff --git a/include/renderer_gl/renderer_gl.hpp b/include/renderer_gl/renderer_gl.hpp index 07f91dcd..92f02662 100644 --- a/include/renderer_gl/renderer_gl.hpp +++ b/include/renderer_gl/renderer_gl.hpp @@ -81,7 +81,8 @@ class RendererGL final : public Renderer { void displayTransfer(u32 inputAddr, u32 outputAddr, u32 inputSize, u32 outputSize, u32 flags) override; // Perform display transfer void textureCopy(u32 inputAddr, u32 outputAddr, u32 totalBytes, u32 inputSize, u32 outputSize, u32 flags) override; void drawVertices(PICA::PrimType primType, std::span vertices) override; // Draw the given vertices - + void deinitGraphicsContext() override; + std::optional getColourBuffer(u32 addr, PICA::ColorFmt format, u32 width, u32 height, bool createIfnotFound = true); // Note: The caller is responsible for deleting the currently bound FBO before calling this diff --git a/include/renderer_null/renderer_null.hpp b/include/renderer_null/renderer_null.hpp index 79d60ba6..bd8f17df 100644 --- a/include/renderer_null/renderer_null.hpp +++ b/include/renderer_null/renderer_null.hpp @@ -15,6 +15,7 @@ class RendererNull final : public Renderer { void textureCopy(u32 inputAddr, u32 outputAddr, u32 totalBytes, u32 inputSize, u32 outputSize, u32 flags) override; void drawVertices(PICA::PrimType primType, std::span vertices) override; void screenshot(const std::string& name) override; + void deinitGraphicsContext() override; #ifdef PANDA3DS_FRONTEND_QT virtual void initGraphicsContext([[maybe_unused]] GL::Context* context) override {} diff --git a/include/renderer_sw/renderer_sw.hpp b/include/renderer_sw/renderer_sw.hpp index e944c16c..dd12bf0a 100644 --- a/include/renderer_sw/renderer_sw.hpp +++ b/include/renderer_sw/renderer_sw.hpp @@ -15,6 +15,7 @@ class RendererSw final : public Renderer { void textureCopy(u32 inputAddr, u32 outputAddr, u32 totalBytes, u32 inputSize, u32 outputSize, u32 flags) override; void drawVertices(PICA::PrimType primType, std::span vertices) override; void screenshot(const std::string& name) override; + void deinitGraphicsContext() override; #ifdef PANDA3DS_FRONTEND_QT virtual void initGraphicsContext([[maybe_unused]] GL::Context* context) override {} diff --git a/include/renderer_vk/renderer_vk.hpp b/include/renderer_vk/renderer_vk.hpp index 92007674..25cc26f8 100644 --- a/include/renderer_vk/renderer_vk.hpp +++ b/include/renderer_vk/renderer_vk.hpp @@ -119,4 +119,5 @@ class RendererVK final : public Renderer { void textureCopy(u32 inputAddr, u32 outputAddr, u32 totalBytes, u32 inputSize, u32 outputSize, u32 flags) override; void drawVertices(PICA::PrimType primType, std::span vertices) override; void screenshot(const std::string& name) override; + void deinitGraphicsContext() override; }; diff --git a/src/core/renderer_gl/renderer_gl.cpp b/src/core/renderer_gl/renderer_gl.cpp index a3743126..a11a6ffa 100644 --- a/src/core/renderer_gl/renderer_gl.cpp +++ b/src/core/renderer_gl/renderer_gl.cpp @@ -801,4 +801,15 @@ void RendererGL::screenshot(const std::string& name) { } stbi_write_png(name.c_str(), width, height, 4, flippedPixels.data(), 0); +} + +void RendererGL::deinitGraphicsContext() { + // Invalidate all surface caches since they'll no longer be valid + textureCache.reset(); + depthBufferCache.reset(); + colourBufferCache.reset(); + + // All other GL objects should be invalidated automatically and be recreated by the next call to initGraphicsContext + // TODO: Make it so that depth and colour buffers get written back to 3DS memory + printf("RendererGL::DeinitGraphicsContext called\n"); } \ No newline at end of file diff --git a/src/core/renderer_null/renderer_null.cpp b/src/core/renderer_null/renderer_null.cpp index b2ebd1d6..4be9d089 100644 --- a/src/core/renderer_null/renderer_null.cpp +++ b/src/core/renderer_null/renderer_null.cpp @@ -12,3 +12,4 @@ void RendererNull::displayTransfer(u32 inputAddr, u32 outputAddr, u32 inputSize, void RendererNull::textureCopy(u32 inputAddr, u32 outputAddr, u32 totalBytes, u32 inputSize, u32 outputSize, u32 flags) {} void RendererNull::drawVertices(PICA::PrimType primType, std::span vertices) {} void RendererNull::screenshot(const std::string& name) {} +void RendererNull::deinitGraphicsContext() {} \ No newline at end of file diff --git a/src/core/renderer_sw/renderer_sw.cpp b/src/core/renderer_sw/renderer_sw.cpp index b671c180..86b6032f 100644 --- a/src/core/renderer_sw/renderer_sw.cpp +++ b/src/core/renderer_sw/renderer_sw.cpp @@ -23,3 +23,4 @@ void RendererSw::drawVertices(PICA::PrimType primType, std::span