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

[Blood 2] 32 bit colors and 60 fps lock not working #59

Open Berzerk2k2 opened 4 years ago

Berzerk2k2 commented 4 years ago

I would like to know what I have to do to get the 32 bit colors and the 60 fps lock to work.

I'm using the GOG version of Blood II - The Chosen together with the high resolution fix from the dgVoodoo website and the widescreen mods from WSGF on Windows 10 Home (fully updated) with the latest Nvidia game-ready driver 442.19.

The game runs ok so far but the colors are only 16 bit and the framerate is too high cutting off characters voice lines in cutscenes.

Changing anything inside the dxwrapper.ini will make the game crash on launch so I can't use DdrawOverrideBitMode, DdrawOverrideRefreshRate or EnableVSync with the game.

Any idea what I would have to do to make everything work correct again?

elishacloud commented 4 years ago

As far as I know the game only supports 16 bit color, at least I have never seen it work on 32 bit color. Are you able to get 32 bit color without dxwrapper?

Can you explain what you mean by "the framerate is too high cutting off characters voice lines in cutscenes"?

Berzerk2k2 commented 4 years ago

I made a small screenshot comparison between Blood II with dgVoodoo 2.63.1 and the DXWrapper. Over all the look is smoother with dgVoodoo imo.

Blood2dgVoodoo01 - https://imgur.com/fiPteGa Blood2DXWrapper01 - https://imgur.com/QksEVBL

Blood2dgVoodoo02 - https://imgur.com/mJehxKi Blood2DXWrapper02 - https://imgur.com/Wak0dE4

And here are two comparison videos of the games first cutscene in the train. Notice how Gideon is not able to finish talking before Caleb starts saying "Bring it on" in the DXWrapper version. In the dgVoodoo version this doesn't happen and he can finish his sentence before Caleb talks.

Blood2dgVoodoo2.63.1 - https://streamable.com/lki36 Blood2DXWrapperWin10 - https://streamable.com/dyo0e

I guess the reason for the cut voice line of Gideon is that the game probably runs at my screen refresh rate which is 144 Hz (so 144 fps with Vsync on). But Blood II was programmed with 60 fps max in mind so it does run too fast.

elishacloud commented 1 year ago

The game runs ok so far but the colors are only 16 bit

From the screenshots it looks like the dgVoodoo2 is just doing some kind of texture smoothing to make the textures look better. I don't have any plans to add smoothing. I don't think the game is running at 32bit color.

the framerate is too high cutting off characters voice lines in cutscenes.

As far as the voice cutting off, I don't have any v-sync controls in dxwrapper for DirectDraw games yet unless you are using Dd7to9 (which isn't supported in this game yet). I could add a feature to enable v-sync with DirectDraw and then have dxwrapper send the functions to dgVoodoo2. However, I am not sure whether dgVoodoo2 would honor v-sync controls.

mirh commented 1 year ago

Daily reminder that specifically using v-sync for frame limiting is always pretty dumb.

elishacloud commented 1 year ago

True. Adding a high performance counter in there to pause the call after each frame is drawn is probably a better solution. Also, that won't matter whether or not dgVoodoo2 honor v-sync controls here.

However, I'm not sure the best way to do that without eating CPU cycles. I cannot rely on Sleep() because that may not return back soon enough.

elishacloud commented 1 year ago

BTW: lots of old games use v-sync for frame limiting. dxwrapper's dd7to9 just converts the game from DirectDraw to Driect3D9.

So for example games like Dune 2000, War Wind and others use v-sync to prevent the game from running too fast. With dxwrapper the game runs at normal speed because I honor the v-sync from the game. Other games, like Moto Racer did not enable v-sync but some menu screens only run at the correct speed with v-sync enabled.

I guess I could convert the DirectDraw's v-sync to use a high performance timer instead. But v-sync already has a high performance timer in it, so why not use it, especially since that is what many of the games are requesting.

mirh commented 1 year ago

Sigh, frame limiting is an extremely touchy topic tbh. You can take a look at specialK, gedosato or whatever the hell else that scanline sync involve.

BTW: lots of old games use v-sync for frame limiting. dxwrapper's dd7to9 just converts the game from DirectDraw to Driect3D9.

Sigh.. I have PTSD from https://github.com/crosire/d3d8to9/pull/143

elishacloud commented 1 year ago

Sigh.. I have PTSD from crosire/d3d8to9#143

LOL. Yeah, I saw the long thread. But frankly, many of these old games were written to use v-sync and I don't see any reason not to use it to fix issues in older games. It is simple to use, it is easily implemented and it works on any hardware (both old and new).

If a feature exists why not use it? Granted, it was not initially intended for this purpose but it works just as good for this purpose on older games.

This feature can be configured differently on different games so just because I use this for fixing older games doesn't mean it will break other games.

Unless I hear of specific issues with enabling v-sync to slow down older games I am going to continue to use it.

BTW: dxwrapper gives you options for using it so users can enable or disable it as they desire.

mirh commented 1 year ago

But frankly, many of these old games were written to use v-sync and I don't see any reason not to use it to fix issues in older games.

For the same reason that I explained in my second last post there. If you believe the implicit "contract" was really only explicitly specific to requesting v-sync in and of itself, then you are correct (but was it? like.. I seem to understand from the documentation that with Windowed=TRUE you couldn't even change resolution/refresh) If you believe that was always eventually just a mean to an end (i.e. no tearing) then what newer Windows does is not even wrong.

It is simple to use, it is easily implemented and it works on any hardware (both old and new).

I mean, it's not really like I could ever be opposed to a technically sound/correct/accurate fix.. but you can understand why 2023 may have slightly increased people's expectation not to get their shiny new HFR monitor to mode switch to 60hz.

Granted, it was not initially intended for this purpose but it works just as good for this purpose on older games.

I would actually go as far as to argue that quite the number of games straightaway consciously used that as a "clock reference". But paradoxically, that's even more of a reason to avoid it like the absolute plague. Like, freaking Skyrim is not even able to play its intro, just because you upgraded to a newer monitor.

BTW: dxwrapper gives you options for using it so users can enable or disable it as they desire.

Sure, by all means both cases should be supported as nicely as possible.. Still, it's just that I couldn't avoid to dot the i's and cross the t's

elishacloud commented 1 year ago

I understand what you are saying and mostly agree. But, just to be clear. Most of the games I work on where v-sync is used to slow down the game have v-sync hard coded into the game. These games specifically ask for v-sync to be enabled and if you disable it then they run too fast. dxwrapper is just honoring their request.

The goal of the d3d7to9 option in dxwrapper is to covert the games up from DirectDraw to Direct3D9, exactly call-for-call. However, all the v-sync items are done in one place in the code. If I find a way to do precise timing that, 1) doesn't cause screen tearing, and 2) doesn't just spin the CPU while its waiting, then I can easily swap out the code for this new code.

BTW: even if I could find a way to do this without v-sync and allowing the fancy monitors/GPUs to run at a higher (or variable) frequency all that would mean is that the same image would be shown on multiple frames since most of these games have their engines and video tide together, meaning if you speed up the video you also speed up the engine. In other words, speeding up the frames will also change the game speed which is almost never desired. So there is not much gained by trying to run these games at a faster (or variable) refresh rate, unless you want to rewrite the whole game engine.

mirh commented 1 year ago

These games specifically ask for v-sync to be enabled and if you disable it then they run too fast. dxwrapper is just honoring their request.

Correct me if I'm wrong.. Not that this should mean everything (of course), but doesn't windowed mode have so many limitations that:

The goal of the d3d7to9 option in dxwrapper is to covert the games up from DirectDraw to Direct3D9, exactly call-for-call.

Is that even a straightforward task? Because it doesn't appear a walk in the park already with d3d8.. I can't imagine for something even older/dumber.

1) doesn't cause screen tearing, and 2) doesn't just spin the CPU while its waiting, then I can easily swap out the code for this new code.

AFAIK this is the state of art. Not sure about performance considerations then (even though it would seem strange if they were noticeable). But my aim here was mostly academic really, I wasn't trying to push for anything to be implemented (unless you feel like going on a coding spree, in which case hats off even more of my respect).

BTW: even if I could find a way to do this without v-sync

I mean, I don't see why you couldn't simulate a 60hz refresh rate, even though that's actually just normal frame limiting anyway. (but I know just how much of an absolute clusterfuck finding the right "clock" to sync is.. so I guess I'm just navel gazing here) Though I'll grant it'd be cool if that was to be the default setting for all v-synced <d3d9 games.

and allowing the fancy monitors/GPUs to run at a higher (or variable) frequency all that would mean is that the same image would be shown on multiple frames

Don't really see much of a downside there? And variable refresh rate would actually mean that frames last just as long as strictly needed (be it because of scaling frequency all the way down to 60hz, or because they employ integer "scaling" factors)

elishacloud commented 9 months ago

@mirh, I added some high performance counters to dxwrapper to do frame limiting, rather than requiring v-sync. If the game requests v-sync then dxwrapper will enable it. Or if there is screen tearing users can enable it. However, there is a new option for limiting frame rate without using v-sync.

This new option can take decimal places, so you can set the frame limiter to numbers like 59.933 or 29.963 or whatever you like. This works well on older games, like Interstate 76 that run too fast on a modern computer.