emoose / OutRun2006Tweaks

Turning and spinning and spinning and turning, woah!
MIT License
355 stars 0 forks source link

Ending cutscene lighting issues #21

Open emoose opened 5 months ago

emoose commented 5 months ago

The ending cutscenes always looked weird to me, figured that's just how they always were but looks like other releases do actually look better: https://youtu.be/h2XfwaAmbWI?t=23

Wonder what's going wrong with it there, does anyone know if there's any footage of the Xbox/arcade endings?

E: looks like arcade does have better lighting, https://youtu.be/h2XfwaAmbWI?t=235 vs https://youtu.be/NuIG3LkmQUU?t=469, hm..


E2: tried looking into the ending anims too, looks like C2C is missing code for a lot of them, the confetti/flower particle effects have code to set them up but doesn't include the actual rendering code for some reason...
There is a "goldleaf" effect which is still included though and seems to share a lot with the confetti/flower code, maybe something could be worked with that.

The anims for the volcano/rocket I'm not really sure about, I think those get handled by GoalRendition functions, seems O2SP has three of those setup for PRIN/FLOR/EAST (guess two of those are the volcano/rocket levels but not really sure yet)

C2C is also missing these goal rendition funcs entirely, I'm not 100% sure these are actually controlling those anims though since it looks like these are just used to play video files.. unless those ending anims are actually just videos playing in the background of the scene or something.

(the video player they use is some Criware thing, which is also what they use for audio in O2SP arcade as well, could maybe explain why Xbox JP brought back both looping BGM & these ending anims at the same time?)

envido32 commented 4 months ago

Have you take a look at the XBLA versions of the files? the file structure is very similar to PC version and some files are even interchangeable, it maybe a similar issue that the one with "lens_flare_offset.bin"?

For example the Shuttle Launch in the Milky Way ending: https://youtu.be/PdClIKIIduQ?si=CHWhny4yzvvIPSJC&t=290

thegreatprophetzarquon commented 4 months ago

I saw a YouTube comment that chalked up the character's off appearance to messed up UV maps in the C2C ending cut scenes. No idea if that's the case, but I figure I'd mention it if it gets you looking down a different track.

emoose commented 2 months ago

Made a tiny bit of progress with this, might have an idea whats wrong with it:

original: OR2006C2C_z89OGfL0qb OR2006C2C_ExSnAbGzWu

semi-fixed: OR2006C2C_8CRtNr5ndP OR2006C2C_J47beQKcvR

Seems the model was setup to be back-face shaded, but the game is using the front-face shader with it, causing lit-up parts to be darkened and the dark parts lit up.

The game does have shaders to handle back-face shading, but some reason I guess some model parts aren't actually flagged to use it (but some like the mid-section are?)

Unfortunately forcing it to use that shader seems to flip the light direction as can be seen in the last pic, from O2SP footage on YT it looks like she's meant to be lit up there: https://youtu.be/Clu7hF2DZe4?t=8 (couldn't find any better capture...)

It could just be an issue with how I forced that shader though, maybe adding the flags to the model file would let game flip direction itself.

(E: or seeing as the mid-section is already using this shader & still has wrong light direction, maybe it's an issue with the shader itself :/)

emoose commented 2 months ago

...or maybe I have it backwards, game is using back-face shader on that mid-section part which makes the model look off, but if we force it to use the front-face shader like the rest of the model uses....

OR2006C2C_z5DDz8Dr5W

OR2006C2C_yJj3nHQ1rp

Now it has the right light direction too 🐱 Something still seems off about it though imo, wish there was a better capture of the 2SP ending to compare with.

emoose commented 2 months ago

Another compare with the change above

original: OR2006C2C_iDSfpdXEO0

fixed(?): OR2006C2C_2024-09-06_02-52-40

If anyone wants to test, use CE: 40DF04 (byte hex) -> 00 40DEF5 (byte hex) -> 20

Hoping char models might be the only things using this broken backface shading, and maybe we can just patch these bytes in Tweaks, but not really sure yet.

(E: those bits of cloth on her back do seem to get lit wrong after this change though, and maybe collar as well, maybe some parts are set to use the backface shading correctly but the mid-section got the flag by accident, same for Alberto too I suppose...)

Tenome commented 2 months ago

That does certainly look better.

emoose commented 2 months ago

Pushed https://github.com/emoose/OutRun2006Tweaks/commit/32877c5d23f0ae4db7d7501de26351ddd22819ed which pretty much works like the above, hoping nothing else might be relying on those shaders though.

Sadly don't really think we could get those backface shaders working exactly like arcade, seems they relied on an Xbox specific register which D3D9 didn't include (Lindbergh seems like it might have added some pixel shader to emulate it but doesn't look like C2C has anything for that, too bad)

Did write some code earlier so this would only apply on character models, but after finding about that Xbox specific thing I figured pretty much all uses of it would be broken, so just made it apply on everything that uses it, hope I don't regret that lol.

E: ahh there are some stage shading changes too, what I saw it mostly seems improved, but haven't tried comparing many places yet

eg: Orig OR2006C2C_2024-09-06_10-27-32

New OR2006C2C_2024-09-06_10-28-24

Tenome commented 2 months ago

Any idea if the same issue is causing this? https://github.com/emoose/OutRun2006Tweaks/issues/103

Oh wait, I think that actually fixed it! Or at the very least, improved it, have to compare with other ports to see how they look. That's another level marked under improved.

OR2006C2C_ihTy124uYg

Do you know if this same issue is what's causing the transparency to be loaded in the wrong order on water surfaces?

10420522560658604032_20240906110012_1 1

Here's what it should look like (Xbox)

image 1

emoose commented 2 months ago

Think that seam might be caused by there being no color / black void under the water, instead of any sky reflection, so the "reflection" of the hill meeting that black void then makes an obvious seam.

Comparing C2C with Xbox: image Xbox image

Looking at Xbox in renderdoc shows the sky being drawn in two passes, first pass draws the upper part of skybox sphere & second pass draws lower part, on C2C it seems only upper part gets drawn.

Tried comparing Sky_Disp func between them and doesn't really seem to be any difference there, can't see anything that would stop the lower half from drawing.

The sky itself does have a model file, afaik it's OBJ_COURSE_OBJ_SKY_2A_SMT on Xbox & obj_course_obj_sky_lake_pmt in C2C, in there it looks like sky object only has 1 VtxGroup defined in C2C while Xbox has 2, so could mean the actual lower sphere was just removed entirely from the skybox model for some reason :/

For now maybe we can change the void color to something closer to the sky, 89BD5C (4bytes) should be the hex RGBA for the void, setting that to something like 00385463 seems to help a little but there is still an obvious seam there...

Tenome commented 2 months ago

Ah, I thought the black void was actually the bottom of the stage's 3D model peeking through as as silhouette.

emoose commented 2 months ago

If there's any other levels that have water reflections working fine it might be possible to switch the obj_course_obj_sky model file out, could probably change the sky texture back with texture replacement too, not sure if any levels do have it working properly though.

Tenome commented 2 months ago

Hmm, maybe cloudy highlands? It seems to look okay from above, but when you go below you get a black void again. So the black void might just be better hidden here. The water texture is really low resolution though so it's kinda hard to tell if it's a seam.

OR2006C2C_zb5DCJ2EyX

OR2006C2C_xpWP936hC6

emoose commented 2 months ago

Checked a couple levels but most of them had black void, but Tulip Garden doesn't oddly, copying obj_course_obj_sky_tuli_pmt.sz over obj_course_obj_sky_lake_pmt.sz does seem to work too:

OR2006C2C_2024-09-07_10-46-01

There is still a kinda obvious seam shown with it though, but not as bad as it was: OR2006C2C_2024-09-07_10-46-37

Kinda seems there might be some blurring missing from it, or maybe the bloom shader would have handled that for us.

Some reason obj_course_obj_sky_lake_pmt doesn't dump with TextureExtract though while obj_course_obj_sky_tuli_pmt does, guess maybe lake sky uses the cube texture loader that I haven't hooked yet, but since tuli sky does extract that should mean sky for it could be replaced at least.

Oh I had upscaled versions in load folder which stopped lake from dumping, seems it dumps fine.

Tenome commented 2 months ago

Yeah, the new water on Deep Lake now has super obvious tiling, so there's definitely something such as a blur layer missing from it. I'm guessing the answer is no, but is it possible to replace the model entirely with the proper fully-modeled one?

emoose commented 2 months ago

Probably not for a while, maybe we can do something with the Xbox sky model at some point though.

The tulip garden model mostly seems fine except some of the upper sky seems to leak under the water around edges of the map, guess maybe the sphere for the skybox is meant to be adjusted per-level or something.

The tiling in my pics could be because of the sloppy upscale textures I'm using, maybe wouldn't be too bad with vanilla ones.

Tenome commented 2 months ago

So the water surface is supposed to be more bright and "reflective" as in the Tulip swap? Unfortunately as it is, the side effect is that the void becomes much more pronounced and distracting, but it's interesting that they can be swapped at all and sorta work still.

firefox_SrN80LAEIW

emoose commented 2 months ago

Eh that looks close to the same brightness as the Xbox ver to me, switching to tulip would only affect what gets drawn under the water, the water itself is part of the stage model afaik.

If I run xemu with the glow filter disabled, it's pretty close when using higher res: xemu_2024-09-07_14-06-35

Lowering to default res seems to help blur it, and also improves water too: xemu_2024-09-07_14-06-46

Wonder if maybe because water bumpmap is really low res (64x64) the game ends up drawing it more times, rather than stretching it? Maybe replacing bumpmap with a basic upscale could help. Didn't actually see the bumpmap getting dumped though, only seen it inside PIX so far. (E: ah nvm, looks like they're in obj_course_obj_common_pmt, there's a bunch of bumpmaps there for each frame of the water anim)

Tenome commented 2 months ago

I updated my screenshot to show the comparison I meant. As for upscaling, I haven't tried it yet but I found these models for ESRGAN. It's for normals though, maybe it can be tweaked for bumps anyway in something like Chainner?

https://github.com/RunDevelopment/rundev-models/tree/main/normals

Tenome commented 2 months ago

I tried replacing all the normal maps for the water with some high-res ones I found online (1024), but it doesn't affect the blur (or lack thereof). On another note, though, if I can get the looping sorted out (OR2 is 40 frames, but this is 120...) we'll probably have some nice looking water. Otherwise I'll try to find some animated water maps with a shorter loop.

10420522560658604032_20240910033205_1

I went and added a grid to each map to see how it tiles, but the resolution doesn't affect anything it seems. It gets scaled to fit the same area no matter the size. 10420522560658604032_20240910034803_1 10420522560658604032_20240910035247_1

s-ilent commented 2 months ago

Regarding the backface issue, is the Xbox register different to D3D9's VFACE?

emoose commented 2 months ago

On Xbox it uses oB0 output register which doesn't seem to exist on PC, seems vertex shader would set oD0 to front-face color and oB0 to backface, but since oB0 doesn't exist on PC it was just changed to overwrite the oD0 color again instead, causing the shading issues...

Don't really know too much about D3D9 shaders, GPT tells me in D3D9 vertex shaders don't actually have access to which face is being drawn, and only pixel shaders know about it, so guess for this to work the VS would have to somehow pass both front-face & back-face colors over to the pixel shader, and then the PS would check VFACE to decide which to draw?

Do have some things setup for reassembling/replacing vertex shaders (haven't looked into replacing pixel shaders yet but it's probably similar), but I'm not really sure how we could pack both colors into oD0 & then be able to extract them in the PS though...

FWIW here's front-face VSULT_DOUBLE_LAMBERT shader (comments/constants from online arcade):

    dp3 r5.x, -R_NORMAL, CV_LIGHT_DIRECTION // R5.x = normal dot light;
    mul r2, R_DIFFUSE, CV_LIGHT_DIFFUSE
    max r0, r5.x, c0 // if dot < 0 then dot = 0;
    mul r1, r5.x, CV_HEMISPHERE_FACTOR0
    add r1, r1, CV_HEMISPHERE_FACTOR1
    mad r1, r1, r8, CV_MATERIAL_EMISSIVE
    mul r1, r1, CV_R_DRANGE

    mad oD0, r0, r2, r1
    mov oD1, c0.x

and the VSULT_TWOSIDE_LAMBERT backface:

    // this should also include same code as VSULT_DOUBLE_LAMBERT, it does in Xbox/Lindbergh anyway
    // but I guess since the result from that would just be overwritten it was removed
    dp3 r5.x, R_NORMAL, CV_LIGHT_DIRECTION // R5.x = normal dot light; -- twoside version works on R_NORMAL instead of -R_NORMAL
    mul r2, R_DIFFUSE, CV_LIGHT_DIFFUSE
    mul r6, r5.x, CV_HEMISPHERE_FACTOR0
    add r1, r6, CV_HEMISPHERE_FACTOR1
    max r0, r5.x, c0 // if dot < 0 then dot = 0;
    mad r1, r1, r8, CV_MATERIAL_EMISSIVE
    mul r1, r1, CV_R_DRANGE

    mad oD0, r0, r2, r1 // xbox assigns this to oB0 instead of oD0...
    mov oD1, c0.x

(there's also specular versions of these shaders which set oD1, so we can't really use that :/)

E: interestingly the TwoSidedLighting sample from Xbox OG SDK has a shader that matches pretty close to those, even includes the same "if dot < 0 then dot = 0;" comment: https://github.com/xerohour/xbox_leak_may_2020/blob/fd00b4b3b2abb1ea6ef9ac64b755419741a3af00/xbox_leak_may_2020/xbox%20trunk/xbox/private/atg/samples/graphics/TwoSidedLighting/media/shaders/twosided.vsh#L55 Seems X360 SDK removed this sample though, maybe they wanted to focus on per-pixel lighting over per-vertex instead.

s-ilent commented 2 months ago

Is that the whole shader? I'm confused. Are there any other semantics or constants? What about the pixel shader, is that specific to this lighting shader or is it reused across several shaders? It seems like it's a mistake that they sent the backface shading through to oD0, as having the front side shading mirrored would make more sense IMO.

If I understand correctly, the Xbox has a whole seperate register for a backface colour? That's interesting.

pass both front-face & back-face colors over to the pixel shader, and then the PS would check VFACE to decide which to draw?

Yeah, that's correct. You can't really tell which is the front/backface from the vertex shader.

A few thoughts come to mind...