Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

VideoBackends: Use proper floating point depth precision. #2369

Merged
merged 11 commits into from
May 8, 2015

Conversation

CrossVR
Copy link
Contributor

@CrossVR CrossVR commented May 5, 2015

Still doing some accuracy tests, but it seems promising that this will fix our off-by-one inaccuracies.

@comex
Copy link
Contributor

comex commented May 5, 2015

Can you explain in more detail what this does?

@CrossVR
Copy link
Contributor Author

CrossVR commented May 5, 2015

Hardware tests showed that our depth values are off-by-one in the hardware video backends: https://gist.github.com/Armada651/bab3e023b5b813e18cb7#comment-1446986

Using a graphics analyzer I could see that we are accurate to the point where we actually store the depth value. According to Fiora this inaccuracy was introduced by the divisor so I changed that after which the D3D backend passes the hardware test. The OGL backend still fails the test though, but now in the other direction with a value of 13884591.

but you can choose "correct range" or "correct precision", but not both

@FioraAeterna
Copy link
Contributor

It's a problem of "correct range, correct precision, but not both".

The only way to losslessly store a 24-bit integer into a 32-bit float is to multiply it by a power of 2 before conversion (or no multiply at all). 0xFFFFFF isn't a power of 2, so error will occur.

This unfortunately also means "max depth" (0xFFFFFF) won't actually map to 1.0. I don't know enough about the graphics stack to know if this matters.

@CrossVR
Copy link
Contributor Author

CrossVR commented May 5, 2015

Confirmed to fix pokemon snap in D3D, this PR currently breaks OGL because it's now off-by-one in the other direction.

@CrossVR
Copy link
Contributor Author

CrossVR commented May 5, 2015

@degasus Since the OGL backend reads the depth buffer as integers this is a bit difficult to fix. It may be fixed if we just use glClipControl(), but then we'd still need to implement a hack for older versions of OpenGL.

I could also switch the OGL backend to use floating points, but that's a bit of a shame since integers more accurately reflect the console.

Another option is to switch back to the old divisor and add or subtract one where needed like we do with the epsilon hack, but I don't really like adding more epsilons to our code.

@CrossVR CrossVR changed the title VideoBackends: Use proper floating point depth percision. VideoBackends: Use proper floating point depth precision. May 5, 2015
@@ -146,7 +146,7 @@ const char depth_matrix_program[] = {
" in float4 pos : SV_Position,\n"
" in float3 uv0 : TEXCOORD0){\n"
" float4 texcol = Tex0.Sample(samp0,uv0);\n"
" int depth = int(round(texcol.x * float(0xFFFFFF)));\n"
" int depth = int(round(texcol.x * 16777216.0));\n"

This comment was marked as off-topic.

@@ -89,7 +89,7 @@ FramebufferManager::FramebufferManager(int targetWidth, int targetHeight, int ms
glTexParameteri(m_textureType, GL_TEXTURE_MAX_LEVEL, 0);
glTexParameteri(m_textureType, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(m_textureType, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexImage3D(m_textureType, 0, GL_DEPTH_COMPONENT24, m_targetWidth, m_targetHeight, m_EFBLayers, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_INT, nullptr);
glTexImage3D(m_textureType, 0, GL_DEPTH_COMPONENT24, m_targetWidth, m_targetHeight, m_EFBLayers, 0, GL_DEPTH_COMPONENT, GL_FLOAT, nullptr);

This comment was marked as off-topic.

This comment was marked as off-topic.

@CrossVR
Copy link
Contributor Author

CrossVR commented May 6, 2015

@degasus Ready for review.

Do you still want to switch the D3D depth buffer from DXGI_FORMAT_R24G8_TYPELESS to DXGI_FORMAT_R32_FLOAT?

@@ -1224,11 +1224,11 @@ static inline void WritePerPixelDepth(T& out, pixel_shader_uid_data* uid_data, A
if (ApiType == API_OPENGL)
out.Write("\tscreenpos.y = %i - screenpos.y;\n", EFB_HEIGHT);

out.Write("\tdepth = float(" I_ZSLOPE".z + " I_ZSLOPE".x * screenpos.x + " I_ZSLOPE".y * screenpos.y) / float(0xFFFFFF);\n");
out.Write("\tdepth = float(" I_ZSLOPE".z + " I_ZSLOPE".x * screenpos.x + " I_ZSLOPE".y * screenpos.y) / 16777216.0;\n");

This comment was marked as off-topic.

This comment was marked as off-topic.

This comment was marked as off-topic.

This comment was marked as off-topic.

@degasus
Copy link
Member

degasus commented May 7, 2015

@Armada651 If there are no issues, we should use the same format on both backends.

@CrossVR CrossVR force-pushed the depth-percision branch 3 times, most recently from 96a466b to de265c7 Compare May 7, 2015 22:28
@PatrickFerry
Copy link
Contributor

The sky is black in the simpsons-tev above.

@CrossVR
Copy link
Contributor Author

CrossVR commented May 8, 2015

@ZephyrSurfer We're aware of the regression, but we're probably going to merge it without fixing that bug. Since the sky in simpsons-tev is also black on the Software backend and that game has never worked correctly in Dolphin anyway we don't see a need to fix it right now.

@degasus
Copy link
Member

degasus commented May 8, 2015

LGTM, but please wait for fifoci ;)

@degasus
Copy link
Member

degasus commented May 8, 2015

@Armada651: This comment grants you the permission to merge this pull request whenever you think it is ready. After addressing the remaining comments, click this link to merge.


@dolphin-emu-bot allowmerge

dolphin-emu-bot added a commit that referenced this pull request May 8, 2015
VideoBackends: Use proper floating point depth precision.
@dolphin-emu-bot dolphin-emu-bot merged commit ca7fe09 into dolphin-emu:master May 8, 2015
@dolphin-emu-bot
Copy link
Contributor

FifoCI detected that this change impacts graphical rendering. Here are the behavior differences detected by the system:

  • ed-lighting on ogl-lin-mesa: diff
  • fog-adj on ogl-lin-mesa: diff
  • fortune-street on ogl-lin-mesa: diff
  • fortune-street-fog on ogl-lin-mesa: diff
  • fortune-street-white-box on ogl-lin-mesa: diff
  • kirby-shadows on ogl-lin-mesa: diff
  • mario-tennis-menu on ogl-lin-mesa: diff
  • megaman-heat on ogl-lin-mesa: diff
  • melee-lighting on ogl-lin-mesa: diff
  • mini-ninjas on ogl-lin-mesa: diff
  • mkdd-efb on ogl-lin-mesa: diff
  • mkwii-bluebox on ogl-lin-mesa: diff
  • nfsu-reflections on ogl-lin-mesa: diff
  • nsmbw-intro on ogl-lin-mesa: diff
  • rs2-zfreeze on ogl-lin-mesa: diff
  • sadx-ui on ogl-lin-mesa: diff
  • sf-assault-flashing on ogl-lin-mesa: diff
  • simpsons-tev on ogl-lin-mesa: diff
  • soa-black on ogl-lin-mesa: diff
  • ss-timestone on ogl-lin-mesa: diff
  • tsp3-pinkgrass on ogl-lin-mesa: diff
  • xenoblade-menu on ogl-lin-mesa: diff
  • ztp-grass on ogl-lin-mesa: diff
  • zww-armos on ogl-lin-mesa: diff
  • ed-lighting on ogl-lin-nv: diff
  • fifa-street on ogl-lin-nv: diff
  • fog-adj on ogl-lin-nv: diff
  • fortune-street on ogl-lin-nv: diff
  • fortune-street-fog on ogl-lin-nv: diff
  • fortune-street-white-box on ogl-lin-nv: diff
  • kirby-shadows on ogl-lin-nv: diff
  • mario-tennis-menu on ogl-lin-nv: diff
  • megaman-heat on ogl-lin-nv: diff
  • melee-lighting on ogl-lin-nv: diff
  • mini-ninjas on ogl-lin-nv: diff
  • mkdd-efb on ogl-lin-nv: diff
  • mkwii-bluebox on ogl-lin-nv: diff
  • nfsu-reflections on ogl-lin-nv: diff
  • nsmbw-intro on ogl-lin-nv: diff
  • rs2-zfreeze on ogl-lin-nv: diff
  • sf-assault-flashing on ogl-lin-nv: diff
  • simpsons-tev on ogl-lin-nv: diff
  • smg2-fog on ogl-lin-nv: diff
  • soa-black on ogl-lin-nv: diff
  • ss-timestone on ogl-lin-nv: diff
  • tsp3-pinkgrass on ogl-lin-nv: diff
  • xenoblade-menu on ogl-lin-nv: diff
  • ztp-grass on ogl-lin-nv: diff
  • zww-armos on ogl-lin-nv: diff
  • zww-water on ogl-lin-nv: diff
  • zww-waves on ogl-lin-nv: diff

automated-fifoci-reporter

@thegrb93
Copy link
Contributor

@BhaaLseN
Copy link
Member

Too bad Windows/DX builder was stuck, so we didn't get this one earlier. Simpsons however was more or less accepted as broken, since it never worked correctly. Def Jam however is odd.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
8 participants