mirror of
https://github.com/izzy2lost/WeeU.git
synced 2026-07-06 00:19:59 -07:00
Remove guiWrapper from gui project & replace all functions with callbacks
This commit is contained in:
@@ -490,7 +490,6 @@ target_link_libraries(CemuCafe PRIVATE
|
||||
CemuCommon
|
||||
CemuComponents
|
||||
CemuConfig
|
||||
CemuGui
|
||||
CemuInput
|
||||
CemuResource
|
||||
CemuUtil
|
||||
|
||||
+20
-5
@@ -64,9 +64,6 @@
|
||||
// HW interfaces
|
||||
#include "Cafe/HW/SI/si.h"
|
||||
|
||||
// dependency to be removed
|
||||
#include "gui/guiWrapper.h"
|
||||
|
||||
std::string _pathToExecutable;
|
||||
std::string _pathToBaseExecutable;
|
||||
|
||||
@@ -354,7 +351,9 @@ uint32 loadSharedData()
|
||||
|
||||
void cemu_initForGame()
|
||||
{
|
||||
gui_updateWindowTitles(false, true, 0.0);
|
||||
auto cafeSystemCallbacks = CafeSystem::getCafeSystemCallbacks();
|
||||
if (cafeSystemCallbacks)
|
||||
cafeSystemCallbacks->updateWindowTitles(false, true, 0.0);
|
||||
// input manager apply game profile
|
||||
InputManager::instance().apply_game_profile();
|
||||
// log info for launched title
|
||||
@@ -443,6 +442,20 @@ void cemu_deinitForGame()
|
||||
|
||||
namespace CafeSystem
|
||||
{
|
||||
CafeSystemCallbacks* sCafeSystemCallbacks = nullptr;
|
||||
void registerCafeSystemCallbacks(CafeSystemCallbacks* cafeSystemCallbacks)
|
||||
{
|
||||
sCafeSystemCallbacks = cafeSystemCallbacks;
|
||||
}
|
||||
void unregisterCafeSystemCallbacks()
|
||||
{
|
||||
sCafeSystemCallbacks = nullptr;
|
||||
}
|
||||
CafeSystemCallbacks* getCafeSystemCallbacks()
|
||||
{
|
||||
return sCafeSystemCallbacks;
|
||||
}
|
||||
|
||||
void InitVirtualMlcStorage();
|
||||
void MlcStorageMountTitle(TitleInfo& titleInfo);
|
||||
|
||||
@@ -679,7 +692,9 @@ namespace CafeSystem
|
||||
PPCTimer_waitForInit();
|
||||
// start system
|
||||
sSystemRunning = true;
|
||||
gui_notifyGameLoaded();
|
||||
auto cafeSystemCallbacks = CafeSystem::getCafeSystemCallbacks();
|
||||
if (cafeSystemCallbacks)
|
||||
cafeSystemCallbacks->notifyGameLoaded();
|
||||
std::thread t(_LaunchTitleThread);
|
||||
t.detach();
|
||||
}
|
||||
|
||||
@@ -14,6 +14,17 @@ namespace CafeSystem
|
||||
//BAD_META_DATA, - the title list only stores titles with valid meta, so this error code is impossible
|
||||
};
|
||||
|
||||
class CafeSystemCallbacks
|
||||
{
|
||||
public:
|
||||
virtual void updateWindowTitles(bool isIdle, bool isLoading, double fps) = 0;
|
||||
virtual void notifyGameLoaded() = 0;
|
||||
};
|
||||
|
||||
void registerCafeSystemCallbacks(CafeSystemCallbacks* cafeSystemCallbacks);
|
||||
void unregisterCafeSystemCallbacks();
|
||||
CafeSystemCallbacks* getCafeSystemCallbacks();
|
||||
|
||||
void Initialize();
|
||||
STATUS_CODE PrepareForegroundTitle(TitleId titleId);
|
||||
STATUS_CODE PrepareForegroundTitleFromStandaloneRPX(const fs::path& path);
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Debugger.h"
|
||||
#include "Cemu/PPCAssembler/ppcAssembler.h"
|
||||
#include "Cafe/HW/Espresso/Recompiler/PPCRecompiler.h"
|
||||
@@ -12,6 +11,21 @@
|
||||
|
||||
debuggerState_t debuggerState{ };
|
||||
|
||||
DebuggerCallbacks* sDebuggerCallbacks = nullptr;
|
||||
|
||||
void debugger_registerDebuggerCallbacks(DebuggerCallbacks* debuggerCallbacks)
|
||||
{
|
||||
sDebuggerCallbacks = debuggerCallbacks;
|
||||
}
|
||||
void debugger_unregisterDebuggerCallbacks()
|
||||
{
|
||||
sDebuggerCallbacks = nullptr;
|
||||
}
|
||||
DebuggerCallbacks* debugger_getDebuggerCallbacks()
|
||||
{
|
||||
return sDebuggerCallbacks;
|
||||
}
|
||||
|
||||
DebuggerBreakpoint* debugger_getFirstBP(uint32 address)
|
||||
{
|
||||
for (auto& it : debuggerState.breakpoints)
|
||||
@@ -329,7 +343,8 @@ void debugger_toggleBreakpoint(uint32 address, bool state, DebuggerBreakpoint* b
|
||||
{
|
||||
bp->enabled = state;
|
||||
debugger_updateExecutionBreakpoint(address);
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
}
|
||||
else if (bpItr->isMemBP())
|
||||
{
|
||||
@@ -351,7 +366,8 @@ void debugger_toggleBreakpoint(uint32 address, bool state, DebuggerBreakpoint* b
|
||||
debugger_updateMemoryBreakpoint(bpItr);
|
||||
else
|
||||
debugger_updateMemoryBreakpoint(nullptr);
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
}
|
||||
return;
|
||||
}
|
||||
@@ -459,8 +475,8 @@ void debugger_stepInto(PPCInterpreter_t* hCPU, bool updateDebuggerWindow = true)
|
||||
PPCInterpreterSlim_executeInstruction(hCPU);
|
||||
debugger_updateExecutionBreakpoint(initialIP);
|
||||
debuggerState.debugSession.instructionPointer = hCPU->instructionPointer;
|
||||
if(updateDebuggerWindow)
|
||||
debuggerWindow_moveIP();
|
||||
if(updateDebuggerWindow && sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->moveIP();
|
||||
ppcRecompilerEnabled = isRecEnabled;
|
||||
}
|
||||
|
||||
@@ -479,7 +495,8 @@ bool debugger_stepOver(PPCInterpreter_t* hCPU)
|
||||
// nothing to skip, use step-into
|
||||
debugger_stepInto(hCPU);
|
||||
debugger_updateExecutionBreakpoint(initialIP);
|
||||
debuggerWindow_moveIP();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->moveIP();
|
||||
ppcRecompilerEnabled = isRecEnabled;
|
||||
return false;
|
||||
}
|
||||
@@ -487,7 +504,8 @@ bool debugger_stepOver(PPCInterpreter_t* hCPU)
|
||||
debugger_createSingleShotExecuteBreakpoint(initialIP +4);
|
||||
// step over current instruction (to avoid breakpoint)
|
||||
debugger_stepInto(hCPU);
|
||||
debuggerWindow_moveIP();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->moveIP();
|
||||
// restore breakpoints
|
||||
debugger_updateExecutionBreakpoint(initialIP);
|
||||
// run
|
||||
@@ -515,8 +533,11 @@ void debugger_enterTW(PPCInterpreter_t* hCPU)
|
||||
DebuggerBreakpoint* singleshotBP = debugger_getFirstBP(debuggerState.debugSession.instructionPointer, DEBUGGER_BP_T_ONE_SHOT);
|
||||
if (singleshotBP)
|
||||
debugger_deleteBreakpoint(singleshotBP);
|
||||
debuggerWindow_notifyDebugBreakpointHit2();
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
if (sDebuggerCallbacks)
|
||||
{
|
||||
sDebuggerCallbacks->notifyDebugBreakpointHit();
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
}
|
||||
// reset step control
|
||||
debuggerState.debugSession.stepInto = false;
|
||||
debuggerState.debugSession.stepOver = false;
|
||||
@@ -533,14 +554,16 @@ void debugger_enterTW(PPCInterpreter_t* hCPU)
|
||||
break; // if true is returned, continue with execution
|
||||
}
|
||||
debugger_createPPCStateSnapshot(hCPU);
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
debuggerState.debugSession.stepOver = false;
|
||||
}
|
||||
if (debuggerState.debugSession.stepInto)
|
||||
{
|
||||
debugger_stepInto(hCPU);
|
||||
debugger_createPPCStateSnapshot(hCPU);
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
if (sDebuggerCallbacks)
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
debuggerState.debugSession.stepInto = false;
|
||||
continue;
|
||||
}
|
||||
@@ -557,8 +580,11 @@ void debugger_enterTW(PPCInterpreter_t* hCPU)
|
||||
|
||||
debuggerState.debugSession.isTrapped = false;
|
||||
debuggerState.debugSession.hCPU = nullptr;
|
||||
debuggerWindow_updateViewThreadsafe2();
|
||||
debuggerWindow_notifyRun();
|
||||
if (sDebuggerCallbacks)
|
||||
{
|
||||
sDebuggerCallbacks->updateViewThreadsafe();
|
||||
sDebuggerCallbacks->notifyRun();
|
||||
}
|
||||
}
|
||||
|
||||
void debugger_shouldBreak(PPCInterpreter_t* hCPU)
|
||||
|
||||
@@ -97,6 +97,21 @@ typedef struct
|
||||
extern debuggerState_t debuggerState;
|
||||
|
||||
// new API
|
||||
class DebuggerCallbacks
|
||||
{
|
||||
public:
|
||||
virtual void updateViewThreadsafe() = 0;
|
||||
virtual void notifyDebugBreakpointHit() = 0;
|
||||
virtual void notifyRun() = 0;
|
||||
virtual void moveIP() = 0;
|
||||
virtual void notifyModuleLoaded(void* module) = 0;
|
||||
virtual void notifyModuleUnloaded(void* module) = 0;
|
||||
};
|
||||
|
||||
void debugger_registerDebuggerCallbacks(DebuggerCallbacks* debuggerCallbacks);
|
||||
void debugger_unregisterDebuggerCallbacks();
|
||||
DebuggerCallbacks* debugger_getDebuggerCallbacks();
|
||||
|
||||
DebuggerBreakpoint* debugger_getFirstBP(uint32 address);
|
||||
void debugger_toggleExecuteBreakpoint(uint32 address); // create/remove execute breakpoint
|
||||
void debugger_createExecuteBreakpoint(uint32 address);
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Cafe/HW/Latte/Core/LatteOverlay.h"
|
||||
#include "Cafe/HW/Latte/Core/LattePerformanceMonitor.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
|
||||
#include "config/CemuConfig.h"
|
||||
|
||||
@@ -14,6 +13,8 @@
|
||||
#include "input/InputManager.h"
|
||||
#include "util/SystemInfo/SystemInfo.h"
|
||||
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
#include <cinttypes>
|
||||
|
||||
struct OverlayStats
|
||||
@@ -512,17 +513,17 @@ void LatteOverlay_render(bool pad_view)
|
||||
return;
|
||||
|
||||
sint32 w = 0, h = 0;
|
||||
if (pad_view && gui_isPadWindowOpen())
|
||||
gui_getPadWindowPhysSize(w, h);
|
||||
if (pad_view && GuiSystem::isPadWindowOpen())
|
||||
GuiSystem::getPadWindowPhysSize(w, h);
|
||||
else
|
||||
gui_getWindowPhysSize(w, h);
|
||||
GuiSystem::getWindowPhysSize(w, h);
|
||||
|
||||
if (w == 0 || h == 0)
|
||||
return;
|
||||
|
||||
const Vector2f window_size{ (float)w,(float)h };
|
||||
|
||||
float fontDPIScale = !pad_view ? gui_getWindowDPIScale() : gui_getPadDPIScale();
|
||||
float fontDPIScale = !pad_view ? GuiSystem::getWindowDPIScale() : GuiSystem::getPadDPIScale();
|
||||
|
||||
float overlayFontSize = 14.0f * (float)config.overlay.text_scale / 100.0f * fontDPIScale;
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#include "Cafe/HW/Latte/Core/LattePerformanceMonitor.h"
|
||||
#include "Cafe/HW/Latte/Core/LatteOverlay.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cafe/CafeSystem.h"
|
||||
|
||||
performanceMonitor_t performanceMonitor{};
|
||||
|
||||
@@ -102,15 +102,18 @@ void LattePerformanceMonitor_frameEnd()
|
||||
// next update in 1 second
|
||||
performanceMonitor.cycle[performanceMonitor.cycleIndex].lastUpdate = GetTickCount();
|
||||
|
||||
auto cafeSystemCallbacks = CafeSystem::getCafeSystemCallbacks();
|
||||
if (isFirstUpdate)
|
||||
{
|
||||
LatteOverlay_updateStats(0.0, 0);
|
||||
gui_updateWindowTitles(false, false, 0.0);
|
||||
if (cafeSystemCallbacks)
|
||||
cafeSystemCallbacks->updateWindowTitles(false, false, 0.0);
|
||||
}
|
||||
else
|
||||
{
|
||||
LatteOverlay_updateStats(fps, drawCallCounter / elapsedFrames);
|
||||
gui_updateWindowTitles(false, false, fps);
|
||||
if (cafeSystemCallbacks)
|
||||
cafeSystemCallbacks->updateWindowTitles(false, false, fps);
|
||||
}
|
||||
}
|
||||
LatteOverlay_updateStatsPerFrame();
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
#include "Cafe/GraphicPack/GraphicPack2.h"
|
||||
#include "config/ActiveSettings.h"
|
||||
#include "Cafe/HW/Latte/Renderer/Vulkan/VulkanRenderer.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
#include "Cafe/OS/libs/erreula/erreula.h"
|
||||
#include "input/InputManager.h"
|
||||
#include "Cafe/OS/libs/swkbd/swkbd.h"
|
||||
@@ -846,10 +846,10 @@ sint32 _currentOutputImageHeight = 0;
|
||||
void LatteRenderTarget_getScreenImageArea(sint32* x, sint32* y, sint32* width, sint32* height, sint32* fullWidth, sint32* fullHeight, bool padView)
|
||||
{
|
||||
int w, h;
|
||||
if(padView && gui_isPadWindowOpen())
|
||||
gui_getPadWindowPhysSize(w, h);
|
||||
if(padView && GuiSystem::isPadWindowOpen())
|
||||
GuiSystem::getPadWindowPhysSize(w, h);
|
||||
else
|
||||
gui_getWindowPhysSize(w, h);
|
||||
GuiSystem::getWindowPhysSize(w, h);
|
||||
|
||||
sint32 scaledOutputX;
|
||||
sint32 scaledOutputY;
|
||||
@@ -1014,8 +1014,8 @@ void LatteRenderTarget_itHLECopyColorBufferToScanBuffer(MPTR colorBufferPtr, uin
|
||||
return;
|
||||
}
|
||||
|
||||
const bool tabPressed = gui_isKeyDown(PlatformKeyCodes::TAB);
|
||||
const bool ctrlPressed = gui_isKeyDown(PlatformKeyCodes::LCONTROL);
|
||||
const bool tabPressed = GuiSystem::isKeyDown(GuiSystem::PlatformKeyCodes::TAB);
|
||||
const bool ctrlPressed = GuiSystem::isKeyDown(GuiSystem::PlatformKeyCodes::LCONTROL);
|
||||
|
||||
bool showDRC = swkbd_hasKeyboardInputHook() == false && tabPressed;
|
||||
bool& alwaysDisplayDRC = LatteGPUState.alwaysDisplayDRC;
|
||||
|
||||
@@ -4,9 +4,9 @@
|
||||
#include "Cafe/HW/Latte/Core/LatteShader.h"
|
||||
#include "Cafe/HW/Latte/LegacyShaderDecompiler/LatteDecompiler.h"
|
||||
#include "Cafe/HW/Latte/Core/FetchShader.h"
|
||||
#include "Cemu/FileCache/FileCache.h"
|
||||
#include "Cafe/GameProfile/GameProfile.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cemu/FileCache/FileCache.h"
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
#include "Cafe/HW/Latte/Renderer/Renderer.h"
|
||||
#include "Cafe/HW/Latte/Renderer/OpenGL/RendererShaderGL.h"
|
||||
@@ -379,7 +379,7 @@ void LatteShaderCache_ShowProgress(const std::function <bool(void)>& loadUpdateF
|
||||
continue;
|
||||
|
||||
int w, h;
|
||||
gui_getWindowPhysSize(w, h);
|
||||
GuiSystem::getWindowPhysSize(w, h);
|
||||
const Vector2f window_size{ (float)w,(float)h };
|
||||
|
||||
ImGui_GetFont(window_size.y / 32.0f); // = 24 by default
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
#include "Cafe/HW/Latte/Core/LatteAsyncCommands.h"
|
||||
#include "Cafe/GameProfile/GameProfile.h"
|
||||
#include "Cafe/GraphicPack/GraphicPack2.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
#include "Cafe/HW/Latte/Core/LatteBufferCache.h"
|
||||
|
||||
@@ -117,7 +117,7 @@ int Latte_ThreadEntry()
|
||||
{
|
||||
SetThreadName("LatteThread");
|
||||
sint32 w,h;
|
||||
gui_getWindowPhysSize(w,h);
|
||||
GuiSystem::getWindowPhysSize(w,h);
|
||||
|
||||
// renderer
|
||||
g_renderer->Initialize();
|
||||
@@ -174,8 +174,7 @@ int Latte_ThreadEntry()
|
||||
|
||||
g_renderer->DrawEmptyFrame(true);
|
||||
g_renderer->DrawEmptyFrame(false);
|
||||
|
||||
gui_hasScreenshotRequest(); // keep the screenshot request queue empty
|
||||
g_renderer->CancelScreenshotRequest();
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(1000/60));
|
||||
}
|
||||
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
#include "Cafe/HW/Latte/Renderer/OpenGL/OpenGLRenderer.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
|
||||
#include "Cafe/HW/Latte/Core/LatteRingBuffer.h"
|
||||
#include "Cafe/HW/Latte/Core/LatteDraw.h"
|
||||
@@ -19,6 +18,8 @@
|
||||
#include "Cafe/HW/Latte/ISA/RegDefines.h"
|
||||
#include "Cafe/OS/libs/gx2/GX2.h"
|
||||
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
#include "GLCanvas.h"
|
||||
|
||||
#define STRINGIFY2(X) #X
|
||||
@@ -478,7 +479,7 @@ void OpenGLRenderer::ClearColorbuffer(bool padView)
|
||||
|
||||
void OpenGLRenderer::HandleScreenshotRequest(LatteTextureView* texView, bool padView)
|
||||
{
|
||||
const bool hasScreenshotRequest = gui_hasScreenshotRequest();
|
||||
const bool hasScreenshotRequest = std::exchange(m_screenshot_requested, false);
|
||||
if(!hasScreenshotRequest && m_screenshot_state == ScreenshotState::None)
|
||||
return;
|
||||
|
||||
@@ -562,9 +563,9 @@ void OpenGLRenderer::DrawBackbufferQuad(LatteTextureView* texView, RendererOutpu
|
||||
{
|
||||
int windowWidth, windowHeight;
|
||||
if (padView)
|
||||
gui_getPadWindowPhysSize(windowWidth, windowHeight);
|
||||
GuiSystem::getPadWindowPhysSize(windowWidth, windowHeight);
|
||||
else
|
||||
gui_getWindowPhysSize(windowWidth, windowHeight);
|
||||
GuiSystem::getWindowPhysSize(windowWidth, windowHeight);
|
||||
g_renderer->renderTarget_setViewport(0, 0, windowWidth, windowHeight, 0.0f, 1.0f);
|
||||
g_renderer->ClearColorbuffer(padView);
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
#include "Cafe/HW/Latte/Renderer/Renderer.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
#include "config/CemuConfig.h"
|
||||
#include "Cafe/HW/Latte/Core/LatteOverlay.h"
|
||||
@@ -65,9 +65,9 @@ bool Renderer::ImguiBegin(bool mainWindow)
|
||||
{
|
||||
sint32 w = 0, h = 0;
|
||||
if(mainWindow)
|
||||
gui_getWindowPhysSize(w, h);
|
||||
else if(gui_isPadWindowOpen())
|
||||
gui_getPadWindowPhysSize(w, h);
|
||||
GuiSystem::getWindowPhysSize(w, h);
|
||||
else if(GuiSystem::isPadWindowOpen())
|
||||
GuiSystem::getPadWindowPhysSize(w, h);
|
||||
else
|
||||
return false;
|
||||
|
||||
@@ -109,74 +109,29 @@ uint8 Renderer::RGBComponentToSRGB(uint8 cli)
|
||||
return (uint8)(cs * 255.0f);
|
||||
}
|
||||
|
||||
static std::optional<fs::path> GenerateScreenshotFilename(bool isDRC)
|
||||
void Renderer::RequestScreenshot(const std::function<std::optional<std::string>(const std::vector<uint8>&, int, int, bool)>& onSaveScreenshot)
|
||||
{
|
||||
fs::path screendir = ActiveSettings::GetUserDataPath("screenshots");
|
||||
// build screenshot name with format Screenshot_YYYY-MM-DD_HH-MM-SS[_GamePad].png
|
||||
// if the file already exists add a suffix counter (_2.png, _3.png etc)
|
||||
std::time_t time_t = std::chrono::system_clock::to_time_t(std::chrono::system_clock::now());
|
||||
std::tm* tm = std::localtime(&time_t);
|
||||
|
||||
std::string screenshotFileName = fmt::format("Screenshot_{:04}-{:02}-{:02}_{:02}-{:02}-{:02}", tm->tm_year+1900, tm->tm_mon+1, tm->tm_mday, tm->tm_hour, tm->tm_min, tm->tm_sec);
|
||||
if (isDRC)
|
||||
screenshotFileName.append("_GamePad");
|
||||
|
||||
fs::path screenshotPath;
|
||||
for(sint32 i=0; i<999; i++)
|
||||
{
|
||||
screenshotPath = screendir;
|
||||
if (i == 0)
|
||||
screenshotPath.append(fmt::format("{}.png", screenshotFileName));
|
||||
else
|
||||
screenshotPath.append(fmt::format("{}_{}.png", screenshotFileName, i + 1));
|
||||
|
||||
std::error_code ec;
|
||||
bool exists = fs::exists(screenshotPath, ec);
|
||||
|
||||
if (!ec && !exists)
|
||||
return screenshotPath;
|
||||
}
|
||||
return std::nullopt;
|
||||
m_screenshot_requested = true;
|
||||
m_on_save_screenshot = onSaveScreenshot;
|
||||
}
|
||||
|
||||
static void ScreenshotThread(std::vector<uint8> data, bool save_screenshot, int width, int height, bool mainWindow)
|
||||
void Renderer::CancelScreenshotRequest()
|
||||
{
|
||||
#if BOOST_OS_WINDOWS
|
||||
// on Windows wxWidgets uses OLE API for the clipboard
|
||||
// to make this work we need to call OleInitialize() on the same thread
|
||||
OleInitialize(nullptr);
|
||||
#endif
|
||||
|
||||
if (mainWindow)
|
||||
{
|
||||
if(gui_saveScreenshotToClipboard(data, width, height))
|
||||
{
|
||||
if (!save_screenshot)
|
||||
LatteOverlay_pushNotification("Screenshot saved to clipboard", 2500);
|
||||
}
|
||||
else
|
||||
{
|
||||
LatteOverlay_pushNotification("Failed to open clipboard", 2500);
|
||||
}
|
||||
}
|
||||
|
||||
if (save_screenshot)
|
||||
{
|
||||
auto imagePath = GenerateScreenshotFilename(mainWindow);
|
||||
if (imagePath.has_value() && gui_saveScreenshotToFile(imagePath.value(), data, width, height))
|
||||
{
|
||||
if (mainWindow)
|
||||
LatteOverlay_pushNotification("Screenshot saved", 2500);
|
||||
}
|
||||
else
|
||||
{
|
||||
LatteOverlay_pushNotification("Failed to save screenshot to file", 2500);
|
||||
}
|
||||
}
|
||||
m_screenshot_requested = false;
|
||||
m_on_save_screenshot = nullptr;
|
||||
}
|
||||
|
||||
void Renderer::SaveScreenshot(const std::vector<uint8>& rgb_data, int width, int height, bool mainWindow) const
|
||||
{
|
||||
const bool save_screenshot = GetConfig().save_screenshot;
|
||||
std::thread(ScreenshotThread, rgb_data, save_screenshot, width, height, mainWindow).detach();
|
||||
std::thread(
|
||||
[=, this]()
|
||||
{
|
||||
if (m_on_save_screenshot)
|
||||
{
|
||||
auto notificationMessage = m_on_save_screenshot(rgb_data, width, height, mainWindow);
|
||||
if (notificationMessage.has_value())
|
||||
LatteOverlay_pushNotification(notificationMessage.value(), 2500);
|
||||
}
|
||||
})
|
||||
.detach();
|
||||
}
|
||||
|
||||
@@ -67,6 +67,9 @@ public:
|
||||
virtual void DrawEmptyFrame(bool mainWindow) = 0;
|
||||
virtual void SwapBuffers(bool swapTV, bool swapDRC) = 0;
|
||||
|
||||
void RequestScreenshot(const std::function<std::optional<std::string>(const std::vector<uint8>&, int, int, bool)>& onSaveScreenshot);
|
||||
void CancelScreenshotRequest();
|
||||
|
||||
virtual void HandleScreenshotRequest(LatteTextureView* texView, bool padView){}
|
||||
|
||||
virtual void DrawBackbufferQuad(LatteTextureView* texView, RendererOutputShader* shader, bool useLinearTexFilter,
|
||||
@@ -172,6 +175,8 @@ protected:
|
||||
Pad,
|
||||
};
|
||||
ScreenshotState m_screenshot_state = ScreenshotState::None;
|
||||
bool m_screenshot_requested = false;
|
||||
std::function<std::optional<std::string>(const std::vector<uint8>&, int, int, bool)> m_on_save_screenshot;
|
||||
void SaveScreenshot(const std::vector<uint8>& rgb_data, int width, int height, bool mainWindow) const;
|
||||
|
||||
|
||||
|
||||
@@ -12,12 +12,12 @@
|
||||
|
||||
#include "Cafe/CafeSystem.h"
|
||||
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
#include "util/helpers/helpers.h"
|
||||
#include "util/helpers/StringHelpers.h"
|
||||
|
||||
#include "config/ActiveSettings.h"
|
||||
#include "config/CemuConfig.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
|
||||
#include "imgui/imgui_extension.h"
|
||||
#include "imgui/imgui_impl_vulkan.h"
|
||||
@@ -112,11 +112,11 @@ std::vector<VulkanRenderer::DeviceInfo> VulkanRenderer::GetDevices()
|
||||
#if __ANDROID__
|
||||
requiredExtensions.emplace_back(VK_KHR_ANDROID_SURFACE_EXTENSION_NAME);
|
||||
#else
|
||||
auto backend = gui_getWindowInfo().window_main.backend;
|
||||
if(backend == WindowHandleInfo::Backend::X11)
|
||||
auto backend = GuiSystem::getWindowInfo().window_main.backend;
|
||||
if(backend == GuiSystem::WindowHandleInfo::Backend::X11)
|
||||
requiredExtensions.emplace_back(VK_KHR_XLIB_SURFACE_EXTENSION_NAME);
|
||||
#ifdef HAS_WAYLAND
|
||||
else if (backend == WindowHandleInfo::Backend::WAYLAND)
|
||||
else if (backend == GuiSystem::WindowHandleInfo::Backend::WAYLAND)
|
||||
requiredExtensions.emplace_back(VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME);
|
||||
#endif // HAS_WAYLAND
|
||||
#endif // __ANDROID__
|
||||
@@ -156,7 +156,7 @@ std::vector<VulkanRenderer::DeviceInfo> VulkanRenderer::GetDevices()
|
||||
throw std::runtime_error("Failed to find a GPU with Vulkan support.");
|
||||
|
||||
// create tmp surface to create a logical device
|
||||
auto surface = CreateFramebufferSurface(instance, gui_getWindowInfo().window_main);
|
||||
auto surface = CreateFramebufferSurface(instance, GuiSystem::getWindowInfo().window_main);
|
||||
std::vector<VkPhysicalDevice> devices(device_count);
|
||||
vkEnumeratePhysicalDevices(instance, &device_count, devices.data());
|
||||
for (const auto& device : devices)
|
||||
@@ -362,7 +362,7 @@ VulkanRenderer::VulkanRenderer()
|
||||
throw std::runtime_error("Failed to find a GPU with Vulkan support.");
|
||||
|
||||
// create tmp surface to create a logical device
|
||||
auto surface = CreateFramebufferSurface(m_instance, gui_getWindowInfo().window_main);
|
||||
auto surface = CreateFramebufferSurface(m_instance, GuiSystem::getWindowInfo().window_main);
|
||||
|
||||
auto& config = GetConfig();
|
||||
decltype(config.graphic_device_uuid) zero{};
|
||||
@@ -677,7 +677,7 @@ VulkanRenderer* VulkanRenderer::GetInstance()
|
||||
|
||||
void VulkanRenderer::InitializeSurface(const Vector2i& size, bool mainWindow)
|
||||
{
|
||||
auto& windowHandleInfo = mainWindow ? gui_getWindowInfo().canvas_main : gui_getWindowInfo().canvas_pad;
|
||||
auto& windowHandleInfo = mainWindow ? GuiSystem::getWindowInfo().canvas_main : GuiSystem::getWindowInfo().canvas_pad;
|
||||
|
||||
const auto surface = CreateFramebufferSurface(m_instance, windowHandleInfo);
|
||||
if (mainWindow)
|
||||
@@ -721,7 +721,7 @@ bool VulkanRenderer::IsPadWindowActive()
|
||||
|
||||
void VulkanRenderer::HandleScreenshotRequest(LatteTextureView* texView, bool padView)
|
||||
{
|
||||
const bool hasScreenshotRequest = gui_hasScreenshotRequest();
|
||||
const bool hasScreenshotRequest = std::exchange(m_screenshot_requested, false);
|
||||
if (!hasScreenshotRequest && m_screenshot_state == ScreenshotState::None)
|
||||
return;
|
||||
|
||||
@@ -1187,11 +1187,11 @@ std::vector<const char*> VulkanRenderer::CheckInstanceExtensionSupport(FeatureCo
|
||||
#if __ANDROID__
|
||||
requiredInstanceExtensions.emplace_back(VK_KHR_ANDROID_SURFACE_EXTENSION_NAME);
|
||||
#else
|
||||
auto backend = gui_getWindowInfo().window_main.backend;
|
||||
if(backend == WindowHandleInfo::Backend::X11)
|
||||
auto backend = GuiSystem::getWindowInfo().window_main.backend;
|
||||
if(backend == GuiSystem::WindowHandleInfo::Backend::X11)
|
||||
requiredInstanceExtensions.emplace_back(VK_KHR_XLIB_SURFACE_EXTENSION_NAME);
|
||||
#if HAS_WAYLAND
|
||||
else if (backend == WindowHandleInfo::Backend::WAYLAND)
|
||||
else if (backend == GuiSystem::WindowHandleInfo::Backend::WAYLAND)
|
||||
requiredInstanceExtensions.emplace_back(VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME);
|
||||
#endif // HAS_WAYLAND
|
||||
#endif // __ANDROID__
|
||||
@@ -1354,24 +1354,24 @@ VkSurfaceKHR VulkanRenderer::CreateWaylandSurface(VkInstance instance, wl_displa
|
||||
#endif // __ANDROID__
|
||||
#endif // BOOST_OS_LINUX
|
||||
|
||||
VkSurfaceKHR VulkanRenderer::CreateFramebufferSurface(VkInstance instance, struct WindowHandleInfo& windowInfo)
|
||||
VkSurfaceKHR VulkanRenderer::CreateFramebufferSurface(VkInstance instance, struct GuiSystem::WindowHandleInfo& windowInfo)
|
||||
{
|
||||
#if BOOST_OS_WINDOWS
|
||||
return CreateWinSurface(instance, windowInfo.hwnd);
|
||||
return CreateWinSurface(instance, reinterpret_cast<HWND>(windowInfo.hwnd));
|
||||
#elif BOOST_OS_LINUX
|
||||
#if __ANDROID__
|
||||
return CreateAndroidSurface(instance, static_cast<ANativeWindow *>(windowInfo.handle));
|
||||
return CreateAndroidSurface(instance, static_cast<ANativeWindow*>(windowInfo.surface));
|
||||
#else
|
||||
if(windowInfo.backend == WindowHandleInfo::Backend::X11)
|
||||
return CreateXlibSurface(instance, windowInfo.xlib_display, windowInfo.xlib_window);
|
||||
if(windowInfo.backend == GuiSystem::WindowHandleInfo::Backend::X11)
|
||||
return CreateXlibSurface(instance, static_cast<Display*>(windowInfo.display), reinterpret_cast<Window>(windowInfo.surface));
|
||||
#ifdef HAS_WAYLAND
|
||||
if(windowInfo.backend == WindowHandleInfo::Backend::WAYLAND)
|
||||
return CreateWaylandSurface(instance, windowInfo.display, windowInfo.surface);
|
||||
if(windowInfo.backend == GuiSystem::WindowHandleInfo::Backend::WAYLAND)
|
||||
return CreateWaylandSurface(instance, static_cast<wl_display*>(windowInfo.display), static_cast<wl_surface*>(windowInfo.surface));
|
||||
#endif
|
||||
return {};
|
||||
#endif // __ANDROID__
|
||||
#elif BOOST_OS_MACOS
|
||||
return CreateCocoaSurface(instance, windowInfo.handle);
|
||||
return CreateCocoaSurface(instance, windowInfo.surface);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -2666,11 +2666,11 @@ void VulkanRenderer::RecreateSwapchain(bool mainWindow, bool skipCreate)
|
||||
if (mainWindow)
|
||||
{
|
||||
ImGui_ImplVulkan_Shutdown();
|
||||
gui_getWindowPhysSize(size.x, size.y);
|
||||
GuiSystem::getWindowPhysSize(size.x, size.y);
|
||||
}
|
||||
else
|
||||
{
|
||||
gui_getPadWindowPhysSize(size.x, size.y);
|
||||
GuiSystem::getPadWindowPhysSize(size.x, size.y);
|
||||
}
|
||||
|
||||
chainInfo.swapchainImageIndex = -1;
|
||||
@@ -2700,9 +2700,9 @@ bool VulkanRenderer::UpdateSwapchainProperties(bool mainWindow)
|
||||
|
||||
int width, height;
|
||||
if (mainWindow)
|
||||
gui_getWindowPhysSize(width, height);
|
||||
GuiSystem::getWindowPhysSize(width, height);
|
||||
else
|
||||
gui_getPadWindowPhysSize(width, height);
|
||||
GuiSystem::getPadWindowPhysSize(width, height);
|
||||
auto extent = chainInfo.getExtent();
|
||||
if (width != extent.width || height != extent.height)
|
||||
stateChanged = true;
|
||||
@@ -3793,9 +3793,9 @@ void VulkanRenderer::NotifySurfaceChanged(bool mainWindow)
|
||||
if(!chainInfo)
|
||||
return;
|
||||
if(mainWindow)
|
||||
chainInfo->surface = CreateFramebufferSurface(m_instance, gui_getWindowInfo().canvas_main);
|
||||
chainInfo->surface = CreateFramebufferSurface(m_instance, GuiSystem::getWindowInfo().canvas_main);
|
||||
else
|
||||
chainInfo->surface = CreateFramebufferSurface(m_instance, gui_getWindowInfo().canvas_pad);
|
||||
chainInfo->surface = CreateFramebufferSurface(m_instance, GuiSystem::getWindowInfo().canvas_pad);
|
||||
m_surfaceCondVar.notify_one();
|
||||
}
|
||||
#endif // __ANDROID__
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
#include "util/helpers/Semaphore.h"
|
||||
#include "util/containers/flat_hash_map.hpp"
|
||||
#include "util/containers/robin_hood.h"
|
||||
#include "Cemu/GuiSystem/GuiSystem.h"
|
||||
|
||||
struct VkSupportedFormatInfo_t
|
||||
{
|
||||
@@ -213,7 +214,7 @@ public:
|
||||
#endif // __ANDROID__
|
||||
#endif // BOOST_OS_LINUX
|
||||
|
||||
static VkSurfaceKHR CreateFramebufferSurface(VkInstance instance, struct WindowHandleInfo& windowInfo);
|
||||
static VkSurfaceKHR CreateFramebufferSurface(VkInstance instance, GuiSystem::WindowHandleInfo& windowInfo);
|
||||
|
||||
void AppendOverlayDebugInfo() override;
|
||||
|
||||
|
||||
@@ -14,7 +14,6 @@
|
||||
#include "util/crypto/crc32.h"
|
||||
#include "config/ActiveSettings.h"
|
||||
#include "Cafe/OS/libs/coreinit/coreinit_DynLoad.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
|
||||
class PPCCodeHeap : public VHeap
|
||||
{
|
||||
@@ -1829,7 +1828,8 @@ void RPLLoader_UnloadModule(RPLModule* rpl)
|
||||
RPLLoader_decrementModuleDependencyRefs(rpl);
|
||||
|
||||
// save module config for this module in the debugger
|
||||
debuggerWindow_notifyModuleUnloaded(rpl);
|
||||
auto debuggerInterface = debugger_getDebuggerCallbacks();
|
||||
if (debuggerInterface) debuggerInterface->notifyModuleLoaded(rpl);
|
||||
|
||||
// release memory
|
||||
rplLoaderHeap_codeArea2.free(rpl->regionMappingBase_text.GetPtr());
|
||||
@@ -1912,7 +1912,8 @@ void RPLLoader_Link()
|
||||
RPLLoader_LoadDebugSymbols(rplModuleList[i]);
|
||||
rplModuleList[i]->isLinked = true; // mark as linked
|
||||
GraphicPack2::NotifyModuleLoaded(rplModuleList[i]);
|
||||
debuggerWindow_notifyModuleLoaded(rplModuleList[i]);
|
||||
auto debuggerCallbacks = debugger_getDebuggerCallbacks();
|
||||
if (debuggerCallbacks) debuggerCallbacks->notifyModuleLoaded(rplModuleList[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Cafe/OS/common/OSCommon.h"
|
||||
#include "Cafe/HW/Espresso/PPCCallback.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cafe/OS/libs/padscore/padscore.h"
|
||||
#include "Cafe/OS/libs/coreinit/coreinit_Time.h"
|
||||
#include "Cafe/OS/libs/coreinit/coreinit_Alarm.h"
|
||||
@@ -450,7 +449,7 @@ sint32 _KPADRead(uint32 channel, KPADStatus_t* samplingBufs, uint32 length, bety
|
||||
samplingBufs->wpadErr = WPAD_ERR_NONE;
|
||||
samplingBufs->data_format = controller->get_data_format();
|
||||
samplingBufs->devType = controller->get_device_type();
|
||||
if(!g_inputConfigWindowHasFocus)
|
||||
if (!InputManager::input_config_window_has_focus())
|
||||
{
|
||||
const auto btn_repeat = padscore::g_padscore.controller_data[channel].btn_repeat;
|
||||
controller->KPADRead(*samplingBufs, btn_repeat);
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "Cafe/OS/common/OSCommon.h"
|
||||
#include "Cafe/HW/Espresso/PPCCallback.h"
|
||||
#include "gui/guiWrapper.h"
|
||||
#include "Cafe/OS/libs/vpad/vpad.h"
|
||||
#include "audio/IAudioAPI.h"
|
||||
#include "Cafe/OS/libs/coreinit/coreinit_Time.h"
|
||||
@@ -263,7 +262,7 @@ namespace vpad
|
||||
PPCCore_switchToScheduler();
|
||||
}
|
||||
|
||||
if (!g_inputConfigWindowHasFocus)
|
||||
if (!InputManager::input_config_window_has_focus())
|
||||
{
|
||||
if (channel <= 1 && vpadDelayEnabled)
|
||||
{
|
||||
|
||||
@@ -5,6 +5,8 @@ add_library(CemuComponents
|
||||
ExpressionParser/ExpressionParser.h
|
||||
FileCache/FileCache.cpp
|
||||
FileCache/FileCache.h
|
||||
GuiSystem/GuiSystem.cpp
|
||||
GuiSystem/GuiSystem.h
|
||||
Logging/CemuDebugLogging.h
|
||||
Logging/CemuLogging.cpp
|
||||
Logging/CemuLogging.h
|
||||
|
||||
@@ -0,0 +1,97 @@
|
||||
#include "GuiSystem.h"
|
||||
|
||||
namespace GuiSystem
|
||||
{
|
||||
std::function<std::string(uint32)> s_key_code_to_string;
|
||||
void registerKeyCodeToStringCallback(const std::function<std::string(uint32)>& keyCodeToString)
|
||||
{
|
||||
s_key_code_to_string = keyCodeToString;
|
||||
}
|
||||
void unregisterKeyCodeToStringCallback()
|
||||
{
|
||||
s_key_code_to_string = {};
|
||||
}
|
||||
std::string keyCodeToString(uint32 key)
|
||||
{
|
||||
if (!s_key_code_to_string)
|
||||
return "";
|
||||
return s_key_code_to_string(key);
|
||||
}
|
||||
|
||||
WindowInfo s_window_info;
|
||||
|
||||
WindowInfo& getWindowInfo()
|
||||
{
|
||||
return s_window_info;
|
||||
}
|
||||
|
||||
void getWindowSize(int& w, int& h)
|
||||
{
|
||||
w = s_window_info.width;
|
||||
h = s_window_info.height;
|
||||
}
|
||||
|
||||
void getPadWindowSize(int& w, int& h)
|
||||
{
|
||||
if (s_window_info.pad_open)
|
||||
{
|
||||
w = s_window_info.pad_width;
|
||||
h = s_window_info.pad_height;
|
||||
}
|
||||
else
|
||||
{
|
||||
w = 0;
|
||||
h = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void getWindowPhysSize(int& w, int& h)
|
||||
{
|
||||
w = s_window_info.phys_width;
|
||||
h = s_window_info.phys_height;
|
||||
}
|
||||
|
||||
void getPadWindowPhysSize(int& w, int& h)
|
||||
{
|
||||
if (s_window_info.pad_open)
|
||||
{
|
||||
w = s_window_info.phys_pad_width;
|
||||
h = s_window_info.phys_pad_height;
|
||||
}
|
||||
else
|
||||
{
|
||||
w = 0;
|
||||
h = 0;
|
||||
}
|
||||
}
|
||||
|
||||
double getWindowDPIScale()
|
||||
{
|
||||
return s_window_info.dpi_scale;
|
||||
}
|
||||
|
||||
double getPadDPIScale()
|
||||
{
|
||||
return s_window_info.pad_open ? s_window_info.pad_dpi_scale.load() : 1.0;
|
||||
}
|
||||
|
||||
bool isPadWindowOpen()
|
||||
{
|
||||
return s_window_info.pad_open;
|
||||
}
|
||||
|
||||
bool isKeyDown(uint32 key)
|
||||
{
|
||||
return s_window_info.get_keystate(key);
|
||||
}
|
||||
|
||||
bool isKeyDown(PlatformKeyCodes key)
|
||||
{
|
||||
return s_window_info.get_keystate(key);
|
||||
}
|
||||
|
||||
bool isFullScreen()
|
||||
{
|
||||
return s_window_info.is_fullscreen;
|
||||
}
|
||||
} // namespace GuiSystem
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user