elishacloud / dxwrapper

Fixes compatibility issues with older games running on Windows 10/11 by wrapping DirectX dlls. Also allows loading custom libraries with the file extension .asi into game processes.
zlib License
1.16k stars 83 forks source link

Dd7to9 offscreen surfaces for Dungeon Keeper 2 #141

Open Trass3r opened 2 years ago

Trass3r commented 2 years ago

After working around #65 Dungeon Keeper 2 is always crashing at the end of the loading screen. It creates a series of weirdly sized DDSCAPS_OFFSCREENPLAIN|DDSCAPS_SYSTEMMEMORY surfaces which get turned into IDirect3DTexture9 textures. I guess the Lock2 is somehow wrong.

With only ConvertToDirectDraw7/ConvertToDirect3D7 it works:

m_IDirectDrawX::CreateSurface2 (00B43460){DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PIXELFORMAT,82,2173,302517504,6103731,302517504,7609384,7610460,0019C828,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0} 4
Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (0F7DC598) converting interface from v4 to v7
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DC598)
m_IDirectDrawSurfaceX::Lock2 (0F7DC598)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DC598)
m_IDirectDrawSurfaceX::Unlock (0F7DC598)
m_IDirectDrawX::CreateSurface2 (00B43460){DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PIXELFORMAT,205,4879,1689704,5992079,1689844,7118016,59568128,006CBAC8,{0x5,0x38cf5b0},{0x50,0x0},{0x5,0x1},{0x19c884,0x639524},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0} 4
Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (0F7DD348) converting interface from v4 to v7
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DD348)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DC598)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DD348)
m_IDirectDrawSurfaceX::Blt (0F7DD348){0,0,206,4880} 0F7565C8 {0,0,82,2174} 16777216 0
m_IDirectDrawSurfaceX::QueryInterface (0F7DC598) IID_GetRealInterface
m_IDirectDrawSurfaceX::Release (0F7DC598) v4
m_IDirectDrawSurfaceX::~m_IDirectDrawSurfaceX (0F7DC598) deleting interface!
m_IDirectDrawX::CreateSurface2 (00B43460){DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PIXELFORMAT,42,20,302517504,6103731,302517504,7609384,7610460,0019C828,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0} 4
Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (0F7DD590) converting interface from v4 to v7
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DD590)
m_IDirectDrawSurfaceX::Lock2 (0F7DD590)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (0F7DD590)
m_IDirectDrawSurfaceX::Unlock (0F7DD590)

Dd7to9:

m_IDirect3DDevice9Ex::BeginScene (09515F50)
m_IDirectDrawX::CreateSurface2 (00A3BB48){0x1007,82,2173,151457024,6103731,151457024,7609384,7610460,0019C828,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0} 4
m_IDirect3D9Ex::CheckDeviceFormat (00A617D0)0 1 D3DFMT_X8R8G8B8 0 D3DRTYPE_SURFACE D3DFMT_X8R8G8B8
Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (095F17F0) converting interface from v4 to v9
m_IDirectDrawSurfaceX::AddRef (095F17F0) v4
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (095F17F0)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (095F17F0):{0x100f,82,2173,328,0,151457024,7609384,0,0019C828,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
m_IDirectDrawSurfaceX::Lock2 (095F17F0){0x0,0,0,0,0,0,0,0,00000000,{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0,0,0x0,0x0,0x0,0x0},0,{{},0x0,0x0,0x0},0},1
m_IDirect3DDevice9Ex::TestCooperativeLevel (09515F50)0
m_IDirectDrawSurfaceX::CreateD3d9Surface (095F17F0) D3d9 Surface size: 82x2174 Format: D3DFMT_X8R8G8B8
m_IDirect3DDevice9Ex::CreateTexture (09515F50)
Creating interface m_IDirect3DTexture9::m_IDirect3DTexture9 (095C5330)
m_IDirect3DDevice9Ex::CreateTexture Succeeded
m_IDirect3DTexture9::LockRect (095C5330)
m_IDirectDrawSurfaceX::ChangeUniquenessValue (095F17F0)
m_IDirectDrawSurfaceX::Lock2 (095F17F0){DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PITCH|DDSD_LPSURFACE|DDSD_PIXELFORMAT,82,2173,328,0,151457024,7609384,0,11BBE040,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
m_IDirectDrawSurfaceX::Lock2 (after){DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PITCH|DDSD_LPSURFACE|DDSD_PIXELFORMAT,82,2173,328,0,151457024,7609384,0,11BBE040,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (095F17F0)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (095F17F0):{0x100f,82,2173,328,0,151457024,7609384,0,0019C828,{0x741c2c,0x5b6015},{0x74205c,0x0},{0x0,0x19c868},{0x741c28,0x474e5089},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
Quiting DxWrapper
full logs https://gist.github.com/Trass3r/6854537d31416ff1b8b68e365db44306 https://gist.github.com/Trass3r/da4f799bfcd6a10253f6fae310f43df1
Trass3r commented 1 year ago

It always seems to crash inside the movie decoding 65CA50 function even with the -nomovies -level mpd6 -32biteverything parameters. The logs show a Lock2 prior to that with garbage input:

m_IDirect3DDeviceX::Clear (08A39810)
m_IDirect3DDevice9Ex::Clear (089EBC90)
m_IDirect3DDeviceX::BeginScene (08A39810)
m_IDirect3DDevice9Ex::BeginScene (089EBC90)
m_IDirectDrawSurfaceX::Lock2 (093E9C88){0x64f2e808,1689268,0,1153611423,1688664,1686932,1691196,1995936688,33D9E5CB,{0xfffffffe,0x19c7d0},{0x64f1434e,0x19c6c0},{0x70d3c0,0x793388},{0x65737341,0x6f697472},{0x64656c69,MAKEFOURCC(':', ' ', 'F', 'a'),1698981227,0x65636976,0x423a3a33,0x6e696765,0x6e656353},1634082926,
    {{ DDSCAPS_3DDEVICE  DDSCAPS_ALLOCONLOAD  DDSCAPS_BACKBUFFER  DDSCAPS_FRONTBUFFER  DDSCAPS_HWCODEC  DDSCAPS_LIVEVIDEO  DDSCAPS_LOCALVIDMEM  DDSCAPS_MODEX  DDSCAPS_NONLOCALVIDMEM  DDSCAPS_OFFSCREENPLAIN  DDSCAPS_PRIMARYSURFACE  DDSCAPS_SYSTEMMEMORY  DDSCAPS_TEXTURE },0x69772039,0x48206874,0x55534552},807425100},1
m_IDirect3DDevice9Ex::TestCooperativeLevel (089EBC90)0
m_IDirectDrawSurfaceX::CreateD3d9Surface (093E9C88) D3d9 Surface size: 128x128 Format: D3DFMT_A8R8G8B8 dwCaps: 0x1800
m_IDirect3DDevice9Ex::CreateTexture (089EBC90)
Creating interface m_IDirect3DTexture9::m_IDirect3DTexture9 (093F8698)
m_IDirect3DTexture9::LockRect (093F8698)
m_IDirect3DTexture9::LockRect (093F8698)
m_IDirectDrawSurfaceX::Lock2 Error: failed to lock surface texture

Other Lock2s before that also fail but don't seem to lead to a crash.

m_IDirectDrawX::CreateSurface2 (00A6CEF8){0x1007,1024,768,1690736,0,1690856,16,5992124,0019CC9C,{0x5b858b,0x19cc9c},{0x742090,0x742094},{0x19cce8,0x742070},{0x19cd48,0x742074},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0} 4
m_IDirect3D9Ex::CheckDeviceFormat (00ABAD10)0 1 D3DFMT_X8R8G8B8 0 D3DRTYPE_SURFACE D3DFMT_X8R8G8B8
Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (09419BF8) converting interface from v4 to v9
m_IDirectDrawSurfaceX::AddRef (09419BF8) v4
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (09419BF8)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (09419BF8):{0x100f,1024,768,4096,0,1690856,16,0,0019CC9C,{0x5b858b,0x19cc9c},{0x742090,0x742094},{0x19cce8,0x742070},{0x19cd48,0x742074},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
m_IDirectDrawSurfaceX::Lock2 (09419BF8){0x0,0,0,0,0,0,0,0,00000000,{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0,0,0x0,0x0,0x0,0x0},0,{{},0x0,0x0,0x0},0},1
m_IDirect3DDevice9Ex::TestCooperativeLevel (08A0AA78)0
m_IDirectDrawSurfaceX::CreateD3d9Surface (09419BF8) D3d9 Surface size: 1024x768 Format: D3DFMT_X8R8G8B8 dwCaps: 0x840
m_IDirect3DDevice9Ex::CreateTexture (08A0AA78)
Creating interface m_IDirect3DTexture9::m_IDirect3DTexture9 (094386E8)
m_IDirect3DTexture9::LockRect (094386E8)
m_IDirect3DTexture9::LockRect (094386E8)
m_IDirectDrawSurfaceX::Lock2 Error: failed to lock surface texture
m_IDirectDrawSurfaceX::Release (09419BF8) v4
m_IDirectDrawSurfaceX::~m_IDirectDrawSurfaceX (09419BF8) deleting interface!
m_IDirectDrawSurfaceX::ReleaseD9Surface Releasing Direct3D9 texture surface
m_IDirect3DTexture9::Release (094386E8)
Trass3r commented 1 year ago
surfaceTexture->LockRect(0, pLockedRect, pRect, Flags);

with Flags=0 returns D3DERR_INVALIDCALL.

https://learn.microsoft.com/en-us/windows/win32/api/d3d9helper/nf-d3d9helper-idirect3dtexture9-lockrect#remarks

Textures created with D3DPOOL_DEFAULT are not lockable.

DDSCAPS_SYSTEMMEMORY | DDSCAPS_OFFSCREENPLAIN is not handled properly in CreateD3d9Surface.

https://learn.microsoft.com/en-us/windows/win32/direct3d9/d3dpool#constants

https://gamedev.stackexchange.com/questions/7993/idirect3ddevice9ex-and-d3dpool-managed

Creating interface m_IDirectDrawSurfaceX::m_IDirectDrawSurfaceX (092FE0F8) converting interface from v4 to v9
m_IDirectDrawSurfaceX::AddRef (092FE0F8) v4
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (092FE0F8)
m_IDirectDrawSurfaceX::GetSurfaceDesc2 (092FE0F8):{0x100f,1024,768,4096,0,1690856,16,0,0019CC9C,{0x5b858b,0x19cc9c},{0x742090,0x742094},{0x19cce8,0x742070},{0x19cd48,0x742074},{0x40,0,32,0xff0000,0xff00,0xff,0x0},32,{{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0},0}
m_IDirectDrawSurfaceX::Lock2 (092FE0F8){0x0,0,0,0,0,0,0,0,00000000,{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0x0},{0x0,0,0,0x0,0x0,0x0,0x0},0,{{},0x0,0x0,0x0},0},1
m_IDirect3DDevice9Ex::TestCooperativeLevel (08A5BEB0)0
m_IDirectDrawSurfaceX::CreateD3d9Surface (092FE0F8) D3d9 Surface size: 1024x768 Format: D3DFMT_X8R8G8B8 ddsCaps: {{ DDSCAPS_OFFSCREENPLAIN  DDSCAPS_SYSTEMMEMORY },0x0,0x0,0x0}
m_IDirect3DDevice9Ex::CreateTexture (08A5BEB0) 1024x768x1 0 D3DFMT_X8R8G8B8 0
Creating interface m_IDirect3DTexture9::m_IDirect3DTexture9 (09317660)
m_IDirect3DTexture9::LockRect (09317660)
m_IDirect3DTexture9::LockRect (09317660)
m_IDirectDrawSurfaceX::Lock2 Error: failed to lock surface texture
m_IDirectDrawSurfaceX::Release (092FE0F8) v4
m_IDirectDrawSurfaceX::~m_IDirectDrawSurfaceX (092FE0F8) deleting interface!
m_IDirectDrawSurfaceX::ReleaseD9Surface Releasing Direct3D9 texture surface
m_IDirect3DTexture9::Release (09317660)
m_IDirectDrawSurfaceX::Blt (08A56508)null 09CE4918 null 16777216 0
m_IDirect3DDevice9Ex::TestCooperativeLevel (08A5BEB0)0
m_IDirectDrawSurfaceX::CreateD3d9Surface (08A56508) D3d9 Surface size: 1024x768 Format: D3DFMT_X8R8G8B8 ddsCaps: {{ DDSCAPS_LOCALVIDMEM  DDSCAPS_VIDEOMEMORY },0x0,0x0,0x0}
m_IDirect3DDevice9Ex::CreateTexture (08A5BEB0) 1024x768x1 0 D3DFMT_X8R8G8B8 0
Creating interface m_IDirect3DTexture9::m_IDirect3DTexture9 (093171A0)
m_IDirectDrawSurfaceX::QueryInterface (08A56730) IID_GetInterfaceX
m_IDirect3DDevice9Ex::TestCooperativeLevel (08A5BEB0)0
m_IDirect3DDevice9Ex::TestCooperativeLevel (08A5BEB0)0
m_IDirect3DTexture9::GetSurfaceLevel (09317020)
Creating interface m_IDirect3DSurface9::m_IDirect3DSurface9 (09D20AD8)
m_IDirect3DTexture9::GetSurfaceLevel (093171A0)
Creating interface m_IDirect3DSurface9::m_IDirect3DSurface9 (09D204A8)
D3DXLoadSurfaceFromSurface
m_IDirect3DSurface9::GetDesc (09D204A8)
m_IDirect3DSurface9::GetDesc (09D20AD8)
m_IDirect3DSurface9::GetDevice (09D20AD8)
m_IDirect3DDevice9Ex::AddRef (08A5BEB0)
m_IDirect3DDevice9Ex::StretchRect (08A5BEB0)
m_IDirect3DDevice9Ex::Release (08A5BEB0)
m_IDirect3DSurface9::GetDesc (09D20AD8)
m_IDirect3DSurface9::LockRect (09D20AD8)
m_IDirect3DSurface9::GetDesc (09D20AD8)
m_IDirect3DSurface9::GetDevice (09D20AD8)
m_IDirect3DDevice9Ex::AddRef (08A5BEB0)
m_IDirect3DDevice9Ex::CreateTexture (08A5BEB0) 1024x768x1 0 D3DFMT_X8R8G8B8 2
elishacloud commented 1 year ago

Yes, I realized this after the change. However, the latest check-in should resolve this issue: 280ba38c49f68353239f0d13cbab0999c602869b

Trass3r commented 1 year ago

Yeah ok now we're back to the original crash I assume. https://gist.github.com/Trass3r/76463d7fc4d5921c53226773f8b65cc6 I added some more logging: https://github.com/elishacloud/dxwrapper/compare/master...Trass3r:dxwrapper:master

elishacloud commented 1 year ago

The issue is that this game uses Direct3D and so far I have only started the conversion from Direct3D to Direct3D9. Only a hand full of Direct3D games work so far. But I do have this game and will take a look later.

Note: this game uses the Direct3D version 3 interfaces. So far the only games I have seen work are the ones that use the Direct3D version 7 interfaces.

Trass3r commented 1 year ago

Yeah I know, on the plus side it doesn't use many D3D features. But it's hard to debug since it crashes deep down in game code when it accesses some surface.

elishacloud commented 1 year ago

Ok, I put a fix in that solves this first issue. There seems to be some other issue I need to look into though.

Trass3r commented 1 year ago

Thanks it starts up now (using the -level parameter). I don't see the keeper hand (which I think is drawn in a special way, in a separate step after everything has been rendered) and it only shows the 1024x768 content in the upper left part the screen.

Other peculiarities of DK2 are the GOG patch messing around with draw calls and also having its own config in %APPDATA%\GOG and multiple windows getting created during startup. I guess for example the video rendering was done with an external EA library that creates its own window.

elishacloud commented 1 year ago

If you set FullscreenWindowMode to 1 then you can start the game normally and see the intro video. The video is done using IID_IMMDeviceEnumerator, which does not interact well with Direct3D9 when in exclusive fullscreen mode.

"I don't see the keeper hand"

Yes, the menu is also not being seen. I'll need to figure out why these items are not being seen. Also, the display looks wrong as it only appears in the upper left corner of the screen:

image

elishacloud commented 1 year ago
  1. You need to run the game in Windows 7 compatibility.
  2. You need to set the following settings in dxwrapper.ini:
[Compatibility]
Dd7to9                     = 1

[Dd7to9]
DdrawOverrideWidth         = 640
DdrawOverrideHeight        = 480

[d3d9]
FullscreenWindowMode       = 1

This does not solve the invisible menu and hand, but otherwise makes everything work.

elishacloud commented 1 year ago

It looks like the game play is in 800x600 but the menu is 640x480. I put a fix in that allows ddraw to get the correct resolution so you don't need to use DdrawOverrideWidth/Height.

Trass3r commented 1 year ago

Yeah they are using different resolutions.

And as I said the GOG patch also fiddles around with those things, e.g. via ScaleMode: https://www.gog.com/forum/dungeon_keeper_series/dk2_gog_configini_extra_settings/post2

It might have to do with the viewport. The structures changed in v5 and v7.

elishacloud commented 1 year ago

And as I said the GOG patch also fiddles around with those things, e.g. via ScaleMode:

After converting it to Direct3D9 we already have many of those types of options: antialiasing, anisotropic filtering, vertical sync, etc. I tried the Direct3D9 antialiasing and it looks pretty good with this game, IMHO.

It might have to do with the viewport. The structures changed in v5 and v7.

There is already code in there to convert the viewport back and forth between the two structures. I know the code works on this game because the same code is used for ConvertToDirectDraw7/ConvertToDirect3D7, which works fine with this game.

Anyways, I am not too worried about the resolution and scaling. I can use the surface size to determine the resolution since this game never calls the SetDisplayMode() function.

The real question is why the hand and the menu items on the first screen after the intro video are missing.

Trass3r commented 1 year ago

It's unfortunate RenderDoc doesn't support DX9. When trying other wrappers like dgVoodoo I think the hand part always showed up weirdly as its own frame. ApiTrace shows all the 3D draw calls, then an EndScene, a few Blts and a SetColorKey (maybe a transparency issue?) a WaitForVerticalBlank, multiple Blt's and the finally the Clear2 and new BeginScene.

elishacloud commented 1 year ago

It's unfortunate RenderDoc doesn't support DX9.

I always use Microsoft PIX for this. You can trace it call-by-call and see the visual display.

ApiTrace shows all the 3D draw calls, then an EndScene, a few Blts and a SetColorKey (maybe a transparency issue?) a WaitForVerticalBlank, multiple Blt's and the finally the Clear2 and new BeginScene.

Yeah, it is weird that there are so many things outside of the BeginScene() and EndScene() pair. Using PIX I can see the hand and the menu items in a surface texture. It could be a color key issue.

Trass3r commented 1 year ago

Thanks for the PIX link. The game doesn't start though. It hangs in the first Present(NULL, NULL, NULL, NULL). The D3D backend was something they only added after the fact. That's why they are still using their SW renderer for T&L, just sending D3DFVF_XYZRHW vertices to be rasterized.

elishacloud commented 1 year ago

Ok, I see what is happening here. This game is mixing 2D and 3D graphics. However, dxwrapper only supports pure 2D or pure 3D modes. Once the intro video ends it switches to 3D mode. All of the graphics you see are 3D. All of the graphics you don't see are the 2D graphics.

All of the missing graphics are on the primary surface. To fix this we would need to find a way to show the primary surface on top of the scene before calling EndScene() and Present().

Trass3r commented 1 year ago

With FullscreenWindowMode it works quite well now. It does mess with my desktop resolution though, setting it to 1024x768. The GOG patch handles this by rendering to a surface I think and upscaling it to the desktop resolution.

Trass3r commented 1 year ago

Once the intro video ends it switches to 3D mode.

Yes the main menu is actually a map. The movies can be skipped with -nomovies or -level mpd6 btw, good for debugging. And there's a reimplementation of the GOG patch for your reference if needed: https://github.com/DiaLight/Ember/blob/b2611b3b65d810299e66d21a693c4b314d67dc9b/patches/gog_patch_dll/fake/FakeDirectDraw1.cpp#L287 ScaleMode handling: https://github.com/DiaLight/Ember/blob/b2611b3b65d810299e66d21a693c4b314d67dc9b/patches/gog_patch_dll/gog_fake.cpp#L80

elishacloud commented 1 year ago

I put a hack into the module under the DDraw-2D-3D-Mix branch that allows the menu and hand to be seen.

However, this exposes another issue where dxwrapper is not detecting the correct buffer size. If you manually put the correct size into DdrawOverrideWidth/Height then it works for the most part.

I'm not quite sure how to detect the correct display size at this point.

elishacloud commented 1 year ago

I put a few fixes in for this game. The overlay is now showing up correctly in both the menu and the game play. There are still a few graphical anomalies, especially during the videos. But it should be completely playable at this point.

Here is the build with the fixes in it: dxwrapper.zip

It requires the following settings:

[Compatibility]
Dd7to9                     = 1

[Dd7to9]
DdrawOverridePrimaryWidth  = 640
DdrawOverridePrimaryHeight = 480

[d3d9]
FullscreenWindowMode       = 1

Note: if you are starting the game using the level hack then you may need to adjust the size to something else, like this:

[Dd7to9]
DdrawOverridePrimaryWidth  = 800
DdrawOverridePrimaryHeight = 600
Trass3r commented 1 year ago

Thanks! No need to make the videos perfect. I always use -nomovies or -level.

Trass3r commented 10 months ago

Unfortunately can't test atm. Some definitions conflict with the Win 10/11 SDK d3dcommon.h: https://github.com/elishacloud/dxwrapper/blob/master/Libraries/d3dx9.h#L58 and https://github.com/elishacloud/dxwrapper/blob/master/Libraries/d3dx9.h#L76

elishacloud commented 10 months ago

Some definitions conflict with the Win 10/11 SDK d3dcommon.h:

Ok, I just put a fix in that should resolve that issue. I am now using d3dcommon.h for the definitions in d3dx9.h.

Trass3r commented 10 months ago

Is it normal that the keeper hand is a bit transparent?

elishacloud commented 10 months ago

That is because when I draw the texture I draw it with blending enabled. This is because the texture is all black and only has the hand and menu on it. If I draw it without blending then it will only show the hand and the menu items and then a black screen.

Technically it should not be transparent. The game is trying to write directly to the render target. However, since writing to a render target is slow and not yet supported in dxwrapper I have it write to a black texture and then do blending to show it on the screen. Later I will find a better way to do this.