mirror of
https://github.com/libretro/parallel-dc.git
synced 2026-11-10 17:26:21 -10:00
dx9: the depth is the position's, as the chip has it
The Direct3D 9 renderer as the others (rend/depth_scale.h): the depth is the vertex position's, by the fixed functions, and no pixel shader writes DEPTH. transformVertex(), which places the vertices of both vertex shaders, gives z = S instead of 0: a depth of S*z, the chip's 1/w up to 1 at fZ_max, reversed, in the D24FS8 depth buffer where the device has that format (it was already preferred) and D24S8 where not (a float depth surface without stencil is no use here: the shadows need the stencil); z is clamped to w, so a vertex beyond fZ_max is at depth 1 and not clipped. S, 1/fZ_max, and the inverse of the matrix's z scale are vertex constant register c3. Shader model 3 has no precise: the same text in the two shaders is what there is, and a polygon drawn again for its shadow (EQUAL) and the sorted depth prepass are placed by it.
This commit is contained in:
1 parent
68ca18ffe2
commit
b78383f9e4
4 files changed
+16
-14
No files matched your search
@@ -503,6 +503,8 @@ void DX9Renderer::SetupFrame()
|
||||
{ normal.tx, -normal.ty, normal.tz, 0.f },
|
||||
};
|
||||
device->SetVertexShaderConstantF(DX9VC_NormalScale, &vtx[0][0], 2);
|
||||
const float depthScale[4] = { pvr_depth_scale(pvrrc.fZ_max), 1.f / normal.sz, 0.f, 0.f };
|
||||
device->SetVertexShaderConstantF(DX9VC_DepthScale, depthScale, 1);
|
||||
|
||||
float frag[5][4] = {};
|
||||
// the clamping limits
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include "rend/tileclip.h"
|
||||
#include "rend/transform_matrix.h"
|
||||
#include "rend/shadows.h"
|
||||
#include "rend/depth_scale.h"
|
||||
#include "dx9context_lr.h"
|
||||
#include "dx9_texture.h"
|
||||
#include "dx9_texdecoder.h"
|
||||
|
||||
@@ -26,8 +26,11 @@
|
||||
* interpolation brings to the inverse of the straight line's value.
|
||||
* - A pixel's centre is where its coordinates are whole numbers, and not
|
||||
* half a pixel further on: the vertices are moved back by half a pixel.
|
||||
* - No depth clipping can be turned off: the clip space's z is 0, inside
|
||||
* the clip volume, and the depth is the pixel shader's own anyway.
|
||||
* - The depth is the position's, as in the other renderers
|
||||
* (rend/depth_scale.h): the vertex goes out at z = S, a depth of S*z,
|
||||
* the guest's 1/w up to 1 at fZ_max; no pixel shader writes a depth, and
|
||||
* one function places the vertices of every shader. (Shader model 3 has
|
||||
* no precise: the same text in every shader is what there is.)
|
||||
* - Vertex colours are read as D3DCOLOR, blue in the first byte: the
|
||||
* vertices have red there, and the vertex shader puts it back.
|
||||
* - Flat shading is the device's (D3DRS_SHADEMODE), as is culling. */
|
||||
@@ -39,18 +42,22 @@ static const char VertexTransform[] = R"(
|
||||
float4 normalScale : register(c0);
|
||||
float4 normalOffset : register(c1);
|
||||
float4 halfPixel : register(c2);
|
||||
// 1/fZ_max, and the inverse of what the matrix scales z by (rend/depth_scale.h)
|
||||
float4 depthScale : register(c3);
|
||||
|
||||
// A vertex's z is the guest's 1/w. It is made the clip space w's inverse,
|
||||
// and x and y are multiplied by w, so that the division by it leaves them
|
||||
// where they are and everything in between is interpolated with the
|
||||
// perspective.
|
||||
// perspective. The clip space z is S, so that the depth is S*z: the
|
||||
// guest's 1/w, linear across the screen, as the chip has it.
|
||||
float4 transformVertex(float3 pos, out float invW)
|
||||
{
|
||||
float4 vpos = float4(pos * normalScale.xyz + normalOffset.xyz, 1.0);
|
||||
vpos.w = 1.0 / vpos.z;
|
||||
invW = vpos.w;
|
||||
vpos.xy = (vpos.xy + halfPixel.xy) * vpos.w;
|
||||
vpos.z = 0.0;
|
||||
// (a z beyond fZ_max is at depth 1, not clipped)
|
||||
vpos.z = min(depthScale.x * depthScale.y, vpos.w);
|
||||
return vpos;
|
||||
}
|
||||
)";
|
||||
@@ -163,17 +170,10 @@ float fog_mode2(float w)
|
||||
return floor((next * blend + cur * (255.0 - blend)) / 256.0) / 256.0;
|
||||
}
|
||||
|
||||
// The depth written: the same function of 1/w as the other renderers write
|
||||
float fragDepth(float w)
|
||||
{
|
||||
w *= 100000.0;
|
||||
return log2(1.0 + max(w, -0.999999)) / 34.0;
|
||||
}
|
||||
|
||||
// (the depth is the position's, which the depth test took: none written here)
|
||||
struct PSO
|
||||
{
|
||||
float4 col : COLOR0;
|
||||
float depth : DEPTH;
|
||||
};
|
||||
)";
|
||||
|
||||
@@ -344,7 +344,6 @@ PSO main(in Pixel inpix)
|
||||
discard;
|
||||
|
||||
PSO pso;
|
||||
pso.depth = fragDepth(w);
|
||||
pso.col = color;
|
||||
return pso;
|
||||
}
|
||||
@@ -356,7 +355,6 @@ static const char ModVolPixelShaderSource[] = R"(
|
||||
PSO main(in float invW : TEXCOORD1)
|
||||
{
|
||||
PSO pso;
|
||||
pso.depth = fragDepth(1.0 / invW);
|
||||
pso.col = float4(0.0, 0.0, 0.0, 1.0 - frameParams.z);
|
||||
return pso;
|
||||
}
|
||||
|
||||
@@ -84,6 +84,7 @@ enum
|
||||
DX9VC_NormalScale = 0,
|
||||
DX9VC_NormalOffset = 1,
|
||||
DX9VC_HalfPixel = 2, // half a pixel of the viewport, in clip space
|
||||
DX9VC_DepthScale = 3, // 1/fZ_max, 1 / the normal matrix's z scale (rend/depth_scale.h)
|
||||
// pixel shaders: the frame's, c0 to c4, and the polygon's, c5 and c6
|
||||
DX9PC_ColorClampMin = 0,
|
||||
DX9PC_ColorClampMax = 1,
|
||||
|
||||
Reference in new issue
Block a user