1
0
Fork 0

Check depth buffer before texture mapping

This commit is contained in:
Austin Morlan 2018-09-20 18:19:26 -07:00
parent ba68f22bee
commit bedc30038b
Signed by: austin
GPG Key ID: FD6B27654AF5E348
1 changed files with 87 additions and 84 deletions

View File

@ -84,85 +84,6 @@ void Render(EngineBuffer &buffer, EngineMemory &memory)
&& (barycenter[1] >= 0.0f) && (barycenter[1] >= 0.0f)
&& (barycenter[2] >= 0.0f)) && (barycenter[2] >= 0.0f))
{ {
// Interpolate U and V of the texture for this point
Texture &texture = textures.data[faces.data[f].materialIndex];
UV &uv0 = uvs.data[face.uvIndex[0]];
UV &uv1 = uvs.data[face.uvIndex[1]];
UV &uv2 = uvs.data[face.uvIndex[2]];
float a = barycenter[0] * p1.w * p2.w;
float b = barycenter[1] * p0.w * p2.w;
float c = barycenter[2] * p0.w * p1.w;
float abc = 1.0f / (a + b + c);
float uInterp =
((a * uv0.u) + (b * uv1.u) + (c * uv2.u))
* abc
* texture.width;
float vInterp =
((a * uv0.v) + (b * uv1.v) + (c * uv2.v))
* abc
* texture.height;
// Bilinear filtering
unsigned int u = (unsigned int)uInterp;
unsigned int v = (unsigned int)vInterp;
float du = uInterp - u;
float dv = vInterp - v;
float duDiff = 1 - du;
float dvDiff = 1 - dv;
ColorU32 color =
{
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].b
+ du * dvDiff * texture.texels[v][u+1].b
+ du * dv * texture.texels[v+1][u+1].b
+ duDiff * dv * texture.texels[v+1][u].b),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].g
+ du * dvDiff * texture.texels[v][u+1].g
+ du * dv * texture.texels[v+1][u+1].g
+ duDiff * dv * texture.texels[v+1][u].g),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].r
+ du * dvDiff * texture.texels[v][u+1].r
+ du * dv * texture.texels[v+1][u+1].r
+ duDiff * dv * texture.texels[v+1][u].r),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].a
+ du * dvDiff * texture.texels[v][u+1].a
+ du * dv * texture.texels[v+1][u+1].a
+ duDiff * dv * texture.texels[v+1][u].a)
};
// Perform Gouraud shading on the texture
ColorF32 &c0 = verts.data[face.vertIndex[0]].color;
ColorF32 &c1 = verts.data[face.vertIndex[1]].color;
ColorF32 &c2 = verts.data[face.vertIndex[2]].color;
ColorF32 shading =
(barycenter[0] * c0)
+ (barycenter[1] * c1)
+ (barycenter[2] * c2);
// Ensure no color channel exceeds max
ScaleColor(shading);
// Light the texture
color.b *= shading.b;
color.g *= shading.g;
color.r *= shading.r;
// Interpolate 1/z for the z-buffer // Interpolate 1/z for the z-buffer
float zInv = float zInv =
1.0f / 1.0f /
@ -171,15 +92,97 @@ void Render(EngineBuffer &buffer, EngineMemory &memory)
+ (barycenter[2] * p2.w)); + (barycenter[2] * p2.w));
// Draw the pixel if it's closer than what's in the z-buffer // Compute pixel color if it's closer than what's in the z-buffer
if (zInv > memory.zbuffer[y][x]) if (zInv > memory.zbuffer[y][x])
{ {
ColorU32 *pixel = (ColorU32*)&buffer.buffer[y*buffer.width+x]; // Update the depth buffer
memory.zbuffer[y][x] = zInv;
// Interpolate U and V of the texture for this point
Texture &texture = textures.data[faces.data[f].materialIndex];
UV &uv0 = uvs.data[face.uvIndex[0]];
UV &uv1 = uvs.data[face.uvIndex[1]];
UV &uv2 = uvs.data[face.uvIndex[2]];
float a = barycenter[0] * p1.w * p2.w;
float b = barycenter[1] * p0.w * p2.w;
float c = barycenter[2] * p0.w * p1.w;
float abc = 1.0f / (a + b + c);
float uInterp =
((a * uv0.u) + (b * uv1.u) + (c * uv2.u))
* abc
* texture.width;
float vInterp =
((a * uv0.v) + (b * uv1.v) + (c * uv2.v))
* abc
* texture.height;
// Bilinear filtering
unsigned int u = (unsigned int)uInterp;
unsigned int v = (unsigned int)vInterp;
float du = uInterp - u;
float dv = vInterp - v;
float duDiff = 1 - du;
float dvDiff = 1 - dv;
ColorU32 color =
{
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].b
+ du * dvDiff * texture.texels[v][u+1].b
+ du * dv * texture.texels[v+1][u+1].b
+ duDiff * dv * texture.texels[v+1][u].b),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].g
+ du * dvDiff * texture.texels[v][u+1].g
+ du * dv * texture.texels[v+1][u+1].g
+ duDiff * dv * texture.texels[v+1][u].g),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].r
+ du * dvDiff * texture.texels[v][u+1].r
+ du * dv * texture.texels[v+1][u+1].r
+ duDiff * dv * texture.texels[v+1][u].r),
(uint8_t)
(duDiff * dvDiff * texture.texels[v][u].a
+ du * dvDiff * texture.texels[v][u+1].a
+ du * dv * texture.texels[v+1][u+1].a
+ duDiff * dv * texture.texels[v+1][u].a)
};
// Perform Gouraud shading on the texture
ColorF32 &c0 = verts.data[face.vertIndex[0]].color;
ColorF32 &c1 = verts.data[face.vertIndex[1]].color;
ColorF32 &c2 = verts.data[face.vertIndex[2]].color;
ColorF32 shading =
(barycenter[0] * c0)
+ (barycenter[1] * c1)
+ (barycenter[2] * c2);
// Ensure no color channel exceeds max
ScaleColor(shading);
// Light the texture
color.b *= shading.b;
color.g *= shading.g;
color.r *= shading.r;
// Alpha blend the pixel
ColorU32 *pixel = (ColorU32*)&buffer.buffer[y*buffer.width+x];
float alpha = color.a / 255.0f; float alpha = color.a / 255.0f;
float alphaDiff = 1.0f - alpha; float alphaDiff = 1.0f - alpha;
// Blend new color with the existing color
ColorU32 blended = ColorU32 blended =
{ {
(uint8_t)((alpha * color.b) + (alphaDiff * pixel->b)), (uint8_t)((alpha * color.b) + (alphaDiff * pixel->b)),
@ -188,9 +191,9 @@ void Render(EngineBuffer &buffer, EngineMemory &memory)
(uint8_t)((alpha * color.a) + (alphaDiff * pixel->a)) (uint8_t)((alpha * color.a) + (alphaDiff * pixel->a))
}; };
DrawPixel(buffer.buffer, buffer.width, blended.u32, x, y);
memory.zbuffer[y][x] = zInv; // Draw
DrawPixel(buffer.buffer, buffer.width, blended.u32, x, y);
} }
} }
} }