From d0020a3b9a6534c65ff0c58ef20483e10adb0bfe Mon Sep 17 00:00:00 2001 From: olebeck <31539311+olebeck@users.noreply.github.com> Date: Wed, 25 Jun 2025 21:40:17 +0200 Subject: [PATCH] avoid sdl renderer for vita, seems broken --- CMakeLists.txt | 2 +- CMakePresets.json | 3 +- ISLE/isleapp.cpp | 3 + miniwin/CMakeLists.txt | 16 +- miniwin/src/d3drm/backends/gxm/Makefile | 6 +- .../src/d3drm/backends/gxm/blit.color.frag.cg | 11 + .../d3drm/backends/gxm/blit.color.frag.gxp | Bin 0 -> 228 bytes .../src/d3drm/backends/gxm/blit.tex.frag.cg | 12 + .../src/d3drm/backends/gxm/blit.tex.frag.gxp | Bin 0 -> 376 bytes miniwin/src/d3drm/backends/gxm/blit.vert.cg | 12 + miniwin/src/d3drm/backends/gxm/blit.vert.gxp | Bin 0 -> 372 bytes miniwin/src/d3drm/backends/gxm/renderer.cpp | 235 +++++---- miniwin/src/d3drm/backends/gxm/utils.h | 41 +- miniwin/src/d3drm/d3drm.cpp | 8 +- miniwin/src/d3drm/d3drmviewport.cpp | 13 +- miniwin/src/ddraw/ddraw.cpp | 15 +- miniwin/src/ddraw/framebuffer.cpp | 6 + miniwin/src/ddraw/framebuffer_vita.cpp | 466 ++++++++++++++++++ miniwin/src/internal/d3drmrenderer.h | 5 +- miniwin/src/internal/d3drmrenderer_gxm.h | 54 +- miniwin/src/internal/ddraw_impl.h | 2 + miniwin/src/internal/framebuffer_impl.h | 5 + miniwin/src/internal/framebuffer_impl_vita.h | 92 ++++ 23 files changed, 863 insertions(+), 144 deletions(-) create mode 100644 miniwin/src/d3drm/backends/gxm/blit.color.frag.cg create mode 100644 miniwin/src/d3drm/backends/gxm/blit.color.frag.gxp create mode 100644 miniwin/src/d3drm/backends/gxm/blit.tex.frag.cg create mode 100644 miniwin/src/d3drm/backends/gxm/blit.tex.frag.gxp create mode 100644 miniwin/src/d3drm/backends/gxm/blit.vert.cg create mode 100644 miniwin/src/d3drm/backends/gxm/blit.vert.gxp create mode 100644 miniwin/src/ddraw/framebuffer_vita.cpp create mode 100644 miniwin/src/internal/framebuffer_impl_vita.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 79c838fb..bb841ea4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -71,7 +71,7 @@ if(VITA) set(CMAKE_POSITION_INDEPENDENT_CODE OFF) set(ISLE_DEBUG OFF) list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}/cmake/modules") - set(VITA_USE_OPENGLES2 ON) + #set(VITA_USE_OPENGLES2 ON) endif() if(VITA_USE_OPENGLES2) diff --git a/CMakePresets.json b/CMakePresets.json index d0147d06..3611ff65 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -18,7 +18,8 @@ "name": "debug", "inherits": ["release"], "cacheVariables": { - "CMAKE_BUILD_TYPE": "Debug" + "CMAKE_BUILD_TYPE": "Debug", + "ISLE_BUILD_CONFIG": false } }, diff --git a/ISLE/isleapp.cpp b/ISLE/isleapp.cpp index ae207002..9ce03ca0 100644 --- a/ISLE/isleapp.cpp +++ b/ISLE/isleapp.cpp @@ -52,6 +52,7 @@ #ifdef __vita__ #include +#define USE_GXM #endif #if defined(__vita__) && defined(USE_OPENGLES2) @@ -724,7 +725,9 @@ MxResult IsleApp::SetupWindow() (HWND) SDL_GetPointerProperty(SDL_GetWindowProperties(window), SDL_PROP_WINDOW_WIN32_HWND_POINTER, NULL); #endif +#if defined(__vita__) && defined(USE_OPENGLES2) DDWindow = window; +#endif SDL_DestroyProperties(props); diff --git a/miniwin/CMakeLists.txt b/miniwin/CMakeLists.txt index 2600bc72..96a2edf2 100644 --- a/miniwin/CMakeLists.txt +++ b/miniwin/CMakeLists.txt @@ -9,7 +9,6 @@ add_library(miniwin STATIC EXCLUDE_FROM_ALL src/ddraw/ddpalette.cpp src/ddraw/ddraw.cpp src/ddraw/ddsurface.cpp - src/ddraw/framebuffer.cpp # D3DRM src/d3drm/d3drm.cpp @@ -22,11 +21,22 @@ add_library(miniwin STATIC EXCLUDE_FROM_ALL src/internal/meshutils.cpp # D3DRM backends - src/d3drm/backends/sdl3gpu/renderer.cpp - src/d3drm/backends/sdl3gpu/shaders/generated/ShaderIndex.cpp src/d3drm/backends/software/renderer.cpp ) +if(VITA) + target_sources(miniwin PRIVATE + src/ddraw/framebuffer_vita.cpp + ) +else() + target_sources(miniwin PRIVATE + src/ddraw/framebuffer.cpp + + src/d3drm/backends/sdl3gpu/renderer.cpp + src/d3drm/backends/sdl3gpu/shaders/generated/ShaderIndex.cpp + ) +endif() + find_package(OpenGL) find_package(GLEW) if(OpenGL_FOUND AND GLEW_FOUND) diff --git a/miniwin/src/d3drm/backends/gxm/Makefile b/miniwin/src/d3drm/backends/gxm/Makefile index 8e4e01b2..356668c6 100644 --- a/miniwin/src/d3drm/backends/gxm/Makefile +++ b/miniwin/src/d3drm/backends/gxm/Makefile @@ -1,4 +1,8 @@ -all: main.frag.gxp main.vert.gxp clear.frag.gxp clear.vert.gxp +shaders += main.frag.gxp main.vert.gxp +shaders += clear.frag.gxp clear.vert.gxp +shaders += blit.color.frag.gxp blit.tex.frag.gxp blit.vert.gxp + +all: $(shaders) %.vert.gxp: %.vert.cg ./psp2cgc.exe -Wperf -profile sce_vp_psp2 $< -o $@ diff --git a/miniwin/src/d3drm/backends/gxm/blit.color.frag.cg b/miniwin/src/d3drm/backends/gxm/blit.color.frag.cg new file mode 100644 index 00000000..74a2fe38 --- /dev/null +++ b/miniwin/src/d3drm/backends/gxm/blit.color.frag.cg @@ -0,0 +1,11 @@ +void main( + float4 vPosition : POSITION, + float2 vTexCoord : TEXCOORD0, + + uniform float4 uColor, + uniform int uUseTexture, + + out float4 outColor : COLOR +) { + outColor = uColor; +} \ No newline at end of file diff --git a/miniwin/src/d3drm/backends/gxm/blit.color.frag.gxp b/miniwin/src/d3drm/backends/gxm/blit.color.frag.gxp new file mode 100644 index 0000000000000000000000000000000000000000..65ac2640480d6e1860c1038ec790b684a5a8c53a GIT binary patch literal 228 zcmZ>d2w-4j4PbuEz`(#$#~r$^eDyO%1_>aKK>$R603#4D0pbE6W@2Cgk|4kcWHT_7 zfY}TT89+J(%0{O^I%0s>!HyX$6#!KLqaC1p3m^@$%K*wpP>f(pVK#%s*d2w-4j4PdTdWMG)-FC5mb&&9whAi)3x0!$zh2tf27AT9v2MZkOp21W)BAio8O zL7)PNOTa7y!2)Fp0O>hE>|nJ(3&dXo#0bF10(2f&EkA<; zA4nWzCJJD8`32%Ta5DU0YMA+d4=;lQ!y%!Dh7Lgqwx*ph{se|bK?$Hi4;oq+A3*dg z`~=aAK*$7y%s>dX0BD0SP+S10*a0N}1Y$ps$zTn{Oe{=59T30-@fMVaNtK4AR`@2C P6lGR0fS4tvMX3w`P!cBE literal 0 HcmV?d00001 diff --git a/miniwin/src/d3drm/backends/gxm/blit.vert.cg b/miniwin/src/d3drm/backends/gxm/blit.vert.cg new file mode 100644 index 00000000..b374bdbb --- /dev/null +++ b/miniwin/src/d3drm/backends/gxm/blit.vert.cg @@ -0,0 +1,12 @@ +void main( + float2 aPosition : POSITION, + float2 aTexCoord : TEXCOORD0, + + uniform float4x4 uScreenMatrix, + + out float4 vPosition : POSITION, + out float2 vTexCoord : TEXCOORD0 +) { + vPosition = mul(uScreenMatrix, float4(aPosition, 0, 1)); + vTexCoord = aTexCoord; +} diff --git a/miniwin/src/d3drm/backends/gxm/blit.vert.gxp b/miniwin/src/d3drm/backends/gxm/blit.vert.gxp new file mode 100644 index 0000000000000000000000000000000000000000..e72b93359a8e8b4fd78d8a892483e4a62cd827b4 GIT binary patch literal 372 zcmZ>d2w-4j4PY)}WMHU$e)gyR_eU)Z43Z2$AOIpjfEkE?0C52jbHIfe8MuM`1|SB3 z5+DZ2V*?context) { + return true; + } + + if(!gxm_init()) { + return false; + } const unsigned int patcherBufferSize = 64 * 1024; const unsigned int patcherVertexUsseSize = 64 * 1024; const unsigned int patcherFragmentUsseSize = 64 * 1024; - - static const SceGxmBlendInfo blendInfoOpaque = { - .colorMask = SCE_GXM_COLOR_MASK_ALL, - .colorFunc = SCE_GXM_BLEND_FUNC_NONE, - .alphaFunc = SCE_GXM_BLEND_FUNC_NONE, - .colorSrc = SCE_GXM_BLEND_FACTOR_ZERO, - .colorDst = SCE_GXM_BLEND_FACTOR_ZERO, - .alphaSrc = SCE_GXM_BLEND_FACTOR_ZERO, - .alphaDst = SCE_GXM_BLEND_FACTOR_ZERO, - }; - - static const SceGxmBlendInfo blendInfoTransparent = { - .colorMask = SCE_GXM_COLOR_MASK_ALL, - .colorFunc = SCE_GXM_BLEND_FUNC_ADD, - .alphaFunc = SCE_GXM_BLEND_FUNC_ADD, - .colorSrc = SCE_GXM_BLEND_FACTOR_SRC_ALPHA, - .colorDst = SCE_GXM_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, - .alphaSrc = SCE_GXM_BLEND_FACTOR_ONE, - .alphaDst = SCE_GXM_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, - }; - data->cdramPool = SDL_gxm_get_cdramPool(); if(!data->cdramPool) { SDL_Log("failed to allocate cdramPool"); @@ -225,7 +228,62 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { if(SCE_ERR(sceGxmShaderPatcherCreate, &patcherParams, &data->shaderPatcher)) { return false; } + return true; +} +static void destroy_gxm_context() { + sceGxmShaderPatcherDestroy(gxm_renderer_context.shaderPatcher); + sceGxmDestroyContext(gxm_renderer_context.context); + vita_mem_fragment_usse_free(gxm_renderer_context.fragmentUsseRingBufferUid); + vita_mem_free(gxm_renderer_context.fragmentRingBufferUid); + vita_mem_free(gxm_renderer_context.vertexRingBufferUid); + vita_mem_free(gxm_renderer_context.vdmRingBufferUid); + SDL_free(gxm_renderer_context.contextHostMem); +} + +bool get_gxm_context(SceGxmContext** context, SceGxmShaderPatcher** shaderPatcher, SceClibMspace* cdramPool) { + if(!create_gxm_context()) { + return false; + } + *context = gxm_renderer_context.context; + *shaderPatcher = gxm_renderer_context.shaderPatcher; + *cdramPool = gxm_renderer_context.cdramPool; + return true; +} + + +static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { + const unsigned int alignedWidth = ALIGN(width, SCE_GXM_TILE_SIZEX); + const unsigned int alignedHeight = ALIGN(height, SCE_GXM_TILE_SIZEY); + + unsigned int sampleCount = alignedWidth * alignedHeight; + unsigned int depthStrideInSamples = alignedWidth; + + if(!get_gxm_context(&data->context, &data->shaderPatcher, &data->cdramPool)) { + return false; + } + + static const SceGxmBlendInfo blendInfoOpaque = { + .colorMask = SCE_GXM_COLOR_MASK_ALL, + .colorFunc = SCE_GXM_BLEND_FUNC_NONE, + .alphaFunc = SCE_GXM_BLEND_FUNC_NONE, + .colorSrc = SCE_GXM_BLEND_FACTOR_ZERO, + .colorDst = SCE_GXM_BLEND_FACTOR_ZERO, + .alphaSrc = SCE_GXM_BLEND_FACTOR_ZERO, + .alphaDst = SCE_GXM_BLEND_FACTOR_ZERO, + }; + + static const SceGxmBlendInfo blendInfoTransparent = { + .colorMask = SCE_GXM_COLOR_MASK_ALL, + .colorFunc = SCE_GXM_BLEND_FUNC_ADD, + .alphaFunc = SCE_GXM_BLEND_FUNC_ADD, + .colorSrc = SCE_GXM_BLEND_FACTOR_SRC_ALPHA, + .colorDst = SCE_GXM_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, + .alphaSrc = SCE_GXM_BLEND_FACTOR_ONE, + .alphaDst = SCE_GXM_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, + }; + + /* // render target SceGxmRenderTargetParams renderTargetParams; memset(&renderTargetParams, 0, sizeof(SceGxmRenderTargetParams)); @@ -265,6 +323,7 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { if(SCE_ERR(sceGxmSyncObjectCreate, &data->renderBufferSync)) { return false; } + */ // depth & stencil @@ -308,7 +367,7 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { if(SCE_ERR(sceGxmShaderPatcherRegisterProgram, data->shaderPatcher, clearFragmentProgramGxp, &data->clearFragmentProgramId)) { return false; } - GET_SHADER_PARAM(positionAttribute, clearVertexProgramGxp, "aPosition"); + GET_SHADER_PARAM(positionAttribute, clearVertexProgramGxp, "aPosition", false); SceGxmVertexAttribute vertexAttributes[1]; SceGxmVertexStream vertexStreams[1]; @@ -352,9 +411,9 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { return false; } - GET_SHADER_PARAM(positionAttribute, mainVertexProgramGxp, "aPosition"); - GET_SHADER_PARAM(normalAttribute, mainVertexProgramGxp, "aNormal"); - GET_SHADER_PARAM(texCoordAttribute, mainVertexProgramGxp, "aTexCoord"); + GET_SHADER_PARAM(positionAttribute, mainVertexProgramGxp, "aPosition", false); + GET_SHADER_PARAM(normalAttribute, mainVertexProgramGxp, "aNormal", false); + GET_SHADER_PARAM(texCoordAttribute, mainVertexProgramGxp, "aTexCoord", false); SceGxmVertexAttribute vertexAttributes[3]; SceGxmVertexStream vertexStreams[1]; @@ -415,6 +474,8 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { // clear mesh + const size_t clearMeshVerticiesSize = 3 * sizeof(float)*2; + const size_t clearMeshIndiciesSize = 3 * sizeof(uint16_t); data->clearMeshBuffer = sceClibMspaceMalloc(data->cdramPool, clearMeshVerticiesSize + clearMeshIndiciesSize); data->clearVerticies = (float*)data->clearMeshBuffer; data->clearIndicies = (uint16_t*)((uint8_t*)(data->clearMeshBuffer)+clearMeshVerticiesSize); @@ -434,18 +495,6 @@ static bool create_gxm_renderer(int width, int height, GXMRendererData* data) { data->lightDataBuffer = sceClibMspaceMalloc(data->cdramPool, 3 * sizeof(SceneLightGXM) + 4 // 3 lights + light count ); - sceGxmSetFragmentUniformBuffer(data->context, 0, data->lightDataBuffer); - - sceGxmSetFrontStencilRef(data->context, 1); - sceGxmSetFrontStencilFunc( - data->context, - SCE_GXM_STENCIL_FUNC_ALWAYS, - SCE_GXM_STENCIL_OP_KEEP, - SCE_GXM_STENCIL_OP_KEEP, - SCE_GXM_STENCIL_OP_KEEP, - 0xFF, - 0xFF - ); return true; } @@ -486,34 +535,20 @@ extern "C" void load_razor() { } } +Direct3DRMRenderer* GXMRenderer::Create(IDirectDrawSurface* surface) +{ + DDSURFACEDESC DDSDesc; + DDSDesc.dwSize = sizeof(DDSURFACEDESC); + surface->GetSurfaceDesc(&DDSDesc); + int width = DDSDesc.dwWidth; + int height = DDSDesc.dwHeight; -bool gxm_init() { - if(SDL_gxm_is_init()) { - return true; + FrameBufferImpl* frameBuffer = static_cast(surface); + if(!frameBuffer) { + SDL_Log("cant create with something that isnt a framebuffer"); + return nullptr; } - SDL_gxm_init(); - - /* - SceGxmInitializeParams initializeParams; - SDL_memset(&initializeParams, 0, sizeof(SceGxmInitializeParams)); - initializeParams.flags = 0; - initializeParams.displayQueueMaxPendingCount = VITA_GXM_PENDING_SWAPS; - initializeParams.displayQueueCallback = display_callback; - initializeParams.displayQueueCallbackDataSize = sizeof(GXMDisplayData); - initializeParams.parameterBufferSize = SCE_GXM_DEFAULT_PARAMETER_BUFFER_SIZE; - - int err = sceGxmInitialize(&initializeParams); - if (err != 0) { - SDL_LogError(SDL_LOG_CATEGORY_RENDER, "gxm init failed: %d", err); - return err; - } - */ - return true; -} - -Direct3DRMRenderer* GXMRenderer::Create(DWORD width, DWORD height) -{ SDL_Log("GXMRenderer::Create width=%d height=%d", width, height); bool success = gxm_init(); @@ -526,6 +561,7 @@ Direct3DRMRenderer* GXMRenderer::Create(DWORD width, DWORD height) if(!success) { return nullptr; } + gxm_data.frameBuffer = frameBuffer; return new GXMRenderer(width, height, gxm_data); } @@ -541,23 +577,17 @@ GXMRenderer::~GXMRenderer() { if(!m_initialized) { return; } - sceGxmShaderPatcherDestroy(this->m_data.shaderPatcher); - sceGxmDestroyRenderTarget(this->m_data.renderTarget); + /* + sceGxmDestroyRenderTarget(this->m_data.renderTarget); vita_mem_free(this->m_data.renderBufferUid); sceGxmSyncObjectDestroy(this->m_data.renderBufferSync); + */ vita_mem_free(this->m_data.depthBufferUid); this->m_data.depthBufferData = nullptr; vita_mem_free(this->m_data.stencilBufferUid); this->m_data.stencilBufferData = nullptr; - - sceGxmDestroyContext(this->m_data.context); - vita_mem_fragment_usse_free(this->m_data.fragmentUsseRingBufferUid); - vita_mem_free(this->m_data.fragmentRingBufferUid); - vita_mem_free(this->m_data.vertexRingBufferUid); - vita_mem_free(this->m_data.vdmRingBufferUid); - SDL_free(this->m_data.contextHostMem); } void* GXMRenderer::AllocateGpu(size_t size, size_t align) { @@ -811,19 +841,39 @@ HRESULT GXMRenderer::BeginFrame() razor_triggered = true; } + SceGxmRenderTarget* renderTarget = this->m_data.frameBuffer->GetRenderTarget(); + GXMDisplayBuffer* backBuffer = this->m_data.frameBuffer->backBuffer(); + sceGxmBeginScene( this->m_data.context, 0, - this->m_data.renderTarget, + renderTarget, + //this->m_data.renderTarget, nullptr, nullptr, - this->m_data.renderBufferSync, - &this->m_data.renderSurface, + backBuffer->sync, + &backBuffer->surface, + //this->m_data.renderBufferSync, + //&this->m_data.renderSurface, &this->m_data.depthSurface ); sceGxmSetViewport(this->m_data.context, 0, m_width, 0, m_height, 0, 0); + sceGxmSetFragmentUniformBuffer(this->m_data.context, 0, this->m_data.lightDataBuffer); + + sceGxmSetFrontStencilRef(this->m_data.context, 1); + sceGxmSetFrontStencilFunc( + this->m_data.context, + SCE_GXM_STENCIL_FUNC_ALWAYS, + SCE_GXM_STENCIL_OP_KEEP, + SCE_GXM_STENCIL_OP_KEEP, + SCE_GXM_STENCIL_OP_KEEP, + 0xFF, + 0xFF + ); + sceGxmSetFrontDepthFunc(this->m_data.context, SCE_GXM_DEPTH_FUNC_ALWAYS); + // clear screen sceGxmSetVertexProgram(this->m_data.context, this->m_data.clearVertexProgram); sceGxmSetFragmentProgram(this->m_data.context, this->m_data.clearFragmentProgram); @@ -871,13 +921,6 @@ void GXMRenderer::EnableTransparency() sceGxmSetFragmentProgram(this->m_data.context, this->m_data.transparentFragmentProgram); } -#define SET_UNIFORM(buffer, param, value) \ - do { \ - size_t __offset = sceGxmProgramParameterGetResourceIndex(param); \ - void* __dst = (uint8_t*)(buffer) + (__offset * sizeof(uint32_t)); \ - memcpy(__dst, reinterpret_cast(&(value)), sizeof(value)); \ - } while (0) - void TransposeD3DRMMATRIX4D(const D3DRMMATRIX4D input, D3DRMMATRIX4D output) { for (int i = 0; i < 4; ++i) { for (int j = 0; j < 4; ++j) { @@ -937,12 +980,14 @@ HRESULT GXMRenderer::FinalizeFrame() nullptr, nullptr ); + /* SDL_Surface* renderedImage = SDL_CreateSurfaceFrom( m_width, m_height, SDL_PIXELFORMAT_ABGR8888, this->m_data.renderBuffer, this->m_width*4 ); SDL_BlitSurface(renderedImage, nullptr, DDBackBuffer, nullptr); SDL_DestroySurface(renderedImage); + */ return DD_OK; } diff --git a/miniwin/src/d3drm/backends/gxm/utils.h b/miniwin/src/d3drm/backends/gxm/utils.h index c0bfdd07..ed73c390 100644 --- a/miniwin/src/d3drm/backends/gxm/utils.h +++ b/miniwin/src/d3drm/backends/gxm/utils.h @@ -1,17 +1,17 @@ #pragma once #include +#include +#include -static bool _sce_err(const char* expr, int err) { - if(err >= 0) { - SDL_Log("sce: %s", expr); - return false; - } - SDL_Log("SCE_ERR: %s failed 0x%x", expr, err); - return true; -} - -#define SCE_ERR(func, ...) _sce_err(#func, func(__VA_ARGS__)) +#define SCE_ERR(func, ...) ({ \ + sceClibPrintf(#func "\n"); \ + int __sce_err_ret_val = func(__VA_ARGS__); \ + if (__sce_err_ret_val < 0) { \ + sceClibPrintf(#func " error: 0x%x\n", __sce_err_ret_val); \ + } \ + __sce_err_ret_val < 0; \ +}) #define ALIGN(x, a) (((x) + ((a)-1)) & ~((a)-1)) @@ -22,3 +22,24 @@ static bool _sce_err(const char* expr, int err) { ".incbin \"" filename "\"" \ ); \ extern const void* symbol + +#define SET_UNIFORM(buffer, param, value) \ + do { \ + size_t __offset = sceGxmProgramParameterGetResourceIndex(param); \ + void* __dst = (uint8_t*)(buffer) + (__offset * sizeof(uint32_t)); \ + memcpy(__dst, reinterpret_cast(&(value)), sizeof(value)); \ + } while (0) + +#define GET_SHADER_PARAM(var, gxp, name, ret) \ + const SceGxmProgramParameter* var = sceGxmProgramFindParameterByName(gxp, name); \ + if(!var) { \ + SDL_Log("Failed to find param %s", name); \ + return ret; \ + } + + +extern const SceGxmProgram* blitVertexProgramGxp; +extern const SceGxmProgram* blitColorFragmentProgramGxp; +extern const SceGxmProgram* blitTexFragmentProgramGxp; + +bool get_gxm_context(SceGxmContext** context, SceGxmShaderPatcher** shaderPatcher, SceClibMspace* cdramPool); diff --git a/miniwin/src/d3drm/d3drm.cpp b/miniwin/src/d3drm/d3drm.cpp index 89385ab9..a1f82e49 100644 --- a/miniwin/src/d3drm/d3drm.cpp +++ b/miniwin/src/d3drm/d3drm.cpp @@ -147,9 +147,13 @@ HRESULT Direct3DRMImpl::CreateDeviceFromSurface( surface->GetSurfaceDesc(&DDSDesc); Direct3DRMRenderer* renderer; - if (SDL_memcmp(&guid, &SDL3_GPU_GUID, sizeof(GUID)) == 0) { + + if(false) {} +#ifndef __vita__ + else if (SDL_memcmp(&guid, &SDL3_GPU_GUID, sizeof(GUID)) == 0) { renderer = Direct3DRMSDL3GPURenderer::Create(DDSDesc.dwWidth, DDSDesc.dwHeight); } +#endif else if (SDL_memcmp(&guid, &SOFTWARE_GUID, sizeof(GUID)) == 0) { renderer = new Direct3DRMSoftwareRenderer(DDSDesc.dwWidth, DDSDesc.dwHeight); } @@ -170,7 +174,7 @@ HRESULT Direct3DRMImpl::CreateDeviceFromSurface( #endif #ifdef __vita__ else if (SDL_memcmp(&guid, &GXM_GUID, sizeof(GUID)) == 0) { - renderer = GXMRenderer::Create(DDSDesc.dwWidth, DDSDesc.dwHeight); + renderer = GXMRenderer::Create(surface); } #endif else { diff --git a/miniwin/src/d3drm/d3drmviewport.cpp b/miniwin/src/d3drm/d3drmviewport.cpp index 933cbbcd..1a9efaa6 100644 --- a/miniwin/src/d3drm/d3drmviewport.cpp +++ b/miniwin/src/d3drm/d3drmviewport.cpp @@ -349,17 +349,14 @@ HRESULT Direct3DRMViewportImpl::ForceUpdate(int x, int y, int w, int h) HRESULT Direct3DRMViewportImpl::Clear() { - if (!DDBackBuffer) { + if (!DDFrameBuffer) { return DDERR_GENERIC; } - uint8_t r = (m_backgroundColor >> 16) & 0xFF; - uint8_t g = (m_backgroundColor >> 8) & 0xFF; - uint8_t b = m_backgroundColor & 0xFF; - - Uint32 color = SDL_MapRGB(SDL_GetPixelFormatDetails(DDBackBuffer->format), nullptr, r, g, b); - SDL_FillSurfaceRect(DDBackBuffer, nullptr, color); - + DDBLTFX DDBltFx; + DDBltFx.dwSize = sizeof(DDBLTFX); + DDBltFx.dwFillColor = m_backgroundColor; + DDFrameBuffer->Blt(nullptr, nullptr, nullptr, DDBLT_COLORFILL, &DDBltFx); return DD_OK; } diff --git a/miniwin/src/ddraw/ddraw.cpp b/miniwin/src/ddraw/ddraw.cpp index c8d38fd2..25e3dacc 100644 --- a/miniwin/src/ddraw/ddraw.cpp +++ b/miniwin/src/ddraw/ddraw.cpp @@ -28,7 +28,9 @@ SDL_Window* DDWindow; SDL_Surface* DDBackBuffer; FrameBufferImpl* DDFrameBuffer; +#ifndef __vita__ SDL_Renderer* DDRenderer; +#endif HRESULT DirectDrawImpl::QueryInterface(const GUID& riid, void** ppvObject) { @@ -85,7 +87,11 @@ HRESULT DirectDrawImpl::CreateSurface( return DD_OK; } if ((lpDDSurfaceDesc->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) == DDSCAPS_PRIMARYSURFACE) { +#ifdef __vita__ + DDFrameBuffer = new FrameBufferImpl(lpDDSurfaceDesc); +#else DDFrameBuffer = new FrameBufferImpl(); +#endif *lplpDDSurface = static_cast(DDFrameBuffer); return DD_OK; } @@ -316,9 +322,11 @@ HRESULT DirectDrawImpl::SetCooperativeLevel(HWND hWnd, DDSCLFlags dwFlags) #endif } DDWindow = sdlWindow; +#ifndef __vita__ DDRenderer = SDL_CreateRenderer(DDWindow, sdlRendererName); SDL_PropertiesID prop = SDL_GetRendererProperties(DDRenderer); SDL_SetRenderLogicalPresentation(DDRenderer, 640, 480, SDL_LOGICAL_PRESENTATION_LETTERBOX); +#endif } return DD_OK; } @@ -340,9 +348,12 @@ HRESULT DirectDrawImpl::CreateDevice( pBackBuffer->GetSurfaceDesc(&DDSDesc); Direct3DRMRenderer* renderer; - if (SDL_memcmp(&guid, &SDL3_GPU_GUID, sizeof(GUID)) == 0) { + if(false) {} +#ifndef __vita__ + else if (SDL_memcmp(&guid, &SDL3_GPU_GUID, sizeof(GUID)) == 0) { renderer = Direct3DRMSDL3GPURenderer::Create(DDSDesc.dwWidth, DDSDesc.dwHeight); } +#endif #ifdef USE_OPENGLES2 else if (SDL_memcmp(&guid, &OpenGLES2_GUID, sizeof(GUID)) == 0) { renderer = OpenGLES2Renderer::Create(DDSDesc.dwWidth, DDSDesc.dwHeight); @@ -360,7 +371,7 @@ HRESULT DirectDrawImpl::CreateDevice( #endif #ifdef __vita__ else if (SDL_memcmp(&guid, &GXM_GUID, sizeof(GUID)) == 0) { - renderer = GXMRenderer::Create(DDSDesc.dwWidth, DDSDesc.dwHeight); + renderer = GXMRenderer::Create(pBackBuffer); } #endif else if (SDL_memcmp(&guid, &SOFTWARE_GUID, sizeof(GUID)) == 0) { diff --git a/miniwin/src/ddraw/framebuffer.cpp b/miniwin/src/ddraw/framebuffer.cpp index eee8b7cb..3d1df677 100644 --- a/miniwin/src/ddraw/framebuffer.cpp +++ b/miniwin/src/ddraw/framebuffer.cpp @@ -43,6 +43,8 @@ HRESULT FrameBufferImpl::AddAttachedSurface(LPDIRECTDRAWSURFACE lpDDSAttachedSur return DDERR_GENERIC; } +#include + HRESULT FrameBufferImpl::Blt( LPRECT lpDestRect, LPDIRECTDRAWSURFACE lpDDSrcSurface, @@ -66,6 +68,7 @@ HRESULT FrameBufferImpl::Blt( SDL_FillSurfaceRect(DDBackBuffer, &rect, color); return DD_OK; } + auto start = SDL_GetTicksNS(); auto other = static_cast(lpDDSrcSurface); if (!other) { return DDERR_GENERIC; @@ -89,6 +92,8 @@ HRESULT FrameBufferImpl::Blt( if (blitSource != other->m_surface) { SDL_DestroySurface(blitSource); } + + auto end = SDL_GetTicksNS(); return DD_OK; } @@ -114,6 +119,7 @@ HRESULT FrameBufferImpl::Flip(LPDIRECTDRAWSURFACE lpDDSurfaceTargetOverride, DDF SDL_UpdateTexture(m_uploadBuffer, nullptr, DDBackBuffer->pixels, DDBackBuffer->pitch); SDL_RenderTexture(DDRenderer, m_uploadBuffer, nullptr, nullptr); SDL_RenderPresent(DDRenderer); + printf("Flip\n"); return DD_OK; } diff --git a/miniwin/src/ddraw/framebuffer_vita.cpp b/miniwin/src/ddraw/framebuffer_vita.cpp new file mode 100644 index 00000000..ae9486e9 --- /dev/null +++ b/miniwin/src/ddraw/framebuffer_vita.cpp @@ -0,0 +1,466 @@ +#include "ddpalette_impl.h" +#include "ddraw_impl.h" +#include "dummysurface_impl.h" +#include "framebuffer_impl.h" +#include "miniwin.h" + +#include + +#include "../d3drm/backends/gxm/memory.h" +#include "../d3drm/backends/gxm/utils.h" + +FrameBufferImpl::FrameBufferImpl(LPDDSURFACEDESC lpDDSurfaceDesc) +{ + this->width = 960; + this->height = 544; + + if(!get_gxm_context(&this->context, &this->shaderPatcher, &this->cdramPool)) { + return; + } + + // render target + SceGxmRenderTargetParams renderTargetParams; + memset(&renderTargetParams, 0, sizeof(SceGxmRenderTargetParams)); + renderTargetParams.flags = 0; + renderTargetParams.width = this->width; + renderTargetParams.height = this->height; + renderTargetParams.scenesPerFrame = 1; + renderTargetParams.multisampleMode = 0; + renderTargetParams.multisampleLocations = 0; + renderTargetParams.driverMemBlock = -1; // Invalid UID + + if(SCE_ERR(sceGxmCreateRenderTarget, &renderTargetParams, &this->renderTarget)) { + return; + } + + for(int i = 0; i < VITA_GXM_DISPLAY_BUFFER_COUNT; i++) { + this->displayBuffers[i].data = vita_mem_alloc( + SCE_KERNEL_MEMBLOCK_TYPE_USER_CDRAM_RW, + 4 * this->width * this->height, + SCE_GXM_COLOR_SURFACE_ALIGNMENT, + SCE_GXM_MEMORY_ATTRIB_READ | SCE_GXM_MEMORY_ATTRIB_WRITE, + &this->displayBuffers[i].uid, "display", nullptr); + + if(SCE_ERR(sceGxmColorSurfaceInit, + &this->displayBuffers[i].surface, + SCE_GXM_COLOR_FORMAT_A8B8G8R8, + SCE_GXM_COLOR_SURFACE_LINEAR, + SCE_GXM_COLOR_SURFACE_SCALE_NONE, + SCE_GXM_OUTPUT_REGISTER_SIZE_32BIT, + width, height, width, + this->displayBuffers[i].data + )) { + return; + }; + + if(SCE_ERR(sceGxmSyncObjectCreate, &this->displayBuffers[i].sync)) { + return; + } + } + + + if(SCE_ERR(sceGxmShaderPatcherRegisterProgram, this->shaderPatcher, blitVertexProgramGxp, &this->blitVertexProgramId)) { + return; + } + if(SCE_ERR(sceGxmShaderPatcherRegisterProgram, this->shaderPatcher, blitColorFragmentProgramGxp, &this->blitColorFragmentProgramId)) { + return; + } + if(SCE_ERR(sceGxmShaderPatcherRegisterProgram, this->shaderPatcher, blitTexFragmentProgramGxp, &this->blitTexFragmentProgramId)) { + return; + } + GET_SHADER_PARAM(positionAttribute, blitVertexProgramGxp, "aPosition",); + GET_SHADER_PARAM(texCoordAttribute, blitVertexProgramGxp, "aTexCoord",); + + SceGxmVertexAttribute vertexAttributes[1]; + SceGxmVertexStream vertexStreams[1]; + vertexAttributes[0].streamIndex = 0; + vertexAttributes[0].offset = 0; + vertexAttributes[0].format = SCE_GXM_ATTRIBUTE_FORMAT_F32; + vertexAttributes[0].componentCount = 2; + vertexAttributes[0].regIndex = sceGxmProgramParameterGetResourceIndex(positionAttribute); + vertexAttributes[1].streamIndex = 0; + vertexAttributes[1].offset = 8; + vertexAttributes[1].format = SCE_GXM_ATTRIBUTE_FORMAT_F32; + vertexAttributes[1].componentCount = 2; + vertexAttributes[1].regIndex = sceGxmProgramParameterGetResourceIndex(texCoordAttribute); + vertexStreams[0].stride = sizeof(float)*4; + vertexStreams[0].indexSource = SCE_GXM_INDEX_SOURCE_INDEX_16BIT; + + if(SCE_ERR(sceGxmShaderPatcherCreateVertexProgram, + this->shaderPatcher, + this->blitVertexProgramId, + vertexAttributes, 2, + vertexStreams, 1, + &this->blitVertexProgram + )) { + return; + } + + if(SCE_ERR(sceGxmShaderPatcherCreateFragmentProgram, + this->shaderPatcher, + this->blitColorFragmentProgramId, + SCE_GXM_OUTPUT_REGISTER_FORMAT_UCHAR4, + SCE_GXM_MULTISAMPLE_NONE, + NULL, + blitVertexProgramGxp, + &this->blitColorFragmentProgram + )) { + return; + } + + if(SCE_ERR(sceGxmShaderPatcherCreateFragmentProgram, + this->shaderPatcher, + this->blitTexFragmentProgramId, + SCE_GXM_OUTPUT_REGISTER_FORMAT_UCHAR4, + SCE_GXM_MULTISAMPLE_NONE, + NULL, + blitVertexProgramGxp, + &this->blitTexFragmentProgram + )) { + return; + } + + this->uScreenMatrix = sceGxmProgramFindParameterByName(blitVertexProgramGxp, "uScreenMatrix"); // matrix4 + + this->uColor = sceGxmProgramFindParameterByName(blitColorFragmentProgramGxp, "uColor"); // vec4 + this->uTexMatrix = sceGxmProgramFindParameterByName(blitTexFragmentProgramGxp, "uTexMatrix"); // matrix4 + + const size_t quadMeshVerticiesSize = 4 * sizeof(float)*4; + const size_t quadMeshIndiciesSize = 4 * sizeof(uint16_t); + this->quadMeshBuffer = sceClibMspaceMalloc(this->cdramPool, quadMeshVerticiesSize + quadMeshIndiciesSize); + this->quadVerticies = (float*)this->quadMeshBuffer; + this->quadIndicies = (uint16_t*)((uint8_t*)(this->quadMeshBuffer)+quadMeshVerticiesSize); + + float quadVerts[] = { + // x, y, u, v + -1.0f, -1.0f, 0.0f, 1.0f, // Bottom-left + -1.0f, 1.0f, 0.0f, 0.0f, // Top-left + 1.0f, -1.0f, 1.0f, 1.0f, // Bottom-right + 1.0f, 1.0f, 1.0f, 0.0f // Top-right + }; + memcpy(this->quadVerticies, quadVerts, quadMeshVerticiesSize); + this->quadIndicies[0] = 0; + this->quadIndicies[1] = 1; + this->quadIndicies[2] = 2; + this->quadIndicies[3] = 3; + + this->backBufferIndex = 0; + this->frontBufferIndex = 1; + + DDBackBuffer = SDL_CreateSurfaceFrom(this->width, this->height, SDL_PIXELFORMAT_RGBA8888, nullptr, 0); + if (!DDBackBuffer) { + SDL_LogError(SDL_LOG_CATEGORY_APPLICATION, "Failed to create surface: %s", SDL_GetError()); + } + + DDBackBuffer->pitch = this->width*4; + DDBackBuffer->pixels = this->backBuffer()->data; +} + +FrameBufferImpl::~FrameBufferImpl() +{ + if (m_palette) { + m_palette->Release(); + } +} + +// IUnknown interface +HRESULT FrameBufferImpl::QueryInterface(const GUID& riid, void** ppvObject) +{ + MINIWIN_NOT_IMPLEMENTED(); + return E_NOINTERFACE; +} + +// IDirectDrawSurface interface +HRESULT FrameBufferImpl::AddAttachedSurface(LPDIRECTDRAWSURFACE lpDDSAttachedSurface) +{ + if (dynamic_cast(lpDDSAttachedSurface)) { + return DD_OK; + } + MINIWIN_NOT_IMPLEMENTED(); + return DDERR_GENERIC; +} + +#include + +void calculateTexMatrix(SDL_Rect srcRect, int textureWidth, int textureHeight, float matrix[4][4]) { + float scaleX = srcRect.w / (float)textureWidth; + float scaleY = srcRect.h / (float)textureHeight; + float offsetX = srcRect.x / (float)textureWidth; + float offsetY = srcRect.y / (float)textureHeight; + memset(matrix, 0, sizeof(float) * 16); + matrix[0][0] = scaleX; + matrix[1][1] = scaleY; + matrix[2][2] = 1.0f; + matrix[3][3] = 1.0f; + matrix[0][3] = offsetX; + matrix[1][3] = offsetY; +} + +void calculateScreenMatrix(SDL_Rect dstRect, int screenWidth, int screenHeight, float matrix[4][4]) { + float scaleX = (2.0f * dstRect.w) / screenWidth; + float scaleY = (2.0f * dstRect.h) / screenHeight; + float offsetX = (2.0f * dstRect.x) / screenWidth - 1.0f + scaleX * 0.5f; + float offsetY = 1.0f - (2.0f * dstRect.y) / screenHeight - scaleY * 0.5f; + memset(matrix, 0, sizeof(float) * 16); + matrix[0][0] = scaleX; + matrix[1][1] = scaleY; + matrix[2][2] = 1.0f; + matrix[3][3] = 1.0f; + matrix[0][3] = offsetX; + matrix[1][3] = offsetY; +} +HRESULT FrameBufferImpl::Blt( + LPRECT lpDestRect, + LPDIRECTDRAWSURFACE lpDDSrcSurface, + LPRECT lpSrcRect, + DDBltFlags dwFlags, + LPDDBLTFX lpDDBltFx +) +{ + if (dynamic_cast(lpDDSrcSurface) == this) { + return Flip(nullptr, DDFLIP_WAIT); + } + + if(!sceneStarted) { + SCE_ERR(sceGxmBeginScene, + this->context, + 0, + this->renderTarget, + nullptr, + nullptr, + nullptr, + &this->backBuffer()->surface, + nullptr + ); + + sceGxmSetFrontStencilFunc( + this->context, + SCE_GXM_STENCIL_FUNC_NEVER, + SCE_GXM_STENCIL_OP_KEEP, + SCE_GXM_STENCIL_OP_KEEP, + SCE_GXM_STENCIL_OP_KEEP, + 0xFF, + 0xFF + ); + sceGxmSetFrontDepthFunc(this->context, SCE_GXM_DEPTH_FUNC_ALWAYS); + + sceneStarted = true; + } + + bool colorFill = ((dwFlags & DDBLT_COLORFILL) == DDBLT_COLORFILL); + sceGxmSetVertexProgram(this->context, this->blitVertexProgram); + SCE_ERR(sceGxmSetVertexStream, this->context, 0, this->quadVerticies); + + if(colorFill) { + sceGxmSetFragmentProgram(this->context, this->blitColorFragmentProgram); + } else { + sceGxmSetFragmentProgram(this->context, this->blitTexFragmentProgram); + } + + void* vertUniforms; + void* fragUniforms; + SCE_ERR(sceGxmReserveVertexDefaultUniformBuffer, this->context, &vertUniforms); + SCE_ERR(sceGxmReserveFragmentDefaultUniformBuffer, this->context, &fragUniforms); + + if(colorFill) { + SDL_Rect rect = {0, 0, this->width, this->height}; + + DirectDrawPaletteImpl* ddPal = static_cast(m_palette); + SDL_Palette* sdlPalette = ddPal ? ddPal->m_palette : nullptr; + uint8_t r,g,b,a; + SDL_GetRGBA(lpDDBltFx->dwFillColor, SDL_GetPixelFormatDetails(SDL_PIXELFORMAT_ABGR8888), sdlPalette, &r, &g, &b, &a); + + float screenMatrix[4][4]; + calculateScreenMatrix(rect, this->width, this->height, screenMatrix); + SET_UNIFORM(vertUniforms, this->uScreenMatrix, screenMatrix); + + float color[4] = { + (float)r / 255.0f, + (float)g / 255.0f, + (float)b / 255.0f, + (float)a / 255.0f + }; + SET_UNIFORM(fragUniforms, this->uColor, color); + } else { + auto other = static_cast(lpDDSrcSurface); + if (!other) { + return DDERR_GENERIC; + } + SDL_Surface* blitSource = other->m_surface; + + SDL_Rect srcRect = lpSrcRect ? ConvertRect(lpSrcRect) : SDL_Rect{0, 0, other->m_surface->w, other->m_surface->h}; + SDL_Rect dstRect = lpDestRect ? ConvertRect(lpDestRect) : SDL_Rect{0, 0, this->width, this->height}; + + float screenMatrix[4][4]; + calculateScreenMatrix(dstRect, this->width, this->height, screenMatrix); + SET_UNIFORM(vertUniforms, this->uScreenMatrix, screenMatrix); + + float texMatrix[4][4]; + calculateTexMatrix(srcRect, blitSource->w, blitSource->h, texMatrix); + SET_UNIFORM(vertUniforms, this->uTexMatrix, texMatrix); + + SceGxmTextureFormat texFormat = SCE_GXM_TEXTURE_FORMAT_A8B8G8R8; + SceGxmTexture gxmTexture; + SCE_ERR(sceGxmTextureInitLinear, &gxmTexture, blitSource->pixels, texFormat, blitSource->w, blitSource->h, 0); + sceGxmTextureSetStride(&gxmTexture, blitSource->pitch); + SCE_ERR(sceGxmTextureSetMinFilter, &gxmTexture, SCE_GXM_TEXTURE_FILTER_POINT); + SCE_ERR(sceGxmTextureSetMagFilter, &gxmTexture, SCE_GXM_TEXTURE_FILTER_POINT); + SCE_ERR(sceGxmSetFragmentTexture, this->context, 0, &gxmTexture); + } + + SCE_ERR(sceGxmDraw, + this->context, + SCE_GXM_PRIMITIVE_TRIANGLE_STRIP, + SCE_GXM_INDEX_FORMAT_U16, + this->quadIndicies, + 4 + ); + return DD_OK; +} + +HRESULT FrameBufferImpl::BltFast( + DWORD dwX, + DWORD dwY, + LPDIRECTDRAWSURFACE lpDDSrcSurface, + LPRECT lpSrcRect, + DDBltFastFlags dwTrans +) +{ + RECT destRect = { + (int) dwX, + (int) dwY, + (int) (lpSrcRect->right - lpSrcRect->left + dwX), + (int) (lpSrcRect->bottom - lpSrcRect->top + dwY) + }; + return Blt(&destRect, lpDDSrcSurface, lpSrcRect, DDBLT_NONE, nullptr); +} + +HRESULT FrameBufferImpl::Flip(LPDIRECTDRAWSURFACE lpDDSurfaceTargetOverride, DDFlipFlags dwFlags) +{ + if(this->sceneStarted) { + sceGxmEndScene(this->context, nullptr, nullptr); + this->sceneStarted = false; + } + + sceGxmPadHeartbeat( + &this->displayBuffers[this->backBufferIndex].surface, + this->displayBuffers[this->backBufferIndex].sync + ); + + VITA_GXM_DisplayData displayData; + displayData.address = this->displayBuffers[this->backBufferIndex].data; + + sceGxmDisplayQueueAddEntry( + this->displayBuffers[this->frontBufferIndex].sync, + this->displayBuffers[this->backBufferIndex].sync, + &displayData + ); + + this->frontBufferIndex = this->backBufferIndex; + this->backBufferIndex = (this->backBufferIndex + 1) % VITA_GXM_DISPLAY_BUFFER_COUNT; + + DDBackBuffer->pixels = this->backBuffer()->data; + return DD_OK; +} + +HRESULT FrameBufferImpl::GetAttachedSurface(LPDDSCAPS lpDDSCaps, LPDIRECTDRAWSURFACE* lplpDDAttachedSurface) +{ + if ((lpDDSCaps->dwCaps & DDSCAPS_BACKBUFFER) != DDSCAPS_BACKBUFFER) { + return DDERR_INVALIDPARAMS; + } + *lplpDDAttachedSurface = static_cast(this); + return DD_OK; +} + +HRESULT FrameBufferImpl::GetDC(HDC* lphDC) +{ + MINIWIN_NOT_IMPLEMENTED(); + return DD_OK; +} + +HRESULT FrameBufferImpl::GetPalette(LPDIRECTDRAWPALETTE* lplpDDPalette) +{ + if (!m_palette) { + return DDERR_GENERIC; + } + m_palette->AddRef(); + *lplpDDPalette = m_palette; + return DD_OK; +} + +HRESULT FrameBufferImpl::GetPixelFormat(LPDDPIXELFORMAT lpDDPixelFormat) +{ + memset(lpDDPixelFormat, 0, sizeof(*lpDDPixelFormat)); + lpDDPixelFormat->dwFlags = DDPF_RGB; + lpDDPixelFormat->dwFlags |= DDPF_PALETTEINDEXED8; + lpDDPixelFormat->dwRGBBitCount = 8; + lpDDPixelFormat->dwRBitMask = 0xff; + lpDDPixelFormat->dwGBitMask = 0xff; + lpDDPixelFormat->dwBBitMask = 0xff; + lpDDPixelFormat->dwRGBAlphaBitMask = 0xff; + return DD_OK; +} + +HRESULT FrameBufferImpl::GetSurfaceDesc(LPDDSURFACEDESC lpDDSurfaceDesc) +{ + lpDDSurfaceDesc->dwFlags = DDSD_PIXELFORMAT; + GetPixelFormat(&lpDDSurfaceDesc->ddpfPixelFormat); + lpDDSurfaceDesc->dwFlags |= DDSD_WIDTH | DDSD_HEIGHT; + lpDDSurfaceDesc->dwWidth = this->width; + lpDDSurfaceDesc->dwHeight = this->height; + return DD_OK; +} + +HRESULT FrameBufferImpl::IsLost() +{ + return DD_OK; +} + +HRESULT FrameBufferImpl::Lock(LPRECT lpDestRect, DDSURFACEDESC* lpDDSurfaceDesc, DDLockFlags dwFlags, HANDLE hEvent) +{ + GetSurfaceDesc(lpDDSurfaceDesc); + lpDDSurfaceDesc->lpSurface = this->backBuffer()->data; + lpDDSurfaceDesc->lPitch = this->width*4; + + return DD_OK; +} + +HRESULT FrameBufferImpl::ReleaseDC(HDC hDC) +{ + MINIWIN_NOT_IMPLEMENTED(); + return DD_OK; +} + +HRESULT FrameBufferImpl::Restore() +{ + MINIWIN_NOT_IMPLEMENTED(); + return DD_OK; +} + +HRESULT FrameBufferImpl::SetClipper(LPDIRECTDRAWCLIPPER lpDDClipper) +{ + return DD_OK; +} + +HRESULT FrameBufferImpl::SetColorKey(DDColorKeyFlags dwFlags, LPDDCOLORKEY lpDDColorKey) +{ + MINIWIN_NOT_IMPLEMENTED(); + return DD_OK; +} + +HRESULT FrameBufferImpl::SetPalette(LPDIRECTDRAWPALETTE lpDDPalette) +{ + if (m_palette) { + m_palette->Release(); + } + + m_palette = lpDDPalette; + //SDL_SetSurfacePalette(DDBackBuffer, ((DirectDrawPaletteImpl*) m_palette)->m_palette); + m_palette->AddRef(); + return DD_OK; +} + +HRESULT FrameBufferImpl::Unlock(LPVOID lpSurfaceData) +{ + return DD_OK; +} diff --git a/miniwin/src/internal/d3drmrenderer.h b/miniwin/src/internal/d3drmrenderer.h index e1e7e558..2d8a719d 100644 --- a/miniwin/src/internal/d3drmrenderer.h +++ b/miniwin/src/internal/d3drmrenderer.h @@ -26,7 +26,9 @@ struct Plane { float d; }; +#ifndef __vita__ extern SDL_Renderer* DDRenderer; +#endif class Direct3DRMRenderer : public IDirect3DDevice2 { public: @@ -51,6 +53,7 @@ class Direct3DRMRenderer : public IDirect3DDevice2 { bool ConvertEventToRenderCoordinates(SDL_Event* event) { - return SDL_ConvertEventToRenderCoordinates(DDRenderer, event); + //return SDL_ConvertEventToRenderCoordinates(DDRenderer, event); + return true; } }; diff --git a/miniwin/src/internal/d3drmrenderer_gxm.h b/miniwin/src/internal/d3drmrenderer_gxm.h index 76a12a30..b6e9bd7d 100644 --- a/miniwin/src/internal/d3drmrenderer_gxm.h +++ b/miniwin/src/internal/d3drmrenderer_gxm.h @@ -32,13 +32,8 @@ struct GXMMeshCacheEntry { uint16_t indexCount; }; -typedef struct GXMRendererInit { - SceGxmContext* context; - SceGxmShaderPatcher* shaderPatcher; - SceClibMspace gpuPool; -} GXMRendererInit; - -typedef struct GXMRendererData { +typedef struct GXMRendererContext { + // context SceUID vdmRingBufferUid; SceUID vertexRingBufferUid; SceUID fragmentRingBufferUid; @@ -55,18 +50,7 @@ typedef struct GXMRendererData { void* contextHostMem; SceGxmContext* context; - SceGxmRenderTarget* renderTarget; - SceUID renderBufferUid; - void* renderBuffer; - SceGxmColorSurface renderSurface; - SceGxmSyncObject* renderBufferSync; - - SceUID depthBufferUid; - void* depthBufferData; - SceUID stencilBufferUid; - void* stencilBufferData; - SceGxmDepthStencilSurface depthSurface; - + // shader patcher SceUID patcherBufferUid; void* patcherBuffer; @@ -79,38 +63,68 @@ typedef struct GXMRendererData { void* patcherFragmentUsse; SceGxmShaderPatcher* shaderPatcher; +} GXMRendererContext; +typedef struct GXMRendererData { + SceGxmContext* context; + SceGxmShaderPatcher* shaderPatcher; + SceClibMspace cdramPool; + + // color buffer + /* + SceGxmRenderTarget* renderTarget; + SceUID renderBufferUid; + void* renderBuffer; + SceGxmColorSurface renderSurface; + SceGxmSyncObject* renderBufferSync; + */ + + // depth buffer + SceUID depthBufferUid; + void* depthBufferData; + SceUID stencilBufferUid; + void* stencilBufferData; + SceGxmDepthStencilSurface depthSurface; + + // clear shader SceGxmShaderPatcherId clearVertexProgramId; SceGxmVertexProgram* clearVertexProgram; SceGxmShaderPatcherId clearFragmentProgramId; SceGxmFragmentProgram* clearFragmentProgram; + // main shader SceGxmShaderPatcherId mainVertexProgramId; SceGxmShaderPatcherId mainFragmentProgramId; SceGxmVertexProgram* mainVertexProgram; SceGxmFragmentProgram* opaqueFragmentProgram; SceGxmFragmentProgram* transparentFragmentProgram; + // main shader vertex uniforms const SceGxmProgramParameter* uModelViewMatrixParam; const SceGxmProgramParameter* uNormalMatrixParam; const SceGxmProgramParameter* uProjectionMatrixParam; + // main shader fragment uniforms const SceGxmProgramParameter* uLights; const SceGxmProgramParameter* uLightCount; const SceGxmProgramParameter* uShininess; const SceGxmProgramParameter* uColor; const SceGxmProgramParameter* uUseTexture; + // clear mesh void* clearMeshBuffer; float* clearVerticies; uint16_t* clearIndicies; + // scene light data void* lightDataBuffer; + + FrameBufferImpl* frameBuffer; } GXMRendererData; class GXMRenderer : public Direct3DRMRenderer { public: - static Direct3DRMRenderer* Create(DWORD width, DWORD height); + static Direct3DRMRenderer* Create(IDirectDrawSurface* surface); GXMRenderer( DWORD width, DWORD height, diff --git a/miniwin/src/internal/ddraw_impl.h b/miniwin/src/internal/ddraw_impl.h index 7cefe2f6..56ec2b77 100644 --- a/miniwin/src/internal/ddraw_impl.h +++ b/miniwin/src/internal/ddraw_impl.h @@ -10,7 +10,9 @@ extern SDL_Window* DDWindow; extern SDL_Surface* DDBackBuffer; extern FrameBufferImpl* DDFrameBuffer; +#ifndef __vita__ extern SDL_Renderer* DDRenderer; +#endif inline static SDL_Rect ConvertRect(const RECT* r) { diff --git a/miniwin/src/internal/framebuffer_impl.h b/miniwin/src/internal/framebuffer_impl.h index c2d9e3c8..4ad15c95 100644 --- a/miniwin/src/internal/framebuffer_impl.h +++ b/miniwin/src/internal/framebuffer_impl.h @@ -1,5 +1,9 @@ #pragma once +#ifdef __vita__ +#include "framebuffer_impl_vita.h" +#else + #include #include #include @@ -40,3 +44,4 @@ struct FrameBufferImpl : public IDirectDrawSurface3 { SDL_Texture* m_uploadBuffer; IDirectDrawPalette* m_palette = nullptr; }; +#endif diff --git a/miniwin/src/internal/framebuffer_impl_vita.h b/miniwin/src/internal/framebuffer_impl_vita.h new file mode 100644 index 00000000..f03f0c2b --- /dev/null +++ b/miniwin/src/internal/framebuffer_impl_vita.h @@ -0,0 +1,92 @@ +#pragma once + +#include +#include +#include + +#include +#include +#define VITA_GXM_DISPLAY_BUFFER_COUNT 2 + +typedef struct GXMDisplayBuffer { + SceUID uid; + SceGxmSyncObject* sync; + void* data; + SceGxmColorSurface surface; +} GXMDisplayBuffer; + +typedef struct { + void *address; + int width; + int height; +} GXMDisplayData; + +struct FrameBufferImpl : public IDirectDrawSurface3 { + FrameBufferImpl(LPDDSURFACEDESC lpDDSurfaceDesc); + ~FrameBufferImpl() override; + + // IUnknown interface + HRESULT QueryInterface(const GUID& riid, void** ppvObject) override; + // IDirectDrawSurface interface + HRESULT AddAttachedSurface(IDirectDrawSurface* lpDDSAttachedSurface) override; + HRESULT Blt( + LPRECT lpDestRect, + IDirectDrawSurface* lpDDSrcSurface, + LPRECT lpSrcRect, + DDBltFlags dwFlags, + LPDDBLTFX lpDDBltFx + ) override; + HRESULT BltFast(DWORD dwX, DWORD dwY, IDirectDrawSurface* lpDDSrcSurface, LPRECT lpSrcRect, DDBltFastFlags dwTrans) + override; + HRESULT Flip(IDirectDrawSurface* lpDDSurfaceTargetOverride, DDFlipFlags dwFlags) override; + HRESULT GetAttachedSurface(LPDDSCAPS lpDDSCaps, IDirectDrawSurface** lplpDDAttachedSurface) override; + HRESULT GetDC(HDC* lphDC) override; + HRESULT GetPalette(LPDIRECTDRAWPALETTE* lplpDDPalette) override; + HRESULT GetPixelFormat(LPDDPIXELFORMAT lpDDPixelFormat) override; + HRESULT GetSurfaceDesc(DDSURFACEDESC* lpDDSurfaceDesc) override; + HRESULT IsLost() override; + HRESULT Lock(LPRECT lpDestRect, DDSURFACEDESC* lpDDSurfaceDesc, DDLockFlags dwFlags, HANDLE hEvent) override; + HRESULT ReleaseDC(HDC hDC) override; + HRESULT Restore() override; + HRESULT SetClipper(IDirectDrawClipper* lpDDClipper) override; + HRESULT SetColorKey(DDColorKeyFlags dwFlags, LPDDCOLORKEY lpDDColorKey) override; + HRESULT SetPalette(LPDIRECTDRAWPALETTE lpDDPalette) override; + HRESULT Unlock(LPVOID lpSurfaceData) override; + +// added + inline GXMDisplayBuffer* backBuffer() { + return &displayBuffers[backBufferIndex]; + } + inline SceGxmRenderTarget* GetRenderTarget() { + return this->renderTarget; + } + +private: + SceGxmContext* context; + SceGxmShaderPatcher* shaderPatcher; + SceGxmRenderTarget* renderTarget; + SceClibMspace cdramPool; + + SceGxmShaderPatcherId blitVertexProgramId; + SceGxmVertexProgram* blitVertexProgram; + SceGxmShaderPatcherId blitColorFragmentProgramId; + SceGxmFragmentProgram* blitColorFragmentProgram; + SceGxmShaderPatcherId blitTexFragmentProgramId; + SceGxmFragmentProgram* blitTexFragmentProgram; + + const SceGxmProgramParameter* uScreenMatrix; + const SceGxmProgramParameter* uColor; + const SceGxmProgramParameter* uTexMatrix; + + void* quadMeshBuffer; + float* quadVerticies; + uint16_t* quadIndicies; + + GXMDisplayBuffer displayBuffers[VITA_GXM_DISPLAY_BUFFER_COUNT]; + int backBufferIndex = 0; + int frontBufferIndex = 1; + int width; + int height; + bool sceneStarted; + IDirectDrawPalette* m_palette = nullptr; +};