From 4cab4a973ff147b219cf1a67bcc050ed7e3616d5 Mon Sep 17 00:00:00 2001 From: Elisha Riedlinger Date: Tue, 13 Aug 2024 19:58:36 -0700 Subject: [PATCH] Update support for MipMap without width or height --- Dllmain/BuildNo.rc | 2 +- ddraw/IDirectDrawSurfaceX.cpp | 18 +++++++++++++++++- ddraw/IDirectDrawX.cpp | 17 ++++++++++------- 3 files changed, 28 insertions(+), 9 deletions(-) diff --git a/Dllmain/BuildNo.rc b/Dllmain/BuildNo.rc index 1136c60e..168670f9 100644 --- a/Dllmain/BuildNo.rc +++ b/Dllmain/BuildNo.rc @@ -1 +1 @@ -#define BUILD_NUMBER 7090 +#define BUILD_NUMBER 7091 diff --git a/ddraw/IDirectDrawSurfaceX.cpp b/ddraw/IDirectDrawSurfaceX.cpp index 3fdae039..968192e5 100644 --- a/ddraw/IDirectDrawSurfaceX.cpp +++ b/ddraw/IDirectDrawSurfaceX.cpp @@ -3992,6 +3992,12 @@ LPDIRECT3DTEXTURE9 m_IDirectDrawSurfaceX::GetD3d9Texture() return nullptr; } + // Check if surface is render target + if (IsRenderTarget()) + { + LOG_LIMIT(100, __FUNCTION__ << " Error: Render Target textures not implemented!"); + } + return Get3DTexture(); } @@ -4270,8 +4276,9 @@ HRESULT m_IDirectDrawSurfaceX::CreateD3d9Surface() } } // Create render target - else if (IsRenderTarget() || (UseVideoMemory && IsSurface3D())) + else if (IsRenderTarget()) { + // ToDo: if render surface is a texture then create as a texture (MipMaps can be supported on render target textures) surface.Type = D3DTYPE_RENDERTARGET; surface.Pool = D3DPOOL_DEFAULT; BOOL IsLockable = (surface.MultiSampleType || (surfaceDesc2.ddsCaps.dwCaps2 & DDSCAPS2_NOTUSERLOCKABLE)) ? FALSE : TRUE; @@ -5605,6 +5612,15 @@ inline void m_IDirectDrawSurfaceX::InitSurfaceDesc(DWORD DirectXVersion) if ((!(surfaceDesc2.dwFlags & DDSD_MIPMAPCOUNT) || ((surfaceDesc2.dwFlags & DDSD_MIPMAPCOUNT) && surfaceDesc2.dwMipMapCount != 1)) && (surfaceDesc2.ddsCaps.dwCaps & (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE)) == (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE)) { + // Compute width and height + if ((!(surfaceDesc2.dwFlags & (DDSD_WIDTH | DDSD_HEIGHT)) || (!surfaceDesc2.dwWidth && !surfaceDesc2.dwHeight)) && + (surfaceDesc2.dwFlags & DDSD_MIPMAPCOUNT) && surfaceDesc2.dwMipMapCount > 0) + { + surfaceDesc2.dwFlags |= DDSD_WIDTH | DDSD_HEIGHT; + surfaceDesc2.dwWidth = pow(2, surfaceDesc2.dwMipMapCount - 1); + surfaceDesc2.dwHeight = surfaceDesc2.dwWidth; + } + // Compute mipcount DWORD MipMapLevelCount = ((surfaceDesc2.dwFlags & DDSD_MIPMAPCOUNT) && surfaceDesc2.dwMipMapCount) ? surfaceDesc2.dwMipMapCount : GetMaxMipMapLevel(surfaceDesc2.dwWidth, surfaceDesc2.dwHeight); MaxMipMapLevel = MipMapLevelCount; diff --git a/ddraw/IDirectDrawX.cpp b/ddraw/IDirectDrawX.cpp index cb51af55..adf2a7b2 100644 --- a/ddraw/IDirectDrawX.cpp +++ b/ddraw/IDirectDrawX.cpp @@ -569,11 +569,14 @@ HRESULT m_IDirectDrawX::CreateSurface2(LPDDSURFACEDESC2 lpDDSurfaceDesc2, LPDIRE } // Check MipMap count - if ((lpDDSurfaceDesc2->dwFlags & DDSD_MIPMAPCOUNT) && (lpDDSurfaceDesc2->dwMipMapCount != 1) && - (lpDDSurfaceDesc2->ddsCaps.dwCaps & (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE)) == (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE) && - GetMaxMipMapLevel(lpDDSurfaceDesc2->dwWidth, lpDDSurfaceDesc2->dwHeight) < lpDDSurfaceDesc2->dwMipMapCount) - { - LOG_LIMIT(100, __FUNCTION__ << " Error: MipMap count too large. Count: " << lpDDSurfaceDesc2->dwMipMapCount << + if ((lpDDSurfaceDesc2->ddsCaps.dwCaps & (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE)) == (DDSCAPS_MIPMAP | DDSCAPS_COMPLEX | DDSCAPS_TEXTURE) && + (((lpDDSurfaceDesc2->dwFlags & DDSD_MIPMAPCOUNT) && (lpDDSurfaceDesc2->dwMipMapCount != 1) && + ((lpDDSurfaceDesc2->dwFlags & (DDSD_WIDTH | DDSD_HEIGHT)) == (DDSD_WIDTH | DDSD_HEIGHT) && lpDDSurfaceDesc2->dwWidth && lpDDSurfaceDesc2->dwHeight) && + GetMaxMipMapLevel(lpDDSurfaceDesc2->dwWidth, lpDDSurfaceDesc2->dwHeight) < lpDDSurfaceDesc2->dwMipMapCount) || + ((!(lpDDSurfaceDesc2->dwFlags & DDSD_WIDTH) || !(lpDDSurfaceDesc2->dwFlags & DDSD_HEIGHT) || !lpDDSurfaceDesc2->dwWidth || !lpDDSurfaceDesc2->dwHeight) && + (!(lpDDSurfaceDesc2->dwFlags & DDSD_MIPMAPCOUNT) || ((lpDDSurfaceDesc2->dwFlags & DDSD_MIPMAPCOUNT) && (lpDDSurfaceDesc2->dwMipMapCount == 0)))))) + { + LOG_LIMIT(100, __FUNCTION__ << " Error: invalid MipMap count. Count: " << lpDDSurfaceDesc2->dwMipMapCount << " " << lpDDSurfaceDesc2->dwWidth << "x" << lpDDSurfaceDesc2->dwHeight << " Max: " << GetMaxMipMapLevel(lpDDSurfaceDesc2->dwWidth, lpDDSurfaceDesc2->dwHeight)); return DDERR_INVALIDPARAMS; } @@ -700,12 +703,12 @@ HRESULT m_IDirectDrawX::CreateSurface2(LPDDSURFACEDESC2 lpDDSurfaceDesc2, LPDIRE { Desc2.dwRefreshRate = 0; } - if (((Desc2.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) && (Desc2.ddsCaps.dwCaps & DDSCAPS_TEXTURE)) || (Desc2.ddpfPixelFormat.dwFlags & (DDPF_ZBUFFER | DDPF_STENCILBUFFER))) + // Removing texture flags from primary and stencil buffer surfaces + if ((Desc2.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) || (Desc2.ddpfPixelFormat.dwFlags & (DDPF_ZBUFFER | DDPF_STENCILBUFFER))) { Desc2.dwFlags &= ~DDSD_MIPMAPCOUNT; Desc2.ddsCaps.dwCaps &= ~(DDSCAPS_TEXTURE | DDSCAPS_MIPMAP); Desc2.ddsCaps.dwCaps2 &= ~(DDSCAPS2_HINTDYNAMIC | DDSCAPS2_HINTSTATIC | DDSCAPS2_TEXTUREMANAGE | DDSCAPS2_D3DTEXTUREMANAGE); - LOG_LIMIT(100, __FUNCTION__ << " Warning: removing texture flag from primary or stencil buffer surface!"); } // Check for depth stencil surface