libretro / LRPS2

GNU General Public License v2.0
172 stars 49 forks source link

Feature request: "Enable No Interlacing Patches" #48

Open covey-j opened 3 years ago

covey-j commented 3 years ago

As @twinaphex and I have discussed, it'd be nice to implement no interlacing patches into the core. For those unfamiliar, interlacing is a technique where, instead of scanning the entire image each frame (as is done in progressive scan), you alternate each frame between scanning only the odd lines and scanning only the even lines, effectively doubling the framerate with the same bandwidth.

This technique was used pretty extensively during the PS2 era because of the bandwidth limitations of composite input, and it looked great on CRT displays. On a modern display, however, this looks kind of shaky/blurry.

Fortunately, there are patches available for this, but they currently aren't integrated into the core. Unfortunately, I'm very busy with school at the moment and won't have time to implement this myself for the next couple months or so. If someone else wants to do it in the meantime, I see a couple of good approaches here:

  1. Apply no interlacing patches on the fly by doing a memory scan and patching the sceGsSetHalfOffset routine, as is explained here: https://forums.pcsx2.net/Thread-No-interlacing-codes. If this approach is used, the option should include a warning that it won't work for every game
  2. Maintain a database of pre-made no interlacing patches, and integrate them into the core in a similar way to how I integrated the widescreen patches in #47

I'm partial to option (1), personally, because no interlacing patches are generally pretty simple/non-intrusive and this saves a lot of manual effort of maintaining a database. Testing would be needed to verify this, but I suspect the approach of (1) would be unlikely to cause major issues.

If we were to maintain a database as in (2), it may well be easier to make a blacklist of games that don't support the no interlacing codes generated by (1), or (even better) a database with patches for games that use custom interlacing routines and need the default "generate the patch on the fly" behavior of (1) overridden.

SeventySixx commented 3 years ago

Ok, I will try the approach 1) let's see the outcome...

SeventySixx commented 3 years ago

Nope... sorry, this task is to much 'low-level programming' for my skills :(

SeventySixx commented 3 years ago

A question, isn't this already implemented in the standalone? because I found in my GSdx.ini:

interlace = 7

And here https://wiki.pcsx2.net/GSdx explains about some de-interlacing presets (F5 hotkey) which seems to be related to this GSdx setting

or this is just another setting which have nothing to do with this issue ?

covey-j commented 3 years ago

They're related, yes, and that's a possible option (3). I haven't played around with those settings much, so don't know how well those work.

It's not exactly the same as what I'm describing, though. De-interlacing is where you take the interlaced video and process it into something non-interlaced.

The no interlacing patches are assembly hacks that trick the game into not doing interlacing in the first place. You know how a lot of PS2-era games had a "Progressive Scan" setting that you could turn on? The no interlacing patches essentially force progressive scan mode

SeventySixx commented 3 years ago

Ok, thanks! Just because curious, I will look in to the code to understand how these presets are applied

20Phoenix commented 3 years ago

However a good beginning would be to get an interlace menu point to set the value, so that the manual editing of the GSdx.ini is past.

SeventySixx commented 3 years ago

However a good beginning would be to get an interlace menu point to set the value, so that the manual editing of the GSdx.ini is past.

ok, this can be done easily, we can start from this. I'm going to implement this option.

20Phoenix commented 3 years ago

ok, this can be done easily.

That's what I thought. Wonderful πŸ‘

SeventySixx commented 3 years ago

OK, I did it. I have also added the option to enable FXAA that was still missing.

But by testing it on a pair of games, I seen that the de-interlacing presets on that games generally sucks, blurry or shacking images... do you know games where it's useful to set a different value than 7? (which is the automatic mode, that in 99% of cases seems to falls to "de-interlace disabled" mode).

Just to know that before make a pull request, because I don't want to push an option that is not really useful :-)

EDIT: Just found one which improves, Sensible Soccer 2006, which with the "Auto" option was very blurry when camera moves around. But by setting de-interlace="Bob tff" it's a lot sharper, with no side effects... So this options seems to be useful in some cases.

covey-j commented 3 years ago

Still sounds like if we're going for a shorter-term solution, it'd probably be better to do (2) than (3), though. (1) can eventually be introduced as an experimental feature and eventually phase out (2)

SeventySixx commented 3 years ago

yeah, but I suspect that if a game is fixed by the "built in" de-interlacing, no one take care about creating a pnach for that game.

For example for Sensible Soccer, which runs great by changing the mode, I didn't find a pnach for the de-interlacing, but maybe because I'm the only one that plays that game ... ;)

I tried it with the standalone and the blur is not there, could be that in newer versions the automatic detection is improved, in fact I found some old posts which discuss about the inaccuracy of the automatic detection.

covey-j commented 3 years ago

yeah, but I suspect that if a game is fixed by the "built in" de-interlacing, no one take cares about creating a pnach for that game

That's a good point. Might as well make it an option then. We should still do no interlacing patches, though, so make sure to call it Deinterlacing, as to distinguish it from "no interlacing" since they're technically different.

SeventySixx commented 3 years ago

Ok, good! In your opinion is better Deinterlacing or De-interlacing? Because I seen that people call it in both ways

covey-j commented 3 years ago

I think Deinterlacing looks better

20Phoenix commented 3 years ago

Works fine, many thanks. πŸ˜„ Can be changed during gameplay, no restart needed, very nice. πŸ‘

inactive123 commented 3 years ago

Hi, I started something here -

https://github.com/libretro/pcsx2/issues/78

I'd love some feedback on this and whether or not you guys want to build on this approach. If not, I'm open to other suggestions as well that you think would work out better.

inactive123 commented 3 years ago

As for option 1 described in the OP, I think instead it'd be best if this was like a 'setting'.

Like, if we have a core option called 'No interlacing patches', then we could have as values 'Auto', 'Database', and 'Off (Disabled)'. 'Auto' would use the programmatic approach ('Apply no interlacing patches on the fly by doing a memory scan and patching the sceGsSetHalfOffset routine, as is explained here:'), 'Database' would use the baked-in database file (the .yaml that will get converted to a .h header file), and Off would simply do nothing. This is possibly the best of both worlds, even if we don't have a specific patch for a game, the users can try this programmatic option that hopefully might work all the same.

covey-j commented 3 years ago

Sounds good to me. I also learned recently that a surprising number of PS2 games natively support progressive mode even if there's no in-game option for it. On real hardware, you'd typically enable it by holding down Triangle and Cross after the PlayStation logo appears. That's something else that could be added to the programmatic approach

inactive123 commented 3 years ago

Finally hooked this up -

https://github.com/libretro/pcsx2/commit/fb684ad3a9a4b4be230f745a0f0ff25d9954e7b7

https://github.com/libretro/pcsx2/commit/7f175d2d5f4a60a358f5c35d90174a1af0147acc

inactive123 commented 3 years ago

Hi @covey-j , I'd still be very much interested in exploring how we can find a way to 'auto-enable' these progressive scab modes in pnach patches for the games that support them, like Soul Calibur 3 and Tekken 4. And maybe later down the line we can find a way to programmatically do it and add a core option for it.

I did learn myself how to nop sceGsSetHalfOffset (for the games that do interlaced rendering that way) - open ELF Search Tool, open the .elf file of an unpacked PS2 ISO, search for the string '38290500 08004264', then replace it with '38290500 00000000'. If the game makes use of this SDK function, it will then output lines for it that you can put in a pnach file to patch it. This of course will only yield results for games that actually made use of this though.

I think the number of games that are progressive scan enabled are so small that we could conceivably just run down the list of them and try to create our own pnach files for it and then include it in this no-interlacing database that way. The only thing it'd have to do is when you enable 'No-interlacing hack', a game with a progressive scan feature just loads a pnach file with the lines of code that allows it to auto-apply this mode instead without requiring the user to press and hold Triangle and X.

covey-j commented 3 years ago

I recall making a naive attempt a while ago at doing essentially what you've laid out in a programmatic way. The idea IIRC was to pretty much just scan through the EE memory for the magic string after the ELF has been loaded but before recompilation, generate the PNACH on the fly (in memory rather than saving to a file), and load the generated patch.

The obstacle as I recall was that the 64-bit version of PCSX2 doesn't use a fixed base address for the EE memory. I don't think that should be hard to overcome, but I was short on time.

It might be better to use the newer IPC protocol for this kind of thing anyway: https://wiki.pcsx2.net/PCSX2_Documentation/IPC_Protocol.