diff --git a/external/parallel-rdp/ParallelRDPWrapper.cpp b/external/parallel-rdp/ParallelRDPWrapper.cpp index 23adf78a..aff415af 100644 --- a/external/parallel-rdp/ParallelRDPWrapper.cpp +++ b/external/parallel-rdp/ParallelRDPWrapper.cpp @@ -3,6 +3,8 @@ #include #include #include +#include +#include using namespace Vulkan; using namespace RDP; @@ -98,13 +100,11 @@ void ParallelRDP::Init(const std::shared_ptr &factory, const st fragLayout.sets[0].fp_mask = 1; fragLayout.sets[0].array_size[0] = 1; - auto fullscreenQuadVert = Util::ReadFileBinary("resources/vert.spv"); - auto fullscreenQuadFrag = Util::ReadFileBinary("resources/frag.spv"); - auto sizeVert = fullscreenQuadVert.size(); - auto sizeFrag = fullscreenQuadFrag.size(); + auto sizeVert = sizeof(vertex_shader); + auto sizeFrag = sizeof(fragment_shader); fullscreen_quad_program = wsi->get_device().request_program( - reinterpret_cast(fullscreenQuadVert.data()), sizeVert, reinterpret_cast(fullscreenQuadFrag.data()), + reinterpret_cast(vertex_shader), sizeVert, reinterpret_cast(fragment_shader), sizeFrag, &vertLayout, &fragLayout); auto aligned_rdram = reinterpret_cast(rdram); diff --git a/resources/frag.spv b/resources/frag.spv deleted file mode 100644 index 5a0382be..00000000 Binary files a/resources/frag.spv and /dev/null differ diff --git a/resources/frag.spv.h b/resources/frag.spv.h new file mode 100644 index 00000000..12ba5341 --- /dev/null +++ b/resources/frag.spv.h @@ -0,0 +1,156 @@ +constexpr unsigned char fragment_shader[] = { + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x0A, 0x00, 0x0D, 0x00, + 0x49, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x47, 0x4C, 0x53, 0x4C, 0x2E, 0x73, 0x74, 0x64, 0x2E, 0x34, 0x35, 0x30, + 0x00, 0x00, 0x00, 0x00, 0x0E, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x07, 0x00, 0x04, 0x00, 0x00, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x6D, 0x61, 0x69, 0x6E, 0x00, 0x00, 0x00, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x00, 0x00, 0x10, 0x00, 0x03, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x03, 0x00, 0x03, 0x00, + 0x02, 0x00, 0x00, 0x00, 0xC2, 0x01, 0x00, 0x00, 0x04, 0x00, 0x0A, 0x00, + 0x47, 0x4C, 0x5F, 0x47, 0x4F, 0x4F, 0x47, 0x4C, 0x45, 0x5F, 0x63, 0x70, + 0x70, 0x5F, 0x73, 0x74, 0x79, 0x6C, 0x65, 0x5F, 0x6C, 0x69, 0x6E, 0x65, + 0x5F, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x69, 0x76, 0x65, 0x00, 0x00, + 0x04, 0x00, 0x08, 0x00, 0x47, 0x4C, 0x5F, 0x47, 0x4F, 0x4F, 0x47, 0x4C, + 0x45, 0x5F, 0x69, 0x6E, 0x63, 0x6C, 0x75, 0x64, 0x65, 0x5F, 0x64, 0x69, + 0x72, 0x65, 0x63, 0x74, 0x69, 0x76, 0x65, 0x00, 0x05, 0x00, 0x04, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x6D, 0x61, 0x69, 0x6E, 0x00, 0x00, 0x00, 0x00, + 0x05, 0x00, 0x03, 0x00, 0x09, 0x00, 0x00, 0x00, 0x75, 0x76, 0x00, 0x00, + 0x05, 0x00, 0x03, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x76, 0x55, 0x56, 0x00, + 0x05, 0x00, 0x04, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x53, 0x63, 0x72, 0x65, + 0x65, 0x6E, 0x00, 0x00, 0x06, 0x00, 0x05, 0x00, 0x0D, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x73, 0x69, 0x7A, 0x65, 0x00, 0x00, 0x00, 0x00, + 0x06, 0x00, 0x05, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x6F, 0x66, 0x66, 0x73, 0x65, 0x74, 0x00, 0x00, 0x05, 0x00, 0x04, 0x00, + 0x0F, 0x00, 0x00, 0x00, 0x75, 0x53, 0x63, 0x72, 0x65, 0x65, 0x6E, 0x00, + 0x05, 0x00, 0x05, 0x00, 0x3D, 0x00, 0x00, 0x00, 0x46, 0x72, 0x61, 0x67, + 0x43, 0x6F, 0x6C, 0x6F, 0x72, 0x00, 0x00, 0x00, 0x05, 0x00, 0x04, 0x00, + 0x40, 0x00, 0x00, 0x00, 0x53, 0x63, 0x61, 0x6C, 0x65, 0x00, 0x00, 0x00, + 0x05, 0x00, 0x04, 0x00, 0x44, 0x00, 0x00, 0x00, 0x75, 0x49, 0x6D, 0x61, + 0x67, 0x65, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x1E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x48, 0x00, 0x05, 0x00, + 0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x48, 0x00, 0x05, 0x00, 0x0D, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, + 0x47, 0x00, 0x03, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x47, 0x00, 0x04, 0x00, 0x3D, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00, 0x40, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00, + 0x44, 0x00, 0x00, 0x00, 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x47, 0x00, 0x04, 0x00, 0x44, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x13, 0x00, 0x02, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x21, 0x00, 0x03, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x16, 0x00, 0x03, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x17, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, + 0x0A, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x3B, 0x00, 0x04, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x04, 0x00, 0x0D, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, + 0x0E, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00, + 0x3B, 0x00, 0x04, 0x00, 0x0E, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, + 0x09, 0x00, 0x00, 0x00, 0x15, 0x00, 0x04, 0x00, 0x10, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, + 0x10, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x04, 0x00, 0x12, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, 0x10, 0x00, 0x00, 0x00, + 0x16, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x00, 0x02, 0x00, + 0x1A, 0x00, 0x00, 0x00, 0x15, 0x00, 0x04, 0x00, 0x1B, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, + 0x1B, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x04, 0x00, 0x1D, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x3F, + 0x2B, 0x00, 0x04, 0x00, 0x1B, 0x00, 0x00, 0x00, 0x2D, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x17, 0x00, 0x04, 0x00, 0x3B, 0x00, 0x00, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, + 0x3C, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x3B, 0x00, 0x00, 0x00, + 0x3B, 0x00, 0x04, 0x00, 0x3C, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0x2C, 0x00, 0x07, 0x00, 0x3B, 0x00, 0x00, 0x00, + 0x3E, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, 0x32, 0x00, 0x04, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x3F, + 0x19, 0x00, 0x09, 0x00, 0x41, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x1B, 0x00, 0x03, 0x00, 0x42, 0x00, 0x00, 0x00, 0x41, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x04, 0x00, 0x43, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x42, 0x00, 0x00, 0x00, 0x3B, 0x00, 0x04, 0x00, 0x43, 0x00, 0x00, 0x00, + 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x36, 0x00, 0x05, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x05, 0x00, 0x00, 0x00, + 0x3B, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x0C, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x41, 0x00, 0x05, 0x00, + 0x12, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, + 0x11, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x14, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x83, 0x00, 0x05, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, + 0x14, 0x00, 0x00, 0x00, 0x41, 0x00, 0x05, 0x00, 0x12, 0x00, 0x00, 0x00, + 0x17, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, + 0x3D, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, + 0x17, 0x00, 0x00, 0x00, 0x88, 0x00, 0x05, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x19, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, + 0x3E, 0x00, 0x03, 0x00, 0x09, 0x00, 0x00, 0x00, 0x19, 0x00, 0x00, 0x00, + 0x41, 0x00, 0x05, 0x00, 0x1D, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, + 0x09, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, + 0xB8, 0x00, 0x05, 0x00, 0x1A, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, + 0x1F, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0xA8, 0x00, 0x04, 0x00, + 0x1A, 0x00, 0x00, 0x00, 0x22, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, + 0xF7, 0x00, 0x03, 0x00, 0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0xFA, 0x00, 0x04, 0x00, 0x22, 0x00, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, + 0x24, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x23, 0x00, 0x00, 0x00, + 0x41, 0x00, 0x05, 0x00, 0x1D, 0x00, 0x00, 0x00, 0x25, 0x00, 0x00, 0x00, + 0x09, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x26, 0x00, 0x00, 0x00, 0x25, 0x00, 0x00, 0x00, + 0xBA, 0x00, 0x05, 0x00, 0x1A, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, + 0x26, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, 0xF9, 0x00, 0x02, 0x00, + 0x24, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x24, 0x00, 0x00, 0x00, + 0xF5, 0x00, 0x07, 0x00, 0x1A, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, + 0x21, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, + 0x23, 0x00, 0x00, 0x00, 0xA8, 0x00, 0x04, 0x00, 0x1A, 0x00, 0x00, 0x00, + 0x2A, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0xF7, 0x00, 0x03, 0x00, + 0x2C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFA, 0x00, 0x04, 0x00, + 0x2A, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x00, 0x00, 0x2C, 0x00, 0x00, 0x00, + 0xF8, 0x00, 0x02, 0x00, 0x2B, 0x00, 0x00, 0x00, 0x41, 0x00, 0x05, 0x00, + 0x1D, 0x00, 0x00, 0x00, 0x2E, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, + 0x2D, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x2F, 0x00, 0x00, 0x00, 0x2E, 0x00, 0x00, 0x00, 0xB8, 0x00, 0x05, 0x00, + 0x1A, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x2F, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0xF9, 0x00, 0x02, 0x00, 0x2C, 0x00, 0x00, 0x00, + 0xF8, 0x00, 0x02, 0x00, 0x2C, 0x00, 0x00, 0x00, 0xF5, 0x00, 0x07, 0x00, + 0x1A, 0x00, 0x00, 0x00, 0x31, 0x00, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, + 0x24, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x00, 0x00, + 0xA8, 0x00, 0x04, 0x00, 0x1A, 0x00, 0x00, 0x00, 0x32, 0x00, 0x00, 0x00, + 0x31, 0x00, 0x00, 0x00, 0xF7, 0x00, 0x03, 0x00, 0x34, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0xFA, 0x00, 0x04, 0x00, 0x32, 0x00, 0x00, 0x00, + 0x33, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, + 0x33, 0x00, 0x00, 0x00, 0x41, 0x00, 0x05, 0x00, 0x1D, 0x00, 0x00, 0x00, + 0x35, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x2D, 0x00, 0x00, 0x00, + 0x3D, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x36, 0x00, 0x00, 0x00, + 0x35, 0x00, 0x00, 0x00, 0xBA, 0x00, 0x05, 0x00, 0x1A, 0x00, 0x00, 0x00, + 0x37, 0x00, 0x00, 0x00, 0x36, 0x00, 0x00, 0x00, 0x27, 0x00, 0x00, 0x00, + 0xF9, 0x00, 0x02, 0x00, 0x34, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, + 0x34, 0x00, 0x00, 0x00, 0xF5, 0x00, 0x07, 0x00, 0x1A, 0x00, 0x00, 0x00, + 0x38, 0x00, 0x00, 0x00, 0x31, 0x00, 0x00, 0x00, 0x2C, 0x00, 0x00, 0x00, + 0x37, 0x00, 0x00, 0x00, 0x33, 0x00, 0x00, 0x00, 0xF7, 0x00, 0x03, 0x00, + 0x3A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFA, 0x00, 0x04, 0x00, + 0x38, 0x00, 0x00, 0x00, 0x39, 0x00, 0x00, 0x00, 0x3F, 0x00, 0x00, 0x00, + 0xF8, 0x00, 0x02, 0x00, 0x39, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x03, 0x00, + 0x3D, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x00, 0xF9, 0x00, 0x02, 0x00, + 0x3A, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x3F, 0x00, 0x00, 0x00, + 0x3D, 0x00, 0x04, 0x00, 0x42, 0x00, 0x00, 0x00, 0x45, 0x00, 0x00, 0x00, + 0x44, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, + 0x46, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58, 0x00, 0x07, 0x00, + 0x3B, 0x00, 0x00, 0x00, 0x47, 0x00, 0x00, 0x00, 0x45, 0x00, 0x00, 0x00, + 0x46, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x8E, 0x00, 0x05, 0x00, 0x3B, 0x00, 0x00, 0x00, 0x48, 0x00, 0x00, 0x00, + 0x47, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x03, 0x00, + 0x3D, 0x00, 0x00, 0x00, 0x48, 0x00, 0x00, 0x00, 0xF9, 0x00, 0x02, 0x00, + 0x3A, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x3A, 0x00, 0x00, 0x00, + 0xFD, 0x00, 0x01, 0x00, 0x38, 0x00, 0x01, 0x00 +}; \ No newline at end of file diff --git a/resources/vert.spv b/resources/vert.spv deleted file mode 100644 index 924cb24d..00000000 Binary files a/resources/vert.spv and /dev/null differ diff --git a/resources/vert.spv.h b/resources/vert.spv.h new file mode 100644 index 00000000..5aa4174f --- /dev/null +++ b/resources/vert.spv.h @@ -0,0 +1,91 @@ +constexpr unsigned char vertex_shader[] = { + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x0A, 0x00, 0x0D, 0x00, + 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x47, 0x4C, 0x53, 0x4C, 0x2E, 0x73, 0x74, 0x64, 0x2E, 0x34, 0x35, 0x30, + 0x00, 0x00, 0x00, 0x00, 0x0E, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x6D, 0x61, 0x69, 0x6E, 0x00, 0x00, 0x00, 0x00, + 0x0D, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x03, 0x00, 0x02, 0x00, 0x00, 0x00, 0xC2, 0x01, 0x00, 0x00, + 0x04, 0x00, 0x0A, 0x00, 0x47, 0x4C, 0x5F, 0x47, 0x4F, 0x4F, 0x47, 0x4C, + 0x45, 0x5F, 0x63, 0x70, 0x70, 0x5F, 0x73, 0x74, 0x79, 0x6C, 0x65, 0x5F, + 0x6C, 0x69, 0x6E, 0x65, 0x5F, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x69, + 0x76, 0x65, 0x00, 0x00, 0x04, 0x00, 0x08, 0x00, 0x47, 0x4C, 0x5F, 0x47, + 0x4F, 0x4F, 0x47, 0x4C, 0x45, 0x5F, 0x69, 0x6E, 0x63, 0x6C, 0x75, 0x64, + 0x65, 0x5F, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x69, 0x76, 0x65, 0x00, + 0x05, 0x00, 0x04, 0x00, 0x04, 0x00, 0x00, 0x00, 0x6D, 0x61, 0x69, 0x6E, + 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x06, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x67, 0x6C, 0x5F, 0x50, 0x65, 0x72, 0x56, 0x65, 0x72, 0x74, 0x65, 0x78, + 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x06, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x67, 0x6C, 0x5F, 0x50, 0x6F, 0x73, 0x69, 0x74, + 0x69, 0x6F, 0x6E, 0x00, 0x06, 0x00, 0x07, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x67, 0x6C, 0x5F, 0x50, 0x6F, 0x69, 0x6E, 0x74, + 0x53, 0x69, 0x7A, 0x65, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x07, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x67, 0x6C, 0x5F, 0x43, + 0x6C, 0x69, 0x70, 0x44, 0x69, 0x73, 0x74, 0x61, 0x6E, 0x63, 0x65, 0x00, + 0x06, 0x00, 0x07, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, + 0x67, 0x6C, 0x5F, 0x43, 0x75, 0x6C, 0x6C, 0x44, 0x69, 0x73, 0x74, 0x61, + 0x6E, 0x63, 0x65, 0x00, 0x05, 0x00, 0x03, 0x00, 0x0D, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x05, 0x00, 0x12, 0x00, 0x00, 0x00, + 0x50, 0x6F, 0x73, 0x69, 0x74, 0x69, 0x6F, 0x6E, 0x00, 0x00, 0x00, 0x00, + 0x05, 0x00, 0x03, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x76, 0x55, 0x56, 0x00, + 0x48, 0x00, 0x05, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x48, 0x00, 0x05, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x48, 0x00, 0x05, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, + 0x48, 0x00, 0x05, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x47, 0x00, 0x03, 0x00, + 0x0B, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x47, 0x00, 0x04, 0x00, + 0x12, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x47, 0x00, 0x04, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x13, 0x00, 0x02, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x21, 0x00, 0x03, 0x00, 0x03, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x16, 0x00, 0x03, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x17, 0x00, 0x04, 0x00, 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x15, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, + 0x08, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x1C, 0x00, 0x04, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x09, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x06, 0x00, 0x0B, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x0A, 0x00, 0x00, 0x00, + 0x0A, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, 0x0C, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x00, 0x00, 0x3B, 0x00, 0x04, 0x00, + 0x0C, 0x00, 0x00, 0x00, 0x0D, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, + 0x15, 0x00, 0x04, 0x00, 0x0E, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, 0x0E, 0x00, 0x00, 0x00, + 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x17, 0x00, 0x04, 0x00, + 0x10, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x20, 0x00, 0x04, 0x00, 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x10, 0x00, 0x00, 0x00, 0x3B, 0x00, 0x04, 0x00, 0x11, 0x00, 0x00, 0x00, + 0x12, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, + 0x06, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x2B, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x80, 0x3F, 0x20, 0x00, 0x04, 0x00, 0x19, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x04, 0x00, + 0x1B, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, + 0x3B, 0x00, 0x04, 0x00, 0x1B, 0x00, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0x2B, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x1D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3F, 0x36, 0x00, 0x05, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x03, 0x00, 0x00, 0x00, 0xF8, 0x00, 0x02, 0x00, 0x05, 0x00, 0x00, 0x00, + 0x3D, 0x00, 0x04, 0x00, 0x10, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, + 0x12, 0x00, 0x00, 0x00, 0x51, 0x00, 0x05, 0x00, 0x06, 0x00, 0x00, 0x00, + 0x16, 0x00, 0x00, 0x00, 0x13, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x51, 0x00, 0x05, 0x00, 0x06, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, + 0x13, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x50, 0x00, 0x07, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, + 0x17, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, + 0x41, 0x00, 0x05, 0x00, 0x19, 0x00, 0x00, 0x00, 0x1A, 0x00, 0x00, 0x00, + 0x0D, 0x00, 0x00, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x03, 0x00, + 0x1A, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x3D, 0x00, 0x04, 0x00, + 0x10, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, 0x12, 0x00, 0x00, 0x00, + 0x8E, 0x00, 0x05, 0x00, 0x10, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x00, 0x00, + 0x1E, 0x00, 0x00, 0x00, 0x1D, 0x00, 0x00, 0x00, 0x50, 0x00, 0x05, 0x00, + 0x10, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x1D, 0x00, 0x00, 0x00, + 0x1D, 0x00, 0x00, 0x00, 0x81, 0x00, 0x05, 0x00, 0x10, 0x00, 0x00, 0x00, + 0x21, 0x00, 0x00, 0x00, 0x1F, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, + 0x3E, 0x00, 0x03, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x21, 0x00, 0x00, 0x00, + 0xFD, 0x00, 0x01, 0x00, 0x38, 0x00, 0x01, 0x00 +}; diff --git a/src/backend/CMakeLists.txt b/src/backend/CMakeLists.txt index d656ead3..ad78fd97 100644 --- a/src/backend/CMakeLists.txt +++ b/src/backend/CMakeLists.txt @@ -4,4 +4,4 @@ file(GLOB HEADERS *.hpp) add_subdirectory(core) add_library(backend ${SOURCES} ${HEADERS}) -target_link_libraries(backend PRIVATE core) \ No newline at end of file +target_link_libraries(backend PRIVATE core) diff --git a/src/backend/core/Mem.hpp b/src/backend/core/Mem.hpp index 9f9fa035..f7c565a7 100644 --- a/src/backend/core/Mem.hpp +++ b/src/backend/core/Mem.hpp @@ -2,12 +2,13 @@ #include #include #include -#include #include #include #include #include #include +#include +#include namespace n64 { struct ROMHeader { diff --git a/src/frontend/CMakeLists.txt b/src/frontend/CMakeLists.txt index 1d9f8ef1..2e84a4f2 100644 --- a/src/frontend/CMakeLists.txt +++ b/src/frontend/CMakeLists.txt @@ -3,6 +3,7 @@ project(kaizen) if (WIN32) add_compile_definitions(NOMINMAX) + add_compile_definitions(_CRT_SECURE_NO_WARNINGS) endif () if(APPLE) @@ -10,9 +11,13 @@ if(APPLE) enable_language(OBJC) endif() +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + include_directories( . ../ + ../../ ../utils ../backend ../backend/core @@ -40,6 +45,7 @@ include_directories( ../../external/capstone/include ../../external/imgui ../../external/imgui/backends + ../../external/nfd/src/include ../../external/cflags/include ImGuiImpl/ ) @@ -65,22 +71,27 @@ else() set(ARM64 FALSE) endif() +set(SIMD_FLAG NULL) + if(ARM64 AND APPLE) message("Defining USE_NEON...") add_compile_definitions(USE_NEON) - set(HAS_SIMD TRUE) + add_compile_definitions(SIMD_SUPPORT) +elseif(NOT ARM64) + if(MSVC) + set(SIMD_FLAG /arch:AVX) + else() + set(SIMD_FLAG -msse4.1) + endif() + check_c_compiler_flag(${SIMD_FLAG} HAS_SIMD) +else() + message("Compiling on an unsupported Arm device! Good Luck!") endif() -if(NOT ARM64) - check_c_compiler_flag(-msse4.1 HAS_SIMD) -endif () - if (HAS_SIMD) message("Defining SIMD_SUPPORT...") add_compile_definitions(SIMD_SUPPORT) - if(NOT ARM64) - add_compile_options(-msse3 -msse4.1) - endif() + add_compile_options(${SIMD_FLAG}) endif () if (${CMAKE_BUILD_TYPE} MATCHES Debug) @@ -97,6 +108,7 @@ add_subdirectory(../../external/unarr unarr) add_subdirectory(../../external/SDL SDL) add_subdirectory(../../external/cflags cflags) add_subdirectory(../../external/imgui imgui) +add_subdirectory(../../external/nfd nfd) set(CAPSTONE_ARCHITECTURE_DEFAULT OFF) set(CAPSTONE_MIPS_SUPPORT ON) set(CAPSTONE_X86_SUPPORT ON) @@ -110,8 +122,6 @@ add_executable(kaizen RenderWidget.hpp EmuThread.hpp EmuThread.cpp - MainWindow.hpp - MainWindow.cpp SettingsWindow.hpp SettingsWindow.cpp CPUSettings.hpp @@ -124,9 +134,8 @@ add_executable(kaizen Debugger.hpp Debugger.cpp) -target_link_libraries(kaizen PUBLIC imgui SDL3::SDL3 SDL3::SDL3-static cflags::cflags discord-rpc fmt mio nlohmann_json parallel-rdp capstone backend) +target_link_libraries(kaizen PUBLIC imgui nfd SDL3::SDL3 SDL3::SDL3-static cflags::cflags discord-rpc fmt mio nlohmann_json parallel-rdp capstone backend) target_compile_definitions(kaizen PUBLIC SDL_MAIN_HANDLED) -set_target_properties(kaizen PROPERTIES CXX_STANDARD 20 CXX_STANDARD_REQUIRED ON) file(COPY ../../resources/ DESTINATION ${PROJECT_BINARY_DIR}/resources/) file(REMOVE diff --git a/src/frontend/EmuThread.cpp b/src/frontend/EmuThread.cpp index 9e6703c9..fdb7eb0f 100644 --- a/src/frontend/EmuThread.cpp +++ b/src/frontend/EmuThread.cpp @@ -1,7 +1,7 @@ #include #include -EmuThread::EmuThread(const std::shared_ptr &core, std::string &fps, RenderWidget &renderWidget, +EmuThread::EmuThread(const std::shared_ptr &core, double &fps, RenderWidget &renderWidget, SettingsWindow &settings) noexcept : renderWidget(renderWidget), core(core), settings(settings), fps(fps) {} @@ -16,7 +16,7 @@ void EmuThread::start() noexcept { auto sampledFps = 0; static bool oneSecondPassed = false; - fps = fmt::format("{:.2f} FPS", 1000.0 / avgFps); + fps = 1000.0 / avgFps; while (!interruptionRequested) { const auto startFrameTime = std::chrono::high_resolution_clock::now(); @@ -44,7 +44,7 @@ void EmuThread::start() noexcept { lastSample = endFrameTime; avgFps /= sampledFps; sampledFps = 0; - fps = fmt::format("{:.2f} FPS", 1000.0 / avgFps); + fps = 1000.0 / avgFps; } } SetRender(false); diff --git a/src/frontend/EmuThread.hpp b/src/frontend/EmuThread.hpp index 510869b3..9b0193b0 100644 --- a/src/frontend/EmuThread.hpp +++ b/src/frontend/EmuThread.hpp @@ -12,7 +12,7 @@ class EmuThread final { RenderWidget &renderWidget; public: - explicit EmuThread(const std::shared_ptr &, std::string &, RenderWidget &, SettingsWindow &) noexcept; + explicit EmuThread(const std::shared_ptr &, double &, RenderWidget &, SettingsWindow &) noexcept; void start() noexcept; void TogglePause() const noexcept; @@ -24,6 +24,6 @@ public: bool interruptionRequested = false, isRunning = false; std::shared_ptr core; SettingsWindow &settings; - std::string& fps; + double& fps; std::thread thread; }; diff --git a/src/frontend/ImGuiImpl/Combobox.hpp b/src/frontend/ImGuiImpl/Combobox.hpp index cdc1215b..8d97e7e7 100644 --- a/src/frontend/ImGuiImpl/Combobox.hpp +++ b/src/frontend/ImGuiImpl/Combobox.hpp @@ -14,7 +14,7 @@ struct ComboItem { return ret; } - const std::string& getLabel() { return label; } + const std::string& getLabel() const { return label; } void setLabel(const std::string& text) { label = text; } private: bool enabled = true; @@ -24,9 +24,9 @@ private: struct Combobox { Combobox(std::string label, std::vector items, std::string preview = "", bool enabled = true) : label(label), items(items), preview(preview), enabled(enabled) {} - void addItem(ComboItem& item) { - if(std::find(items.begin(), items.end(), - [&item](ComboItem& a) { return a.getLabel() == item.getLabel(); }) != items.end()) + void addItem(const ComboItem& item) { + if(std::find_if(items.begin(), items.end(), + [&item](const ComboItem& a) { return a.getLabel() == item.getLabel(); }) != items.end()) return; items.push_back(item); diff --git a/src/frontend/ImGuiImpl/Menu.hpp b/src/frontend/ImGuiImpl/Menu.hpp new file mode 100644 index 00000000..e85d4146 --- /dev/null +++ b/src/frontend/ImGuiImpl/Menu.hpp @@ -0,0 +1,74 @@ +#pragma once +#include +#include +#include +#include + +namespace gui { +struct MenuItem { + MenuItem(const std::string& label, std::function&& func = nullptr, bool enabled = true) : label(label), exec(std::move(func)), enabled(enabled) {} + bool render() { + bool ret = false; + ImGui::BeginDisabled(!enabled); + if(ImGui::MenuItem(label.c_str())) { + if(exec) + exec(); + ret = true; + } + ImGui::EndDisabled(); + return ret; + } + + void setEnabled(bool v) { enabled = v; } +private: + bool enabled = true; + std::string label; + std::function exec; +}; + +struct Menu { + Menu(const std::string& label, const std::vector& items = {}, bool enabled = true) : label(label), items(items), enabled(enabled) {} + void addMenuItem(const MenuItem& item) { items.push_back(item); } + bool render() { + bool ret = false; + ImGui::BeginDisabled(!enabled); + if(ImGui::BeginMenu(label.c_str())) { + for(auto& item : items) { + ret |= item.render(); + } + ImGui::EndMenu(); + } + ImGui::EndDisabled(); + return ret; + } + void setEnabled(bool v) { enabled = v; } +private: + std::vector items{}; + std::string label{}; + bool enabled = true; +}; + +template +struct MenuBar { + MenuBar(bool enabled = true) : enabled(enabled) {} + void addMenu(const Menu& menu) { menus.push_back(menu); } + bool render() { + bool ret = false; + ImGui::BeginDisabled(!enabled); + auto beginMenuBar = main ? &ImGui::BeginMainMenuBar : &ImGui::BeginMenuBar; + auto endMenuBar = main ? &ImGui::EndMainMenuBar : &ImGui::EndMenuBar; + if(beginMenuBar()) { + for(auto& menu : menus) { + ret |= menu.render(); + } + endMenuBar(); + } + ImGui::EndDisabled(); + return ret; + } + void setEnabled(bool v) { enabled = v; } +private: + bool enabled = true; + std::vector menus{}; +}; +} \ No newline at end of file diff --git a/src/frontend/ImGuiImpl/PopupWindow.hpp b/src/frontend/ImGuiImpl/PopupWindow.hpp new file mode 100644 index 00000000..071b2e70 --- /dev/null +++ b/src/frontend/ImGuiImpl/PopupWindow.hpp @@ -0,0 +1,33 @@ +#include +#include +#include + +namespace gui { +struct PopupWindow { + PopupWindow(const std::string& title, std::function&& func = nullptr, bool opened = true) : title(title), exec(func), opened(opened) {} + void setFunc(std::function&& func) { + exec = func; + } + + bool render() { + ImGui::OpenPopup(title.c_str()); + ImVec2 center = ImGui::GetMainViewport()->GetCenter(); + ImGui::SetNextWindowPos(center, ImGuiCond_Appearing, ImVec2(0.5f, 0.5f)); + + if (ImGui::BeginPopupModal(title.c_str(), &opened, ImGuiWindowFlags_AlwaysAutoResize)) + { + if(exec) + exec(); + ImGui::EndPopup(); + + return true; + } + + return false; + } +private: + std::function exec; + std::string title; + bool opened = true; +}; +} \ No newline at end of file diff --git a/src/frontend/ImGuiImpl/Slider.hpp b/src/frontend/ImGuiImpl/Slider.hpp index a870c633..6d716ca4 100644 --- a/src/frontend/ImGuiImpl/Slider.hpp +++ b/src/frontend/ImGuiImpl/Slider.hpp @@ -5,8 +5,8 @@ namespace gui { template struct Slider { - Slider(const std::string& label, T min = 0, T max = 0, T default = 0) - : val(default), label(label), min(min), max(max) { } + Slider(const std::string& label, T min = 0, T max = 0, T initial_value = 0) + : val(initial_value), label(label), min(min), max(max) { } void setValue(T v) { val = v; } bool render() { diff --git a/src/frontend/ImGuiImpl/StatusBar.hpp b/src/frontend/ImGuiImpl/StatusBar.hpp new file mode 100644 index 00000000..a95b83e3 --- /dev/null +++ b/src/frontend/ImGuiImpl/StatusBar.hpp @@ -0,0 +1,28 @@ +#include +#include + +namespace gui { +struct StatusBar { + StatusBar(std::function&& func = nullptr, bool enabled = true) : exec(func), enabled(enabled) {} + + bool render() { + float statusWindowHeight = ImGui::GetFrameHeight() * 1.4f; + ImGuiViewport* viewport = ImGui::GetMainViewport(); + + ImVec2 statusBarSize, statusBarPos; + + ImGui::SetNextWindowPos(statusBarPos); + ImGui::SetNextWindowSize(statusBarSize); + ImGui::SetNextWindowViewport(viewport->ID); + + ImGuiWindowFlags windowFlags = ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoDocking; + ImGui::Begin("StatusBar", nullptr, windowFlags); + if(exec) + exec(); + ImGui::End(); + } +private: + std::function exec = nullptr; + bool enabled = true; +}; +} \ No newline at end of file diff --git a/src/frontend/ImGuiImpl/TabBar.hpp b/src/frontend/ImGuiImpl/TabBar.hpp index 01acfe5f..6f79c0cd 100644 --- a/src/frontend/ImGuiImpl/TabBar.hpp +++ b/src/frontend/ImGuiImpl/TabBar.hpp @@ -2,18 +2,19 @@ #include #include #include +#include namespace gui { struct TabItem { - TabItem(std::string label, void(*func)(TabItem*, void* userData) = nullptr, void* userData = nullptr, bool enabled = true) : exec(func), enabled(enabled), userData(userData) {} + TabItem(std::string label, std::function&& func, bool enabled = true) : exec(std::move(func)), enabled(enabled) {} bool render() { bool ret = false; ImGui::BeginDisabled(!enabled); if(ImGui::BeginTabItem(label.c_str())) { if(exec) - exec(this, userData); + exec(); ImGui::EndTabItem(); ret = true; } @@ -23,15 +24,12 @@ struct TabItem { private: bool enabled = true; std::string label; - void(*exec)(TabItem*, void* userData); - void* userData; + std::function exec; }; struct TabBar { - TabBar(std::string label) : label(label) {} - void addTab(TabItem tabItem) { - tabs.push_back(tabItem); - } + TabBar(std::string label, const std::vector& items = {}) : label(label), tabs(items) {} + void addTab(TabItem tabItem) { tabs.push_back(tabItem); } bool render() { bool ret = false; diff --git a/src/frontend/KaizenGui.cpp b/src/frontend/KaizenGui.cpp index 223b8e4a..10751cba 100644 --- a/src/frontend/KaizenGui.cpp +++ b/src/frontend/KaizenGui.cpp @@ -1,125 +1,105 @@ -#include #include +#include +#include +#include -namespace fs = std::filesystem; +KaizenGui::KaizenGui() noexcept : core(std::make_shared()), vulkanWidget(core), emuThread(core, fpsCounter, vulkanWidget, settingsWindow) { + emuExitFunc = [&]() { + quit = true; + if (emuThread.isRunning) { + emuThread.requestInterruption(); + while (emuThread.isRunning) {} + } + }; + + menuBar.addMenu({"File", + { + {"Open", [&]() { + NFD::Guard guard; + NFD::UniquePath path; + nfdfilteritem_t filterItem = {"Nintendo 64 roms", "n64,z64,v64,N64,Z64,V64"}; -KaizenGui::KaizenGui() noexcept : mainWindow(core), emuThread(core, mainWindow.fpsCounter, mainWindow.vulkanWidget, settingsWindow) { - // debugger = std::make_unique(); + auto result = NFD::OpenDialog(path, &filterItem, 1); + if(result == NFD_CANCEL) return; + if(result == NFD_ERROR) + Util::panic("Error: {}", NFD::GetError()); + LoadROM(path.get()); + }}, + {"Exit", std::move(emuExitFunc)} + } + }); - ConnectMainWindowSignalsToSlots(); - Util::RPC::GetInstance().Update(Util::RPC::Idling); + menuBar.addMenu({"Emulation", + { + actionPause, + actionStop, + actionReset, + {"Settings", [&]() { + settingsWindow.render(); + }}, + } + }); + + menuBar.addMenu({"Help", + { + {"About", [&]() { + gui::PopupWindow about{"About Kaizen", [&]() { + ImGui::Text("Kaizen is a Nintendo 64 emulator that strives"); + ImGui::Text("to offer a friendly user experience and compatibility."); + ImGui::Text("Kaizen is licensed under the BSD 3-clause license."); + ImGui::Text("Nintendo 64 is a registered trademarks of Nintendo Co., Ltd."); + }}; + }}, + } + }); } -void KaizenGui::ConnectMainWindowSignalsToSlots() noexcept { - connect(settingsWindow.get(), &SettingsWindow::regrabKeyboard, this, [&] { grabKeyboard(); }); +void KaizenGui::LoadROM(const std::string &path) noexcept { + actionPause.setEnabled(true); + actionReset.setEnabled(true); + actionStop.setEnabled(true); + emuThread.start(); + emuThread.core->LoadROM(path); + const auto gameNameDB = emuThread.core->cpu->GetMem().rom.gameNameDB; + Util::RPC::GetInstance().Update(Util::RPC::Playing, gameNameDB); +} - connect(settingsWindow.get(), &SettingsWindow::gotClosed, this, - [&] { mainWindow->vulkanWidget->wsiPlatform->EnableEventPolling(); }); - - connect(settingsWindow.get(), &SettingsWindow::gotOpened, this, - [&] { mainWindow->vulkanWidget->wsiPlatform->DisableEventPolling(); }); - - connect(mainWindow.get(), &MainWindow::OpenSettings, this, [this] { settingsWindow->show(); }); - // connect(mainWindow.get(), &MainWindow::OpenDebugger, this, [this] { debugger->show(); }); - connect(mainWindow.get(), &MainWindow::OpenROM, this, &KaizenGui::LoadROM); - connect(mainWindow.get(), &MainWindow::Exit, this, &KaizenGui::Quit); - connect(mainWindow.get(), &MainWindow::Reset, emuThread.get(), &EmuThread::Reset); - connect(mainWindow.get(), &MainWindow::Stop, this, [this] { emuThread->requestInterruption(); }); - connect(mainWindow.get(), &MainWindow::Pause, emuThread.get(), &EmuThread::TogglePause); +void KaizenGui::handleEvents() { + SDL_Event e; + while(SDL_PollEvent(&e)) { + switch(e.type) { + case SDL_EVENT_QUIT: + emuExitFunc(); + break; + } + } } int KaizenGui::run() { - bool inputForEmu = true; + while(!quit) { + handleEvents(); - if(settingsWindow.render()) { - inputForEmu = false; + menuBar.render(); + + // TODO VULKAN CANVAS + + gui::StatusBar statusBar{[&]() { + ImGui::Text("GUI FPS: %.2f, Emulation FPS: %.2f", ImGui::GetIO().Framerate, fpsCounter); + }}; + + statusBar.render(); } - mainWindow.render(); - return 0; } -void KaizenGui::LoadROM(const QString &path) const noexcept { - mainWindow->actionPause->setEnabled(true); - mainWindow->actionReset->setEnabled(true); - mainWindow->actionStop->setEnabled(true); - emuThread->start(); - emuThread->core->LoadROM(path.toStdString()); - const 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); -} - -void KaizenGui::Quit() const noexcept { - if (emuThread) { - emuThread->requestInterruption(); - while (emuThread->isRunning) {} - } - QApplication::quit(); -} - -void KaizenGui::LoadTAS(const QString &path) const noexcept { - if (emuThread->core->LoadTAS(fs::path(path.toStdString()))) { - const auto gameNameDB = emuThread->core->cpu->GetMem().rom.gameNameDB; - const auto movieName = fs::path(path.toStdString()).stem().string(); +void KaizenGui::LoadTAS(const std::string &path) const noexcept { + if (emuThread.core->LoadTAS(fs::path(path))) { + const auto gameNameDB = emuThread.core->cpu->GetMem().rom.gameNameDB; + const auto movieName = fs::path(path).stem().string(); Util::RPC::GetInstance().Update(Util::RPC::MovieReplay, gameNameDB, movieName); return; } - Util::panic("Could not load TAS movie {}!", path.toStdString()); -} - -void KaizenGui::keyPressEvent(QKeyEvent *e) { - if (settingsWindow->inputSettings->selectedDeviceIsNotKeyboard) - return; - - emuThread->core->pause = true; - n64::Mem &mem = emuThread->core->cpu->GetMem(); - n64::PIF &pif = mem.mmio.si.pif; - - const auto k = static_cast(e->key()); - for (int i = 0; i < 14; i++) { - if (k == settingsWindow->keyMap[i]) - pif.UpdateButton(0, static_cast(i), true); - } - - if (k == settingsWindow->keyMap[14]) - pif.UpdateAxis(0, n64::Controller::Axis::Y, 86); - if (k == settingsWindow->keyMap[15]) - pif.UpdateAxis(0, n64::Controller::Axis::Y, -86); - if (k == settingsWindow->keyMap[16]) - pif.UpdateAxis(0, n64::Controller::Axis::X, -86); - if (k == settingsWindow->keyMap[17]) - pif.UpdateAxis(0, n64::Controller::Axis::X, 86); - - emuThread->core->pause = false; - QWidget::keyPressEvent(e); -} - -void KaizenGui::keyReleaseEvent(QKeyEvent *e) { - if (settingsWindow->inputSettings->selectedDeviceIsNotKeyboard) - return; - - emuThread->core->pause = true; - n64::Mem &mem = emuThread->core->cpu->GetMem(); - n64::PIF &pif = mem.mmio.si.pif; - - const auto k = static_cast(e->key()); - for (int i = 0; i < 14; i++) { - if (k == settingsWindow->keyMap[i]) - pif.UpdateButton(0, static_cast(i), false); - } - - if (k == settingsWindow->keyMap[14]) - pif.UpdateAxis(0, n64::Controller::Axis::Y, 0); - if (k == settingsWindow->keyMap[15]) - pif.UpdateAxis(0, n64::Controller::Axis::Y, 0); - if (k == settingsWindow->keyMap[16]) - pif.UpdateAxis(0, n64::Controller::Axis::X, 0); - if (k == settingsWindow->keyMap[17]) - pif.UpdateAxis(0, n64::Controller::Axis::X, 0); - - emuThread->core->pause = false; - QWidget::keyReleaseEvent(e); -} + Util::panic("Could not load TAS movie {}!", path); +} \ No newline at end of file diff --git a/src/frontend/KaizenGui.hpp b/src/frontend/KaizenGui.hpp index 5111879b..2c2726af 100644 --- a/src/frontend/KaizenGui.hpp +++ b/src/frontend/KaizenGui.hpp @@ -1,24 +1,28 @@ #pragma once -#include +#include +#include +#include #include -#include -#include -#include -#include +#include -class KaizenGui { +class KaizenGui final { public: - KaizenGui() noexcept; - void LoadTAS(const std::string &path) const noexcept; - void LoadROM(const std::string &path) const noexcept; - int run(); - -private: - void Quit() const noexcept; - void ConnectMainWindowSignalsToSlots() noexcept; - MainWindow mainWindow; - SettingsWindow settingsWindow; - EmuThread emuThread; - // std::unique_ptr debugger; + explicit KaizenGui() noexcept; + double fpsCounter; + gui::MenuBar menuBar; + gui::MenuItem actionPause{"Pause"}, actionStop{"Stop"}, actionReset{"Reset"}; std::shared_ptr core; + EmuThread emuThread; + SettingsWindow settingsWindow; + RenderWidget vulkanWidget; + + int run(); + void LoadTAS(const std::string &path) const noexcept; + void LoadROM(const std::string &path) noexcept; +private: + bool quit = false; + void handleEvents(); + std::function emuExitFunc; + + bool textPauseToggle = false; }; diff --git a/src/frontend/MainWindow.cpp b/src/frontend/MainWindow.cpp deleted file mode 100644 index c9d8579c..00000000 --- a/src/frontend/MainWindow.cpp +++ /dev/null @@ -1,153 +0,0 @@ -#include - -MainWindow::MainWindow(const std::shared_ptr &core) noexcept : vulkanWidget(core) { - /* if (objectName().isEmpty()) - setObjectName("MainWindow"); - resize(800, 646); - actionOpenDebuggerWindow = std::make_unique(this); - actionOpenDebuggerWindow->setObjectName("actionOpenDebuggerWindow"); - actionAbout = std::make_unique(this); - actionAbout->setObjectName("actionAbout"); - actionOpen = std::make_unique(this); - actionOpen->setObjectName("actionOpen"); - actionExit = std::make_unique(this); - actionExit->setObjectName("actionExit"); - actionPause = std::make_unique(this); - actionPause->setObjectName("actionPause"); - actionReset = std::make_unique(this); - actionReset->setObjectName("actionReset"); - actionStop = std::make_unique(this); - actionStop->setObjectName("actionStop"); - actionSettings = std::make_unique(this); - actionSettings->setObjectName("actionSettings"); - centralwidget = std::make_unique(this); - centralwidget->setObjectName("centralwidget"); - verticalLayout = std::make_unique(); - verticalLayout->setSpacing(0); - verticalLayout->setObjectName("verticalLayout"); - verticalLayout->setContentsMargins(0, 0, 0, 0); - - verticalLayout->addWidget(vulkanWidget.get()); - - centralwidget->setLayout(verticalLayout.get()); - - setCentralWidget(centralwidget.get()); - menubar = std::make_unique(this); - menubar->setObjectName("menubar"); - menubar->setGeometry(QRect(0, 0, 800, 22)); - menuFile = std::make_unique(menubar.get()); - menuFile->setObjectName("menuFile"); - menuEmulation = std::make_unique(menubar.get()); - menuEmulation->setObjectName("menuEmulation"); - menuTools = std::make_unique(menubar.get()); - menuTools->setObjectName("menuTools"); - menuAbout = std::make_unique(menubar.get()); - menuAbout->setObjectName("menuAbout"); - setMenuBar(menubar.get()); - statusbar = std::make_unique(this); - statusbar->setObjectName("statusbar"); - fpsCounter = std::make_unique("Not playing"); - statusbar->addPermanentWidget(fpsCounter.get()); - setStatusBar(statusbar.get()); - - menubar->addAction(menuFile->menuAction()); - menubar->addAction(menuEmulation->menuAction()); - menubar->addAction(menuTools->menuAction()); - menubar->addAction(menuAbout->menuAction()); - menuFile->addAction(actionOpen.get()); - menuFile->addAction(actionExit.get()); - menuEmulation->addAction(actionSettings.get()); - menuEmulation->addAction(actionPause.get()); - menuEmulation->addAction(actionReset.get()); - menuEmulation->addAction(actionStop.get()); - menuTools->addAction(actionOpenDebuggerWindow.get()); - menuAbout->addAction(actionAbout.get()); - - Retranslate(); - - QMetaObject::connectSlotsByName(this); - actionPause->setDisabled(true); - actionReset->setDisabled(true); - actionStop->setDisabled(true); - vulkanWidget->hide(); - ConnectSignalsToSlots();*/ -} - -void MainWindow::Retranslate() { - /*setWindowTitle(QCoreApplication::translate("MainWindow", "Kaizen", nullptr)); - actionOpenDebuggerWindow->setText(QCoreApplication::translate("MainWindow", "CPU Debugger", nullptr)); - actionOpenDebuggerWindow->setStatusTip(QCoreApplication::translate( - "MainWindow", "Open the CPU debugger window which allows you see registers, memory and disassembled code", - nullptr)); - actionAbout->setText(QCoreApplication::translate("MainWindow", "About Kaizen", nullptr)); - actionAbout->setStatusTip(QCoreApplication::translate("MainWindow", "About this emulator", nullptr)); - actionOpen->setText(QCoreApplication::translate("MainWindow", "Open...", nullptr)); - actionOpen->setStatusTip(QCoreApplication::translate("MainWindow", "Open a ROM", nullptr)); - actionOpen->setShortcut(QCoreApplication::translate("MainWindow", "Ctrl+O", nullptr)); - actionExit->setText(QCoreApplication::translate("MainWindow", "Exit", nullptr)); - actionExit->setStatusTip(QCoreApplication::translate("MainWindow", "Quit the emulator", nullptr)); - actionPause->setText(QCoreApplication::translate("MainWindow", "Pause", nullptr)); - actionPause->setStatusTip(QCoreApplication::translate("MainWindow", "Pause the emulation", nullptr)); - actionReset->setText(QCoreApplication::translate("MainWindow", "Reset", nullptr)); - actionReset->setStatusTip(QCoreApplication::translate("MainWindow", "Reset the emulation", nullptr)); - actionStop->setText(QCoreApplication::translate("MainWindow", "Stop", nullptr)); - actionStop->setStatusTip(QCoreApplication::translate("MainWindow", "Stop the emulation", nullptr)); - actionSettings->setText(QCoreApplication::translate("MainWindow", "Settings", nullptr)); - actionSettings->setToolTip(QCoreApplication::translate("MainWindow", "Settings", nullptr)); - actionSettings->setStatusTip(QCoreApplication::translate("MainWindow", "Open the settings window", nullptr)); - menuFile->setTitle(QCoreApplication::translate("MainWindow", "File", nullptr)); - menuEmulation->setTitle(QCoreApplication::translate("MainWindow", "Emulation", nullptr)); - menuTools->setTitle(QCoreApplication::translate("MainWindow", "Tools", nullptr)); - menuAbout->setTitle(QCoreApplication::translate("MainWindow", "Help", nullptr)); - */ -} // retranslateUi - -void MainWindow::ConnectSignalsToSlots() noexcept { - /* connect(actionOpen.get(), &QAction::triggered, this, [this]() { - const QString file_name = QFileDialog::getOpenFileName( - this, "Nintendo 64 executable", QString(), - "All supported types (*.zip *.ZIP *.7z *.7Z *.rar *.RAR *.tar *.TAR *.n64 *.N64 *.v64 *.V64 *.z64 *.Z64)"); - - if (!file_name.isEmpty()) { - emit OpenROM(file_name); - vulkanWidget->show(); - } - }); - - connect(actionExit.get(), &QAction::triggered, this, [this]() { emit Exit(); }); - - connect(this, &MainWindow::destroyed, this, [this]() { emit Exit(); }); - - connect(actionReset.get(), &QAction::triggered, this, [this]() { emit Reset(); }); - - connect(actionStop.get(), &QAction::triggered, this, [this]() { - setWindowTitle("Kaizen"); - vulkanWidget->hide(); - actionPause->setDisabled(true); - actionReset->setDisabled(true); - actionStop->setDisabled(true); - emit Stop(); - }); - - connect(actionPause.get(), &QAction::triggered, this, [this]() { - textPauseToggle = !textPauseToggle; - actionPause->setText(textPauseToggle ? "Resume" : "Pause"); - emit Pause(); - }); - - connect(actionAbout.get(), &QAction::triggered, this, [this]() { - QMessageBox::about(this, tr("About Kaizen"), - tr("Kaizen is a Nintendo 64 emulator that strives to offer a friendly user " - "experience and great compatibility.\n" - "Kaizen is licensed under the BSD 3-clause license.\n" - "Nintendo 64 is a registered trademarks of Nintendo Co., Ltd.")); - }); - - connect(actionSettings.get(), &QAction::triggered, this, [this]() { emit OpenSettings(); }); - connect(actionOpenDebuggerWindow.get(), &QAction::triggered, this, [this]() { emit OpenDebugger(); }); - */ -} - -bool MainWindow::render() { - -} \ No newline at end of file diff --git a/src/frontend/MainWindow.hpp b/src/frontend/MainWindow.hpp deleted file mode 100644 index 162e326f..00000000 --- a/src/frontend/MainWindow.hpp +++ /dev/null @@ -1,37 +0,0 @@ -#pragma once -#include -#include - -class MainWindow final { -public: - explicit MainWindow(const std::shared_ptr &) noexcept; - std::string fpsCounter; - RenderWidget vulkanWidget; - - bool render(); - -//std::unique_ptr actionOpenDebuggerWindow{}; -//std::unique_ptr actionAbout{}; -//std::unique_ptr actionOpen{}; -//std::unique_ptr actionExit{}; -//std::unique_ptr actionPause{}; -//std::unique_ptr actionReset{}; -//std::unique_ptr actionStop{}; -//std::unique_ptr actionSettings{}; -//std::unique_ptr centralwidget{}; -//std::unique_ptr verticalLayout{}; -//std::unique_ptr vulkanWidget{}; -//std::unique_ptr menubar{}; -//std::unique_ptr menuFile{}; -//std::unique_ptr menuEmulation{}; -//std::unique_ptr menuTools{}; -//std::unique_ptr menuAbout{}; -//std::unique_ptr statusbar{}; -//std::unique_ptr fpsCounter{}; - -private: - void Retranslate(); - void ConnectSignalsToSlots() noexcept; - - bool textPauseToggle = false; -}; diff --git a/src/frontend/RenderWidget.cpp b/src/frontend/RenderWidget.cpp index 60c05e72..11151d06 100644 --- a/src/frontend/RenderWidget.cpp +++ b/src/frontend/RenderWidget.cpp @@ -9,11 +9,11 @@ RenderWidget::RenderWidget(const std::shared_ptr &core) { } imGuiVkInstanceFactory = std::make_shared(); - windowHandle()->setVulkanInstance(&imGuiVkInstanceFactory->handle); - windowHandle()->create(); + //windowHandle()->setVulkanInstance(&imGuiVkInstanceFactory->create_instance()); + //windowHandle()->create(); - wsiPlatform = std::make_shared(core, windowHandle()); - windowInfo = std::make_shared(windowHandle()); + //wsiPlatform = std::make_shared(core, windowHandle()); + // windowInfo = std::make_shared(windowHandle()); } void ImGuiWSIPlatform::poll_input() { diff --git a/src/frontend/SettingsWindow.cpp b/src/frontend/SettingsWindow.cpp index 9cf0615e..16360081 100644 --- a/src/frontend/SettingsWindow.cpp +++ b/src/frontend/SettingsWindow.cpp @@ -1,76 +1,76 @@ #include #include +#include +#include +#include std::string savePath; -SettingsWindow::SettingsWindow() { - settings = JSONOpenOrCreate("resources/settings.json"); - - savePath = JSONGetField(settings, "general", "savePath"); - +SettingsWindow::SettingsWindow() : settings{JSONOpenOrCreate("resources/settings.json")} { keyMap = inputSettings.GetMappedKeys(); - savesFolder.setName(fmt::format(savesFolder.getName(), savePath)); + savesFolder.setName(fmt::format("Save path: {}", + JSONGetField(settings, "general", "savePath"))); - tabs.addTab({"General", [](gui::TabItem* tab, void* userData) { - SettingsWindow* sW = (SettingsWindow*)userData; - if(sW->savesFolder.render()) { - // TODO: HANDLE FILE DIALOG savePath = QFileDialog::getExistingDirectory(this, tr("Select directory")).toStdString(); - sW->savesFolder.setName(fmt::format(sW->savesFolder.getName(), savePath)); - JSONSetField(sW->settings, "general", "savePath", savePath); - sW->apply.setEnabled(true); + tabs.addTab({"General", [&]() { + if(savesFolder.render()) { + NFD::Guard guard; + NFD::UniquePath outPath; + + auto result = NFD::PickFolder(outPath); + if(result == NFD_CANCEL) + return; + if(result == NFD_ERROR) + Util::panic("Error: {}", NFD::GetError()); + + savesFolder.setName(fmt::format("Save path: {}", outPath.get())); + JSONSetField(settings, "general", "savePath", outPath.get()); + apply.setEnabled(true); } - }, this}); + }}); - tabs.addTab({"CPU", [](gui::TabItem* tab, void* userData) { - SettingsWindow* sW = (SettingsWindow*)userData; - CPUSettings& cS = sW->cpuSettings; - gui::PushButton& apply = sW->apply; - - if(cS.render()) { - if(cS.getModified()) - sW->apply.setEnabled(true); - } - }, this}); - - tabs.addTab({"Audio", [](gui::TabItem* tab, void* userData) { - SettingsWindow* sW = (SettingsWindow*)userData; - AudioSettings& aS = sW->audioSettings; - gui::PushButton& apply = sW->apply; - if(aS.render()) { - if(aS.getModified()) + tabs.addTab({"CPU", [&]() { + if(cpuSettings.render()) { + if(cpuSettings.getModified()) apply.setEnabled(true); } - }, this}); + }}); - tabs.addTab({"Input", [](gui::TabItem* tab, void* userData) { - SettingsWindow* sW = (SettingsWindow*)userData; - sW->inputSettings.render(); - InputSettings& iS = sW->inputSettings; - gui::PushButton& apply = sW->apply; - - if(iS.render()) { - if(iS.getModified()) + tabs.addTab({"Audio", [&]() { + if(audioSettings.render()) { + if(audioSettings.getModified()) apply.setEnabled(true); } - }, this}); + }}); + + tabs.addTab({"Input", [&]() { + if(inputSettings.render()) { + if(inputSettings.getModified()) + apply.setEnabled(true); + } + }}); apply.setEnabled(false); + + canvas.setFunc([&]() { + tabs.render(); + + if(apply.render()) { + auto newMap = inputSettings.GetMappedKeys(); + if (keyMap != newMap) + keyMap = newMap; + + apply.setEnabled(false); + std::ofstream file("resources/settings.json"); + file << settings; + file.close(); + } + }); } bool SettingsWindow::render() { - tabs.render(); - - if(apply.render()) { - auto newMap = inputSettings.GetMappedKeys(); - if (keyMap != newMap) - keyMap = newMap; - - apply.setEnabled(false); - std::ofstream file("resources/settings.json"); - file << settings; - file.close(); - } + if(canvas.render()) + return true; return false; } \ No newline at end of file diff --git a/src/frontend/SettingsWindow.hpp b/src/frontend/SettingsWindow.hpp index 7de70166..160570f3 100644 --- a/src/frontend/SettingsWindow.hpp +++ b/src/frontend/SettingsWindow.hpp @@ -3,25 +3,17 @@ #include #include #include +#include #include #include class SettingsWindow final { gui::PushButton cancel{"Cancel"}, apply{"Apply", "", false}, savesFolder{"Open", "Save path: {}"}; + gui::PopupWindow canvas{"Settings"}; + nlohmann::json settings; CPUSettings cpuSettings{settings}; AudioSettings audioSettings{settings}; InputSettings inputSettings{settings}; - //std::unique_ptr cancel = std::make_unique("Cancel"); - //std::unique_ptr apply = std::make_unique("Apply"); - //std::unique_ptr iconProv = std::make_unique(); - //std::unique_ptr folderBtn = std::make_unique(iconProv->icon(QFileIconProvider::Folder), ""); - //std::unique_ptr folderLabelPrefix = std::make_unique("Save files' path: "); - //std::unique_ptr folderLabel; - //std::unique_ptr generalLayout = std::make_unique(); - //std::unique_ptr generalLayoutV = std::make_unique(); - //std::unique_ptr tabs = std::make_unique(); - //std::unique_ptr mainLayout = std::make_unique(); - //std::unique_ptr buttonsLayout = std::make_unique(); public: bool render(); SettingsWindow(); @@ -29,7 +21,5 @@ public: [[nodiscard]] float getVolumeR() const { return audioSettings.volumeR.getValue() / 100.f; } std::array keyMap{}; - nlohmann::json settings; gui::TabBar tabs{"SettingsTabs"}; - //std::unique_ptr generalSettings{}; }; diff --git a/src/frontend/main.cpp b/src/frontend/main.cpp index 2e5f6f49..31753596 100644 --- a/src/frontend/main.cpp +++ b/src/frontend/main.cpp @@ -2,7 +2,7 @@ #include int main(int argc, char **argv) { - KaizenGui kaizenGui; + KaizenGui kaizenGui; cflags::cflags flags; std::string romPath; std::string moviePath; diff --git a/src/utils/MemoryHelpers.hpp b/src/utils/MemoryHelpers.hpp index 5204ed99..5a8ad0a6 100644 --- a/src/utils/MemoryHelpers.hpp +++ b/src/utils/MemoryHelpers.hpp @@ -3,6 +3,8 @@ #include #include #include +#include +#include namespace Util { template