[Patch] Specular Highlight

Technical discussion for those interested in Supermodel development and Model 3 reverse engineering. Prospective contributors welcome.
Forum rules
Keep it classy!

  • No ROM requests or links.
  • Do not ask to be a play tester.
  • Do not ask about release dates.
  • No drama!

[Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 12:20 pm

The following patch is not entirely a creation of mine, this was inspired by Bart and Ian discussing some time ago about the probable specular algorithm. I've got no real proof of what really happens inside Real3D, however this solution matches visually the orignal almost by-the-pixel.

First of all I can confirm, after examining many high quality videos, that vertex normal vector is calculated and normalized only in vertex shader, but the remaining lightning calculation is done per fragment. Doing everything per vertex-only gives visually different results from real Model3.

As Ian already hinted the calculation is based on the angle of incidence. We already have it since it's used for diffuse lighting, so I reuse it and perform other calculation as explained later.

Another "mistery" was the so called exponent, the values given are not meant to be used directly. At first I thought of an index to some built-in formula in Real3D, but I realized that it's just this (pseudo-code):
Code: Select all
// "shininess" is the uniform from "(header[6] >> 5) & 3"
// "NdotL" is the angle of incidence
float expIndex[4] = {8.0, 16.0, 32.0, 64.0};
float exponent = expIndex[int(shininess)];
float specularIntensity = pow(NdotL, exponent);
specularIntensity = clamp(specularIntensity, 0.0, 1.0); // Clamp it just to avoid unpredictable results


Then, I realized that value should be multiplied by a "magic constant" as this (I use again the shininess as an index):
Code: Select all
float valueIndex[4] = {1.25, 1.5, 1.75, 2.0};
specularIntensity *= valueIndex[int(shininess)];


And finally I multiply by the specular value:
Code: Select all
// "specularValue" is uniform from "(header[0] >> 26)"
specularIntensity *= specularValue;


Another thing I noticed, and implemented, is that when translucent polys, like glasses, are hit directly by light they become over-brightened, "whitish". Model 3 seems to treat those special cases by altering the alpha channel by means of that "specularIntensity" value above. Just watch the attract mode of scud race, there are many instances of that case.

Beware that until we make fragment shader "aware" of the machine stepID, and so clamp the ambient+diffuse coefficients only for step 1.0 games, instead of doing it always, the current specular patch still produces slightly different results from real hardware. The screenshots that I'll post later will be from my private build.

Last thing: there're little random shading "misbehavior" for some quad polys whose sub-edges must be inverted, this has nothing to do with specular. I'll talk to Ian about that in another topic.
Attachments
diff.zip
(2.15 KiB) Downloaded 54 times
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Re: [Patch] Specular Highlight

Postby Ian » Wed Mar 22, 2017 12:29 pm

quite excited to try this one :)

also
Another thing I noticed, and implemented, is that when translucent polys, like glasses, are hit directly by light they become over-brightened, "whitish". Model 3 seems to treat those special cases by altering the alpha channel by means of that "specularIntensity" value above. Just watch the attract mode of scud race, there are many instances of that case.


Maybe they just apply specular to all 4 terms?
ie r,g,b,a instead of just the rgb values
Ian
 
Posts: 1120
Joined: Tue Feb 23, 2016 9:23 am

Re: [Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 12:33 pm

Not exactly, I thought that at start, but after many attempts it seems doing this (btw you can actually see it in the patch):
Code: Select all
// Code-snippet from actual patch
if (finalData.a < 1.0) {
  finalData.a = max(finalData.a, specularIntensity);
}
finalData.rgb += vec3(specularIntensity * lighting[1].x);
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Re: [Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 12:38 pm

Ian, if you want to test it remember to also comment this one in <R3DShader.cpp>
Code: Select all
lightIntensity = clamp(lightIntensity,0.0,1.0);
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Re: [Patch] Specular Highlight

Postby Ian » Wed Mar 22, 2017 12:43 pm

I will try and test in a bit :)
I was just looking at the scissor code
Screenshots would be really great.
Also, what makes you think that
The normals are normalised ? Pretty much most of them are unit length anyway. And the calculations are done per pixel?
Ian
 
Posts: 1120
Joined: Tue Feb 23, 2016 9:23 am

Re: [Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 12:59 pm

ian wrote:Also, what makes you think that
The normals are normalised ? Pretty much most of them are unit length anyway. And the calculations are done per pixel?


There're some special cases in SWT (but maybe others) that will give you an all-bright result if you don't normalize them. It's just an added safety measure to avoid crazy values. I've also written in my personal shader this pseudo-code again for safety:
Code: Select all
// Avoids implementation-specific handling of division by zero
length(viewNormal) != zero ? normalize(viewNormal) : vec3(zero);
length(sunVector) != zero ? normalize(sunVector) : vec3(zero);


I'll post some screens about the difference between per-pixel and per-vertex and arcade. I know it's a bit strange but it's done like this. Also this is just a mid-quality solution. The best would be to do everything per-pixel (perfect round highlights), but it's not like it's done in Model 3 (I mean: visually).
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Re: [Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 1:13 pm

Screenshots (left: Arcade, right: Supermodel)

ECA:
eca1.jpeg
eca1.jpeg (242.2 KiB) Viewed 1163 times


Lost World:
lw1.png
Ingen Logo
lw1.png (163.39 KiB) Viewed 1150 times


Daytona USA 2 Battle on the Edge:
du2bote_1.jpeg
du2bote_1.jpeg (249.96 KiB) Viewed 1148 times
Last edited by HarryTuttle on Wed Mar 22, 2017 2:06 pm, edited 2 times in total.
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Re: [Patch] Specular Highlight

Postby Ian » Wed Mar 22, 2017 1:19 pm

That's very good :)
Ian
 
Posts: 1120
Joined: Tue Feb 23, 2016 9:23 am

Re: [Patch] Specular Highlight

Postby Ian » Wed Mar 22, 2017 1:22 pm

My previous specular efforts were derailed by the lost world

https://www.youtube.com/watch?v=F38OnpIHGaU&t=1493s

If you see the bullets on the left side of the screen. They are marked as with specular, but there is no highlight on them on the model3. On mine they came out white :(
Ian
 
Posts: 1120
Joined: Tue Feb 23, 2016 9:23 am

Re: [Patch] Specular Highlight

Postby HarryTuttle » Wed Mar 22, 2017 2:15 pm

Another bunch of screenshots:

Scud Race:
sr1.jpeg
sr1.jpeg (255.95 KiB) Viewed 1150 times


L.A. Machineguns (sorry didn't find better original pics. Also hacked sun normals: actually the game has bugged sun normal):
lam1.jpeg
lam1.jpeg (247.4 KiB) Viewed 1142 times
Last edited by HarryTuttle on Wed Mar 22, 2017 2:35 pm, edited 1 time in total.
User avatar
HarryTuttle
 
Posts: 481
Joined: Thu Mar 09, 2017 8:57 am

Next

Return to The Dark Room

Who is online

Users browsing this forum: No registered users and 1 guest

cron