- Fix depth values written by sloped planes

This commit is contained in:
Magnus Norddahl 2018-04-08 02:22:01 +02:00
parent c15328de2f
commit 7f25913b2d
3 changed files with 41 additions and 12 deletions

View file

@ -289,6 +289,8 @@ namespace swrenderer
float idepth; float idepth;
}; };
// #define DEPTH_DEBUG
class DepthSpanCommand : public DrawerCommand class DepthSpanCommand : public DrawerCommand
{ {
public: public:
@ -297,6 +299,9 @@ namespace swrenderer
y = args.DestY(); y = args.DestY();
x1 = args.DestX1(); x1 = args.DestX1();
x2 = args.DestX2(); x2 = args.DestX2();
#ifdef DEPTH_DEBUG
dest = (uint32_t*)args.Viewport()->GetDest(0, args.DestY());
#endif
} }
FString DebugInfo() override { return "DepthSpanCommand"; } FString DebugInfo() override { return "DepthSpanCommand"; }
@ -314,9 +319,16 @@ namespace swrenderer
if (idepth1 == idepth2) if (idepth1 == idepth2)
{ {
float depth = idepth1; float depth = idepth1;
#ifdef DEPTH_DEBUG
uint32_t gray = clamp<int32_t>((int32_t)(1.0f / depth / 4.0f), 0, 255);
uint32_t color = MAKEARGB(255, gray, gray, gray);
#endif
for (int x = x1; x <= end; x++) for (int x = x1; x <= end; x++)
{ {
values[x] = depth; values[x] = depth;
#ifdef DEPTH_DEBUG
dest[x] = color;
#endif
} }
} }
else else
@ -325,6 +337,12 @@ namespace swrenderer
float step = (idepth2 - idepth1) / (x2 - x1 + 1); float step = (idepth2 - idepth1) / (x2 - x1 + 1);
for (int x = x1; x <= end; x++) for (int x = x1; x <= end; x++)
{ {
#ifdef DEPTH_DEBUG
uint32_t gray = clamp<int32_t>((int32_t)(1.0f / depth / 4.0f), 0, 255);
uint32_t color = MAKEARGB(255, gray, gray, gray);
dest[x] = color;
#endif
values[x] = depth; values[x] = depth;
depth += step; depth += step;
} }
@ -334,6 +352,9 @@ namespace swrenderer
private: private:
int y, x1, x2; int y, x1, x2;
float idepth1, idepth2; float idepth1, idepth2;
#ifdef DEPTH_DEBUG
uint32_t *dest;
#endif
}; };
void SWPixelFormatDrawers::DrawDepthSkyColumn(const SkyDrawerArgs &args, float idepth) void SWPixelFormatDrawers::DrawDepthSkyColumn(const SkyDrawerArgs &args, float idepth)

View file

@ -89,11 +89,10 @@ namespace swrenderer
auto viewport = Thread->Viewport.get(); auto viewport = Thread->Viewport.get();
DVector3 worldNormal = pl->height.Normal(); DVector3 worldNormal = pl->height.Normal();
double worldD = pl->height.fD();
planeNormal.X = worldNormal.X * viewport->viewpoint.Sin - worldNormal.Y * viewport->viewpoint.Cos; planeNormal.X = worldNormal.X * viewport->viewpoint.Sin - worldNormal.Y * viewport->viewpoint.Cos;
planeNormal.Y = worldNormal.X * viewport->viewpoint.Cos + worldNormal.Y * viewport->viewpoint.Sin; planeNormal.Y = worldNormal.X * viewport->viewpoint.Cos + worldNormal.Y * viewport->viewpoint.Sin;
planeNormal.Z = worldNormal.Z; planeNormal.Z = worldNormal.Z;
planeD = worldD + planeNormal.Z * viewport->viewpoint.Pos.Z; planeD = -planeNormal.Z * (pl->height.ZatPoint(viewport->viewpoint.Pos.X, viewport->viewpoint.Pos.Y) - viewport->viewpoint.Pos.Z);
drawerargs.SetSolidColor(3); drawerargs.SetSolidColor(3);
@ -213,24 +212,23 @@ namespace swrenderer
void RenderSlopePlane::RenderLine(int y, int x1, int x2) void RenderSlopePlane::RenderLine(int y, int x1, int x2)
{ {
drawerargs.DrawTiltedSpan(Thread, y, x1, x2, plane_sz, plane_su, plane_sv, plane_shade, planeshade, planelightfloat, pviewx, pviewy, basecolormap);
if (r_models) if (r_models)
{ {
// Calculate normalized device coordinates for the span double viewZ = 1.0;
// 1.5 is not a typo. The range is [x1,x2] double viewX1 = Thread->Viewport->ScreenToViewX(x1, viewZ);
double devY = -(y + 0.5 - Thread->Viewport->CenterY) / Thread->Viewport->InvZtoScale / Thread->Viewport->viewwindow.FocalTangent; double viewX2 = Thread->Viewport->ScreenToViewX(x2 + 1, viewZ);
double devX1 = (x1 + 0.5 - Thread->Viewport->CenterX) / Thread->Viewport->CenterX; double viewY = Thread->Viewport->ScreenToViewY(y, viewZ);
double devX2 = (x2 + 1.5 - Thread->Viewport->CenterX) / Thread->Viewport->CenterX;
// Find depth values for the span // Find depth values for the span
float zbufferdepth1 = (float)-planeD / (planeNormal | DVector3(devX1, 1.0, devY)); float zbufferdepth1 = (float)(-planeD / (planeNormal | DVector3(viewX1, viewZ, viewY)));
float zbufferdepth2 = (float)-planeD / (planeNormal | DVector3(devX2, 1.0, devY)); float zbufferdepth2 = (float)(-planeD / (planeNormal | DVector3(viewX2, viewZ, viewY)));
drawerargs.SetDestX1(x1); drawerargs.SetDestX1(x1);
drawerargs.SetDestX2(x2); drawerargs.SetDestX2(x2);
drawerargs.SetDestY(Thread->Viewport.get(), y); drawerargs.SetDestY(Thread->Viewport.get(), y);
drawerargs.DrawDepthSpan(Thread, 1.0f / zbufferdepth1, 1.0f / zbufferdepth2); drawerargs.DrawDepthSpan(Thread, 1.0f / zbufferdepth1, 1.0f / zbufferdepth2);
} }
drawerargs.DrawTiltedSpan(Thread, y, x1, x2, plane_sz, plane_su, plane_sv, plane_shade, planeshade, planelightfloat, pviewx, pviewy, basecolormap);
} }
} }

View file

@ -69,6 +69,16 @@ namespace swrenderer
return FocalLengthY / (screenY + 0.5 - CenterY) * planeHeight; return FocalLengthY / (screenY + 0.5 - CenterY) * planeHeight;
} }
double ScreenToViewX(int screenX, double viewZ) const
{
return (screenX + 0.5 - CenterX) / FocalLengthX * viewZ;
}
double ScreenToViewY(int screenY, double viewZ) const
{
return (CenterY - screenY - 0.5) / FocalLengthY * viewZ;
}
private: private:
void InitTextureMapping(); void InitTextureMapping();
void SetupBuffer(); void SetupBuffer();