diff --git a/external/parallel-rdp/ParallelRDPWrapper.cpp b/external/parallel-rdp/ParallelRDPWrapper.cpp index c40c9f0b..be96e675 100644 --- a/external/parallel-rdp/ParallelRDPWrapper.cpp +++ b/external/parallel-rdp/ParallelRDPWrapper.cpp @@ -2,6 +2,7 @@ #include #include #include +#include using namespace Vulkan; using namespace RDP; diff --git a/external/parallel-rdp/ParallelRDPWrapper.hpp b/external/parallel-rdp/ParallelRDPWrapper.hpp index 80211d34..579b5177 100644 --- a/external/parallel-rdp/ParallelRDPWrapper.hpp +++ b/external/parallel-rdp/ParallelRDPWrapper.hpp @@ -1,8 +1,11 @@ #pragma once -#include #include #include -#include +#include + +namespace n64 { +struct VI; +} class ParallelRDP { public: diff --git a/src/backend/Core.cpp b/src/backend/Core.cpp index 29edbb83..10a8ae70 100644 --- a/src/backend/Core.cpp +++ b/src/backend/Core.cpp @@ -3,7 +3,7 @@ #include namespace n64 { -Core::Core(ParallelRDP ¶llel) : cpu(std::make_unique(parallel)) {} +Core::Core() : cpu(std::make_unique(parallel)) {} void Core::Stop() { render = false; @@ -106,15 +106,15 @@ void Core::Serialize() { } void Core::Deserialize() { - std::vector dVER(serialized[slot].begin(), serialized[slot].begin() + verSize); + std::vector dVER(serialized[slot].begin(), serialized[slot].begin() + verSize); if (dVER[0] != (KAIZEN_VERSION >> 8) || dVER[1] != (KAIZEN_VERSION >> 4) || dVER[2] != (KAIZEN_VERSION & 0xFF)) { Util::panic("PROBLEMI!"); } cpu->GetMem().Deserialize( - std::vector(serialized[slot].begin() + verSize, serialized[slot].begin() + verSize + memSize)); - cpu->Deserialize(std::vector(serialized[slot].begin() + verSize + memSize, - serialized[slot].begin() + verSize + memSize + cpuSize)); + std::vector(serialized[slot].begin() + verSize, serialized[slot].begin() + verSize + memSize)); + cpu->Deserialize( + std::vector(serialized[slot].begin() + verSize + memSize, serialized[slot].begin() + verSize + memSize + cpuSize)); serialized[slot].erase(serialized[slot].begin(), serialized[slot].end()); } } // namespace n64 diff --git a/src/backend/Core.hpp b/src/backend/Core.hpp index d6194952..545707a1 100644 --- a/src/backend/Core.hpp +++ b/src/backend/Core.hpp @@ -1,14 +1,12 @@ #pragma once +#include #include #include #include -struct Window; -struct Event; - namespace n64 { struct Core { - explicit Core(ParallelRDP &); + explicit Core(); void Stop(); void LoadROM(const std::string &); [[nodiscard]] bool LoadTAS(const fs::path &) const; @@ -29,5 +27,6 @@ struct Core { std::vector serialized[10]{}; size_t memSize{}, cpuSize{}, verSize{}; int slot = 0; + ParallelRDP parallel; }; } // namespace n64 diff --git a/src/backend/core/Disassembler.hpp b/src/backend/core/Disassembler.hpp index 1f217872..d03ff8a1 100644 --- a/src/backend/core/Disassembler.hpp +++ b/src/backend/core/Disassembler.hpp @@ -2,7 +2,6 @@ #include #include #include -#include #include struct Disassembler { @@ -19,7 +18,7 @@ struct Disassembler { return ret; } - DisassemblyResult Disassemble(u32 address, u32 instruction) { + DisassemblyResult Disassemble(const u32 address, const u32 instruction) { return details ? DisassembleDetailed(address, instruction) : DisassembleSimple(address, instruction); } @@ -29,7 +28,7 @@ private: DisassemblyResult DisassembleDetailed(u32 address, u32 instruction); DisassemblyResult DisassembleSimple(u32 address, u32 instruction); - Disassembler(bool rsp) : rsp(rsp) { + explicit Disassembler(const bool rsp) : rsp(rsp) { if (cs_open(CS_ARCH_MIPS, static_cast((rsp ? CS_MODE_32 : CS_MODE_64) | CS_MODE_BIG_ENDIAN), &handle) != CS_ERR_OK) { Util::panic("Could not initialize {} disassembler!", rsp ? "RSP" : "CPU"); @@ -43,5 +42,5 @@ private: bool rsp = false; bool details = true; - csh handle; + csh handle{}; }; diff --git a/src/backend/core/RDP.cpp b/src/backend/core/RDP.cpp index 0c365cfd..c1b79d6b 100644 --- a/src/backend/core/RDP.cpp +++ b/src/backend/core/RDP.cpp @@ -2,6 +2,7 @@ #include #include #include +#include namespace n64 { RDP::RDP(Mem &mem, ParallelRDP ¶llel) : mem(mem), parallel(parallel) { diff --git a/src/frontend/EmuThread.cpp b/src/frontend/EmuThread.cpp index 20d13609..4c7d0892 100644 --- a/src/frontend/EmuThread.cpp +++ b/src/frontend/EmuThread.cpp @@ -1,102 +1,53 @@ +#include #include #include -EmuThread::EmuThread(RenderWidget &renderWidget, SettingsWindow &settings) noexcept : - renderWidget(renderWidget), core(parallel), settings(settings) {} +EmuThread::EmuThread(const std::shared_ptr &core, RenderWidget &renderWidget, + SettingsWindow &settings) noexcept : renderWidget(renderWidget), core(core), settings(settings) {} [[noreturn]] void EmuThread::run() noexcept { - parallel.Init(renderWidget.qtVkInstanceFactory, renderWidget.wsiPlatform, renderWidget.windowInfo, - core.cpu->GetMem().GetRDRAMPtr()); + core->parallel.Init(renderWidget.qtVkInstanceFactory, renderWidget.wsiPlatform, renderWidget.windowInfo, + core->cpu->GetMem().GetRDRAMPtr()); SDL_InitSubSystem(SDL_INIT_GAMEPAD); - bool controllerConnected = false; if (SDL_AddGamepadMappingsFromFile("resources/gamecontrollerdb.txt") < 0) { Util::warn("[SDL] Could not load game controller DB"); } - auto pollEvents = [&] { - SDL_Event e; - while (SDL_PollEvent(&e)) { - switch (e.type) { - case SDL_EVENT_GAMEPAD_ADDED: - { - const int index = e.gdevice.which; - controller = SDL_OpenGamepad(index); - Util::info("Found controller!"); - auto serial = SDL_GetGamepadSerial(controller); - auto name = SDL_GetGamepadName(controller); - auto path = SDL_GetGamepadPath(controller); - Util::info("\tName: {}", name ? name : "Not available"); - Util::info("\tSerial: {}", serial ? serial : "Not available"); - Util::info("\tPath: {}", path ? path : "Not available"); - controllerConnected = true; - } - break; - case SDL_EVENT_GAMEPAD_REMOVED: - { - controllerConnected = false; - SDL_CloseGamepad(controller); - } - break; - } - } - }; - while (!isInterruptionRequested()) { - if (!core.pause) { - core.Run(settings.getVolumeL(), settings.getVolumeR()); + if (!core->pause) { + core->Run(settings.getVolumeL(), settings.getVolumeR()); } - if (core.render) { - parallel.UpdateScreen(core.cpu->GetMem().mmio.vi); - } - - pollEvents(); - - if (controllerConnected) { - n64::PIF &pif = core.cpu->GetMem().mmio.si.pif; - pif.UpdateButton(0, n64::Controller::Key::A, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_SOUTH)); - pif.UpdateButton(0, n64::Controller::Key::B, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_WEST)); - pif.UpdateButton(0, n64::Controller::Key::Z, - SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_LEFT_TRIGGER) == SDL_JOYSTICK_AXIS_MAX); - pif.UpdateButton(0, n64::Controller::Key::Start, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_START)); - pif.UpdateButton(0, n64::Controller::Key::DUp, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_DPAD_UP)); - pif.UpdateButton(0, n64::Controller::Key::DDown, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_DPAD_DOWN)); - pif.UpdateButton(0, n64::Controller::Key::DLeft, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_DPAD_LEFT)); - pif.UpdateButton(0, n64::Controller::Key::DRight, - SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_DPAD_RIGHT)); - pif.UpdateButton(0, n64::Controller::Key::LT, SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_LEFT_SHOULDER)); - pif.UpdateButton(0, n64::Controller::Key::RT, - SDL_GetGamepadButton(controller, SDL_GAMEPAD_BUTTON_RIGHT_SHOULDER)); - pif.UpdateButton(0, n64::Controller::Key::CUp, SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_RIGHTY) <= -127); - pif.UpdateButton(0, n64::Controller::Key::CDown, SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_RIGHTY) >= 127); - pif.UpdateButton(0, n64::Controller::Key::CLeft, SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_RIGHTX) <= -127); - pif.UpdateButton(0, n64::Controller::Key::CRight, SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_RIGHTX) >= 127); - - float xclamped = SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_LEFTX); - if (xclamped < 0) { - xclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MAX)); - } else { - xclamped /= SDL_JOYSTICK_AXIS_MAX; - } - - xclamped *= 86; - - float yclamped = SDL_GetGamepadAxis(controller, SDL_GAMEPAD_AXIS_LEFTY); - if (yclamped < 0) { - yclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MIN)); - } else { - yclamped /= SDL_JOYSTICK_AXIS_MAX; - } - - yclamped *= 86; - - pif.UpdateAxis(0, n64::Controller::Axis::Y, -yclamped); - pif.UpdateAxis(0, n64::Controller::Axis::X, xclamped); + if (core->render) { + core->parallel.UpdateScreen(core->cpu->GetMem().mmio.vi); } } SetRender(false); Stop(); } + +void EmuThread::TogglePause() const noexcept { + core->TogglePause(); + Util::RPC::GetInstance().Update(core->pause ? Util::RPC::Paused : Util::RPC::GetInstance().GetState(), + core->cpu->GetMem().rom.gameNameDB, + core->cpu->GetMem().mmio.si.pif.movie.GetFilename()); +} + +void EmuThread::SetRender(bool v) const noexcept { core->render = v; } + +void EmuThread::Reset() const noexcept { + core->pause = true; + core->Stop(); + core->LoadROM(core->rom); + core->pause = false; +} + +void EmuThread::Stop() const noexcept { + Util::RPC::GetInstance().Update(Util::RPC::Idling); + core->rom = {}; + core->pause = true; + core->Stop(); +} diff --git a/src/frontend/EmuThread.hpp b/src/frontend/EmuThread.hpp index 87754bcd..995946a4 100644 --- a/src/frontend/EmuThread.hpp +++ b/src/frontend/EmuThread.hpp @@ -1,46 +1,27 @@ #pragma once -#include #include #include #include -#include #include #include +namespace n64 { +struct Core; +} + class EmuThread : public QThread { Q_OBJECT RenderWidget &renderWidget; public: - explicit EmuThread(RenderWidget &, SettingsWindow &) noexcept; + explicit EmuThread(const std::shared_ptr &, RenderWidget &, SettingsWindow &) noexcept; [[noreturn]] void run() noexcept override; + void TogglePause() const noexcept; + void SetRender(bool v) const noexcept; + void Reset() const noexcept; + void Stop() const noexcept; - SDL_Gamepad *controller{}; - ParallelRDP parallel; - n64::Core core; + std::shared_ptr core; SettingsWindow &settings; - - void TogglePause() { - core.TogglePause(); - Util::RPC::GetInstance().Update(core.pause ? Util::RPC::Paused : Util::RPC::GetInstance().GetState(), - core.cpu->GetMem().rom.gameNameDB, - core.cpu->GetMem().mmio.si.pif.movie.GetFilename()); - } - - void SetRender(bool v) { core.render = v; } - - void Reset() { - core.pause = true; - core.Stop(); - core.LoadROM(core.rom); - core.pause = false; - } - - void Stop() { - Util::RPC::GetInstance().Update(Util::RPC::Idling); - core.rom = {}; - core.pause = true; - core.Stop(); - } }; diff --git a/src/frontend/KaizenQt.cpp b/src/frontend/KaizenQt.cpp index 39e10a2e..7991bab7 100644 --- a/src/frontend/KaizenQt.cpp +++ b/src/frontend/KaizenQt.cpp @@ -1,16 +1,17 @@ +#include #include #include #include #include #include -#include namespace fs = std::filesystem; KaizenQt::KaizenQt() noexcept : QWidget(nullptr) { - mainWindow = std::make_unique(); + core = std::make_shared(); + mainWindow = std::make_unique(core); settingsWindow = std::make_unique(); - emuThread = std::make_unique(*mainWindow->vulkanWidget, *settingsWindow); + emuThread = std::make_unique(core, *mainWindow->vulkanWidget, *settingsWindow); debugger = std::make_unique(); ConnectMainWindowSignalsToSlots(); @@ -53,9 +54,9 @@ void KaizenQt::LoadROM(const QString &fileName) noexcept { mainWindow->actionReset->setEnabled(true); mainWindow->actionStop->setEnabled(true); emuThread->start(); - emuThread->core.LoadROM(fileName.toStdString()); - auto gameNameDB = emuThread->core.cpu->GetMem().rom.gameNameDB; - mainWindow->setWindowTitle(emuThread->core.cpu->GetMem().rom.gameNameDB.c_str()); + emuThread->core->LoadROM(fileName.toStdString()); + auto gameNameDB = emuThread->core->cpu->GetMem().rom.gameNameDB; + mainWindow->setWindowTitle(emuThread->core->cpu->GetMem().rom.gameNameDB.c_str()); Util::RPC::GetInstance().Update(Util::RPC::Playing, gameNameDB); } @@ -69,15 +70,19 @@ void KaizenQt::Quit() noexcept { } void KaizenQt::LoadTAS(const QString &fileName) const noexcept { - emuThread->core.LoadTAS(fs::path(fileName.toStdString())); - auto gameNameDB = emuThread->core.cpu->GetMem().rom.gameNameDB; - auto movieName = fs::path(fileName.toStdString()).stem().string(); - Util::RPC::GetInstance().Update(Util::RPC::MovieReplay, gameNameDB, movieName); + if (emuThread->core->LoadTAS(fs::path(fileName.toStdString()))) { + auto gameNameDB = emuThread->core->cpu->GetMem().rom.gameNameDB; + auto movieName = fs::path(fileName.toStdString()).stem().string(); + Util::RPC::GetInstance().Update(Util::RPC::MovieReplay, gameNameDB, movieName); + return; + } + + Util::panic("Could not load TAS movie {}!", fileName.toStdString()); } void KaizenQt::keyPressEvent(QKeyEvent *e) { - emuThread->core.pause = true; - n64::Mem &mem = emuThread->core.cpu->GetMem(); + emuThread->core->pause = true; + n64::Mem &mem = emuThread->core->cpu->GetMem(); n64::PIF &pif = mem.mmio.si.pif; auto k = static_cast(e->key()); @@ -95,13 +100,13 @@ void KaizenQt::keyPressEvent(QKeyEvent *e) { if (k == settingsWindow->keyMap[17]) pif.UpdateAxis(0, n64::Controller::Axis::X, 86); - emuThread->core.pause = false; + emuThread->core->pause = false; QWidget::keyPressEvent(e); } void KaizenQt::keyReleaseEvent(QKeyEvent *e) { - emuThread->core.pause = true; - n64::Mem &mem = emuThread->core.cpu->GetMem(); + emuThread->core->pause = true; + n64::Mem &mem = emuThread->core->cpu->GetMem(); n64::PIF &pif = mem.mmio.si.pif; auto k = static_cast(e->key()); @@ -119,6 +124,6 @@ void KaizenQt::keyReleaseEvent(QKeyEvent *e) { if (k == settingsWindow->keyMap[17]) pif.UpdateAxis(0, n64::Controller::Axis::X, 0); - emuThread->core.pause = false; + emuThread->core->pause = false; QWidget::keyReleaseEvent(e); } diff --git a/src/frontend/KaizenQt.hpp b/src/frontend/KaizenQt.hpp index f8591937..cc8fef49 100644 --- a/src/frontend/KaizenQt.hpp +++ b/src/frontend/KaizenQt.hpp @@ -3,6 +3,7 @@ #include #include #include +#include enum class CompositorCategory { Windows, MacOS, XCB, Wayland }; @@ -39,4 +40,5 @@ private: std::unique_ptr settingsWindow; std::unique_ptr emuThread; std::unique_ptr debugger; + std::shared_ptr core; }; diff --git a/src/frontend/MainWindow.cpp b/src/frontend/MainWindow.cpp index d5d54070..4257a615 100644 --- a/src/frontend/MainWindow.cpp +++ b/src/frontend/MainWindow.cpp @@ -1,6 +1,6 @@ #include -MainWindow::MainWindow() noexcept { +MainWindow::MainWindow(const std::shared_ptr &core) noexcept { if (objectName().isEmpty()) setObjectName("MainWindow"); resize(800, 646); @@ -26,7 +26,7 @@ MainWindow::MainWindow() noexcept { verticalLayout->setSpacing(0); verticalLayout->setObjectName("verticalLayout"); verticalLayout->setContentsMargins(0, 0, 0, 0); - vulkanWidget = std::make_unique(); + vulkanWidget = std::make_unique(core); vulkanWidget->setObjectName("vulkanWidget"); verticalLayout->addWidget(vulkanWidget.get()); diff --git a/src/frontend/MainWindow.hpp b/src/frontend/MainWindow.hpp index b821de25..77d2d952 100644 --- a/src/frontend/MainWindow.hpp +++ b/src/frontend/MainWindow.hpp @@ -16,7 +16,7 @@ class MainWindow : public QMainWindow { Q_OBJECT public: - MainWindow() noexcept; + MainWindow(const std::shared_ptr &) noexcept; std::unique_ptr actionOpenDebuggerWindow{}; std::unique_ptr actionAbout{}; diff --git a/src/frontend/RenderWidget.cpp b/src/frontend/RenderWidget.cpp index 95084ca3..33f1d28e 100644 --- a/src/frontend/RenderWidget.cpp +++ b/src/frontend/RenderWidget.cpp @@ -1,7 +1,9 @@ +#include #include #include +#include -RenderWidget::RenderWidget() : QWidget(nullptr) { +RenderWidget::RenderWidget(const std::shared_ptr &core) : QWidget(nullptr) { setAttribute(Qt::WA_NativeWindow); setAttribute(Qt::WA_PaintOnScreen); if (GetOSCompositorCategory() == CompositorCategory::Wayland) { @@ -22,6 +24,76 @@ RenderWidget::RenderWidget() : QWidget(nullptr) { windowHandle()->setVulkanInstance(&qtVkInstanceFactory->handle); windowHandle()->create(); - wsiPlatform = std::make_shared(windowHandle()); + wsiPlatform = std::make_shared(core, windowHandle()); windowInfo = std::make_shared(windowHandle()); } + +void QtWSIPlatform::poll_input() { + SDL_Event e; + while (SDL_PollEvent(&e)) { + switch (e.type) { + case SDL_EVENT_GAMEPAD_ADDED: + { + const auto index = e.gdevice.which; + gamepad = SDL_OpenGamepad(index); + Util::info("Found controller!"); + const auto serial = SDL_GetGamepadSerial(gamepad); + const auto name = SDL_GetGamepadName(gamepad); + const auto path = SDL_GetGamepadPath(gamepad); + Util::info("\tName: {}", name ? name : "Not available"); + Util::info("\tSerial: {}", serial ? serial : "Not available"); + Util::info("\tPath: {}", path ? path : "Not available"); + gamepadConnected = true; + } + break; + case SDL_EVENT_GAMEPAD_REMOVED: + { + gamepadConnected = false; + SDL_CloseGamepad(gamepad); + } + break; + default: + break; + } + } + + if (gamepadConnected) { + n64::PIF &pif = core->cpu->GetMem().mmio.si.pif; + pif.UpdateButton(0, n64::Controller::Key::A, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_SOUTH)); + pif.UpdateButton(0, n64::Controller::Key::B, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_WEST)); + pif.UpdateButton(0, n64::Controller::Key::Z, + SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_LEFT_TRIGGER) == SDL_JOYSTICK_AXIS_MAX); + pif.UpdateButton(0, n64::Controller::Key::Start, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_START)); + pif.UpdateButton(0, n64::Controller::Key::DUp, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_DPAD_UP)); + pif.UpdateButton(0, n64::Controller::Key::DDown, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_DPAD_DOWN)); + pif.UpdateButton(0, n64::Controller::Key::DLeft, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_DPAD_LEFT)); + pif.UpdateButton(0, n64::Controller::Key::DRight, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_DPAD_RIGHT)); + pif.UpdateButton(0, n64::Controller::Key::LT, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_LEFT_SHOULDER)); + pif.UpdateButton(0, n64::Controller::Key::RT, SDL_GetGamepadButton(gamepad, SDL_GAMEPAD_BUTTON_RIGHT_SHOULDER)); + pif.UpdateButton(0, n64::Controller::Key::CUp, SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_RIGHTY) <= -127); + pif.UpdateButton(0, n64::Controller::Key::CDown, SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_RIGHTY) >= 127); + pif.UpdateButton(0, n64::Controller::Key::CLeft, SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_RIGHTX) <= -127); + pif.UpdateButton(0, n64::Controller::Key::CRight, SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_RIGHTX) >= 127); + + float xclamped = SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_LEFTX); + if (xclamped < 0) { + xclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MAX)); + } else { + xclamped /= SDL_JOYSTICK_AXIS_MAX; + } + + xclamped *= 86; + + float yclamped = SDL_GetGamepadAxis(gamepad, SDL_GAMEPAD_AXIS_LEFTY); + if (yclamped < 0) { + yclamped /= float(std::abs(SDL_JOYSTICK_AXIS_MIN)); + } else { + yclamped /= SDL_JOYSTICK_AXIS_MAX; + } + + yclamped *= 86; + + pif.UpdateAxis(0, n64::Controller::Axis::Y, -yclamped); + pif.UpdateAxis(0, n64::Controller::Axis::X, xclamped); + } +} diff --git a/src/frontend/RenderWidget.hpp b/src/frontend/RenderWidget.hpp index ecdd50f0..969f28d0 100644 --- a/src/frontend/RenderWidget.hpp +++ b/src/frontend/RenderWidget.hpp @@ -4,6 +4,11 @@ #include #include #include +#include + +namespace n64 { +struct Core; +} struct QtInstanceFactory : Vulkan::InstanceFactory { VkInstance create_instance(const VkInstanceCreateInfo *info) override { @@ -29,7 +34,7 @@ struct QtInstanceFactory : Vulkan::InstanceFactory { class QtParallelRdpWindowInfo : public ParallelRDP::WindowInfo { public: - explicit QtParallelRdpWindowInfo(QWindow* window) : window(window) {} + explicit QtParallelRdpWindowInfo(QWindow *window) : window(window) {} CoordinatePair get_window_size() override { return CoordinatePair{static_cast(window->width()), static_cast(window->height())}; } @@ -40,7 +45,7 @@ private: class QtWSIPlatform final : public Vulkan::WSIPlatform { public: - explicit QtWSIPlatform(QWindow* window) : window(window) {} + explicit QtWSIPlatform(const std::shared_ptr &core, QWindow *window) : window(window), core(core) {} std::vector get_instance_extensions() override { auto vec = std::vector(); @@ -64,7 +69,7 @@ public: bool alive(Vulkan::WSI &) override { return true; } - void poll_input() override {} + void poll_input() override; void poll_input_async(Granite::InputTrackerHandler *handler) override {} void event_frame_tick(double frame, double elapsed) override {} @@ -74,15 +79,19 @@ public: VkApplicationInfo appInfo{.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO, .apiVersion = VK_API_VERSION_1_3}; std::shared_ptr window{}; + +private: + std::shared_ptr core; + SDL_Gamepad *gamepad{}; + bool gamepadConnected = false; }; class RenderWidget : public QWidget { public: [[nodiscard]] VkInstance instance() const { return qtVkInstanceFactory->handle.vkInstance(); } - explicit RenderWidget(); + explicit RenderWidget(const std::shared_ptr &); [[nodiscard]] QPaintEngine *paintEngine() const override { return nullptr; } - std::shared_ptr windowInfo; std::shared_ptr wsiPlatform; std::shared_ptr qtVkInstanceFactory;