Stop copying the matrix and remove r_triangle

This commit is contained in:
Magnus Norddahl 2016-11-20 02:07:55 +01:00
parent f8efe394cc
commit 7ac0cace7d
18 changed files with 183 additions and 1745 deletions

View file

@ -1092,7 +1092,6 @@ set( FASTMATH_PCH_SOURCES
r_segs.cpp
r_sky.cpp
r_things.cpp
r_triangle.cpp
s_advsound.cpp
s_environment.cpp
s_playlist.cpp

View file

@ -234,8 +234,6 @@ struct TriUniforms
nearest_filter = 2,
fixed_light = 4
};
TriMatrix objectToClip;
};
struct TriDrawTriangleArgs

View file

@ -59,7 +59,6 @@
#include "v_palette.h"
#include "r_data/colormaps.h"
#include "r_draw_rgba.h"
#include "r_triangle.h"
#ifdef _MSC_VER
#pragma warning(disable:4244)
@ -1015,261 +1014,6 @@ static const BYTE *R_GetTwoSkyColumns (FTexture *fronttex, int x)
}
}
static void R_DrawCubeSky(visplane_t *pl)
{
int x1 = pl->left;
int x2 = pl->right;
short *uwal = (short *)pl->top;
short *dwal = (short *)pl->bottom;
static TriVertex cube[6 * 6] =
{
// Top
{ -1.0f, 1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
{ 1.0f, 1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ 1.0f, -1.0f, 0.6f, 1.0f, 0.0f, 0.1f },
{ 1.0f, -1.0f, 0.6f, 1.0f, 0.0f, 0.1f },
{ -1.0f, -1.0f, 0.6f, 1.0f, 1.0f, 0.1f },
{ -1.0f, 1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
// Bottom
{ 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, 0.9f },
{ 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 1.0f },
{ -1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 1.0f },
{ -1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 1.0f },
{ -1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.9f },
{ 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, 0.9f },
// Front
{ 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 2.0f },
{ 1.0f, 1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
{ -1.0f, 1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ -1.0f, 1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ -1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ 1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 2.0f },
// Back
{ -1.0f, -1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
{ 1.0f, -1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ -1.0f, -1.0f, -1.0f, 1.0f, 1.0f, 2.0f },
{ -1.0f, -1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
// Right
{ 1.0f, -1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
{ 1.0f, 1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ 1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ 1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, 2.0f },
{ 1.0f, -1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
// Left
{ -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 2.0f },
{ -1.0f, 1.0f, 0.6f, 1.0f, 1.0f, 0.0f },
{ -1.0f, -1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ -1.0f, -1.0f, 0.6f, 1.0f, 0.0f, 0.0f },
{ -1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 2.0f },
{ -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, 2.0f }
};
TriMatrix objectToWorld = TriMatrix::translate((float)ViewPos.X, (float)ViewPos.Y, (float)ViewPos.Z) * TriMatrix::scale(1000.0f, 1000.0f, 1000.0f);
TriMatrix objectToClip = TriMatrix::viewToClip() * TriMatrix::worldToView() * objectToWorld;
//TriMatrix objectToWorld = TriMatrix::scale(1000.0f, 1000.0f, 1000.0f);
//TriMatrix objectToClip = TriMatrix::viewToClip() * objectToWorld;
uint32_t solid_top = frontskytex->GetSkyCapColor(false);
uint32_t solid_bottom = frontskytex->GetSkyCapColor(true);
solid_top = RGB32k.RGB[(RPART(solid_top) >> 3)][(GPART(solid_top) >> 3)][(BPART(solid_top) >> 3)];
solid_bottom = RGB32k.RGB[(RPART(solid_bottom) >> 3)][(GPART(solid_bottom) >> 3)][(BPART(solid_bottom) >> 3)];
TriUniforms uniforms;
uniforms.objectToClip = objectToClip;
uniforms.light = 256;
uniforms.flags = 0;
TriangleDrawer::fill(uniforms, cube, 6, TriangleDrawMode::Normal, false, x1, x2 - 1, uwal, dwal, solid_top);
TriangleDrawer::fill(uniforms, cube + 6, 6, TriangleDrawMode::Normal, false, x1, x2 - 1, uwal, dwal, solid_bottom);
TriangleDrawer::draw(uniforms, cube + 2 * 6, 4 * 6, TriangleDrawMode::Normal, false, x1, x2 - 1, uwal, dwal, frontskytex);
}
namespace
{
class SkyDome
{
public:
SkyDome() { CreateDome(); }
void Render(visplane_t *pl);
private:
TArray<TriVertex> mVertices;
TArray<unsigned int> mPrimStart;
int mRows, mColumns;
void SkyVertex(int r, int c, bool yflip);
void CreateSkyHemisphere(bool zflip);
void CreateDome();
void RenderRow(int row, visplane_t *pl);
void RenderCapColorRow(int row, bool bottomCap, visplane_t *pl);
TriVertex SetVertex(float xx, float yy, float zz, float uu = 0, float vv = 0);
TriVertex SetVertexXYZ(float xx, float yy, float zz, float uu = 0, float vv = 0);
};
TriVertex SkyDome::SetVertex(float xx, float yy, float zz, float uu, float vv)
{
TriVertex v;
v.x = xx;
v.y = yy;
v.z = zz;
v.w = 1.0f;
v.varying[0] = uu;
v.varying[1] = vv;
return v;
}
TriVertex SkyDome::SetVertexXYZ(float xx, float yy, float zz, float uu, float vv)
{
TriVertex v;
v.x = xx;
v.y = zz;
v.z = yy;
v.w = 1.0f;
v.varying[0] = uu;
v.varying[1] = vv;
return v;
}
void SkyDome::SkyVertex(int r, int c, bool zflip)
{
static const FAngle maxSideAngle = 60.f;
static const float scale = 10000.;
FAngle topAngle = (c / (float)mColumns * 360.f);
FAngle sideAngle = maxSideAngle * (mRows - r) / mRows;
float height = sideAngle.Sin();
float realRadius = scale * sideAngle.Cos();
FVector2 pos = topAngle.ToVector(realRadius);
float z = (!zflip) ? scale * height : -scale * height;
float u, v;
//uint32_t color = r == 0 ? 0xffffff : 0xffffffff;
// And the texture coordinates.
if (!zflip) // Flipped Y is for the lower hemisphere.
{
u = (-c / (float)mColumns);
v = (r / (float)mRows);
}
else
{
u = (-c / (float)mColumns);
v = 1.0f + ((mRows - r) / (float)mRows);
}
if (r != 4) z += 300;
// And finally the vertex.
TriVertex vert;
vert = SetVertexXYZ(-pos.X, z - 1.f, pos.Y, u * 4.0f, v + 0.5f/*, color*/);
mVertices.Push(vert);
}
void SkyDome::CreateSkyHemisphere(bool zflip)
{
int r, c;
mPrimStart.Push(mVertices.Size());
for (c = 0; c < mColumns; c++)
{
SkyVertex(1, c, zflip);
}
// The total number of triangles per hemisphere can be calculated
// as follows: rows * columns * 2 + 2 (for the top cap).
for (r = 0; r < mRows; r++)
{
mPrimStart.Push(mVertices.Size());
for (c = 0; c <= mColumns; c++)
{
SkyVertex(r + zflip, c, zflip);
SkyVertex(r + 1 - zflip, c, zflip);
}
}
}
void SkyDome::CreateDome()
{
mColumns = 128;
mRows = 4;
CreateSkyHemisphere(false);
CreateSkyHemisphere(true);
mPrimStart.Push(mVertices.Size());
}
void SkyDome::RenderRow(int row, visplane_t *pl)
{
int x1 = pl->left;
int x2 = pl->right;
short *uwal = (short *)pl->top;
short *dwal = (short *)pl->bottom;
TriMatrix objectToWorld = TriMatrix::translate((float)ViewPos.X, (float)ViewPos.Y, (float)ViewPos.Z);
TriMatrix objectToClip = TriMatrix::viewToClip() * TriMatrix::worldToView() * objectToWorld;
TriUniforms uniforms;
uniforms.objectToClip = objectToClip;
uniforms.light = 256;
uniforms.flags = 0;
TriangleDrawer::draw(uniforms, &mVertices[mPrimStart[row]], mPrimStart[row + 1] - mPrimStart[row], TriangleDrawMode::Strip, false, x1, x2 - 1, uwal, dwal, frontskytex);
}
void SkyDome::RenderCapColorRow(int row, bool bottomCap, visplane_t *pl)
{
uint32_t solid = frontskytex->GetSkyCapColor(bottomCap);
solid = RGB32k.RGB[(RPART(solid) >> 3)][(GPART(solid) >> 3)][(BPART(solid) >> 3)];
int x1 = pl->left;
int x2 = pl->right;
short *uwal = (short *)pl->top;
short *dwal = (short *)pl->bottom;
TriMatrix objectToWorld = TriMatrix::translate((float)ViewPos.X, (float)ViewPos.Y, (float)ViewPos.Z);
TriMatrix objectToClip = TriMatrix::viewToClip() * TriMatrix::worldToView() * objectToWorld;
TriUniforms uniforms;
uniforms.objectToClip = objectToClip;
uniforms.light = 256;
uniforms.flags = 0;
TriangleDrawer::fill(uniforms, &mVertices[mPrimStart[row]], mPrimStart[row + 1] - mPrimStart[row], TriangleDrawMode::Fan, bottomCap, x1, x2 - 1, uwal, dwal, solid);
}
void SkyDome::Render(visplane_t *pl)
{
int rc = mRows + 1;
// No need to draw this as the software renderer can't look that high anyway
//RenderCapColorRow(0, false, pl);
//RenderCapColorRow(rc, true, pl);
for (int i = 1; i <= mRows; i++)
{
RenderRow(i, pl);
RenderRow(rc + i, pl);
}
}
}
static void R_DrawDomeSky(visplane_t *pl)
{
static SkyDome skydome;
skydome.Render(pl);
}
static void R_DrawSkyColumnStripe(int start_x, int y1, int y2, int columns, double scale, double texturemid, double yrepeat)
{
uint32_t height = frontskytex->GetHeight();
@ -1467,16 +1211,6 @@ static void R_DrawSky (visplane_t *pl)
R_DrawCapSky(pl);
return;
}
else if (r_skymode == 3)
{
R_DrawCubeSky(pl);
return;
}
else if (r_skymode == 4)
{
R_DrawDomeSky(pl);
return;
}
int x;
float swal;

View file

@ -129,7 +129,6 @@ void RenderPolyDecal::Render(const TriMatrix &worldToClip, DBaseDecal *decal, co
bool fullbrightSprite = (decal->RenderFlags & RF_FULLBRIGHT) == RF_FULLBRIGHT;
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
if (fullbrightSprite || fixedlightlev >= 0 || fixedcolormap)
{
uniforms.light = 256;
@ -145,6 +144,7 @@ void RenderPolyDecal::Render(const TriMatrix &worldToClip, DBaseDecal *decal, co
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = 4;
args.mode = TriangleDrawMode::Fan;

View file

@ -22,7 +22,7 @@
#pragma once
#include "r_triangle.h"
#include "r_poly_triangle.h"
class RenderPolyDecal
{

View file

@ -22,7 +22,7 @@
#pragma once
#include "r_triangle.h"
#include "r_poly_triangle.h"
#include <algorithm>
#include <cmath>

View file

@ -71,7 +71,6 @@ void RenderPolyParticle::Render(const TriMatrix &worldToClip, particle_t *partic
bool fullbrightSprite = particle->bright != 0;
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
if (fullbrightSprite || fixedlightlev >= 0 || fixedcolormap)
{
uniforms.light = 256;
@ -88,6 +87,7 @@ void RenderPolyParticle::Render(const TriMatrix &worldToClip, particle_t *partic
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = 4;
args.mode = TriangleDrawMode::Fan;

View file

@ -103,7 +103,6 @@ void RenderPolyPlane::Render3DFloor(const TriMatrix &worldToClip, subsector_t *s
}
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
uniforms.light = (uint32_t)(lightlevel / 255.0f * 256.0f);
if (fixedlightlev >= 0 || fixedcolormap)
uniforms.light = 256;
@ -133,6 +132,7 @@ void RenderPolyPlane::Render3DFloor(const TriMatrix &worldToClip, subsector_t *s
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = sub->numlines;
args.mode = TriangleDrawMode::Fan;
@ -195,7 +195,6 @@ void RenderPolyPlane::Render(const TriMatrix &worldToClip, subsector_t *sub, uin
bool isSky = picnum == skyflatnum;
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
uniforms.light = (uint32_t)(frontsector->lightlevel / 255.0f * 256.0f);
if (fixedlightlev >= 0 || fixedcolormap)
uniforms.light = 256;
@ -225,6 +224,7 @@ void RenderPolyPlane::Render(const TriMatrix &worldToClip, subsector_t *sub, uin
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = sub->numlines;
args.mode = TriangleDrawMode::Fan;

View file

@ -48,9 +48,9 @@ void PolySkyDome::Render(const TriMatrix &worldToClip)
backskytex = TexMan(sky2tex, true);
TriMatrix objectToWorld = TriMatrix::translate((float)ViewPos.X, (float)ViewPos.Y, (float)ViewPos.Z);
objectToClip = worldToClip * objectToWorld;
TriUniforms uniforms;
uniforms.objectToClip = worldToClip * objectToWorld;
uniforms.light = 256;
uniforms.flags = 0;
uniforms.subsectorDepth = RenderPolyScene::SkySubsectorDepth;
@ -59,6 +59,7 @@ void PolySkyDome::Render(const TriMatrix &worldToClip)
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &objectToClip;
args.stenciltestvalue = 255;
args.stencilwritevalue = 1;
args.SetTexture(frontskytex);

View file

@ -33,6 +33,7 @@ private:
TArray<TriVertex> mVertices;
TArray<unsigned int> mPrimStart;
int mRows, mColumns;
TriMatrix objectToClip;
void SkyVertex(int r, int c, bool yflip);
void CreateSkyHemisphere(bool zflip);

View file

@ -114,7 +114,6 @@ void RenderPolySprite::Render(const TriMatrix &worldToClip, AActor *thing, subse
bool fullbrightSprite = ((thing->renderflags & RF_FULLBRIGHT) || (thing->flags5 & MF5_BRIGHT));
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
if (fullbrightSprite || fixedlightlev >= 0 || fixedcolormap)
{
uniforms.light = 256;
@ -129,6 +128,7 @@ void RenderPolySprite::Render(const TriMatrix &worldToClip, AActor *thing, subse
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = 4;
args.mode = TriangleDrawMode::Fan;

View file

@ -124,28 +124,28 @@ void PolyTriangleDrawer::draw_arrays(const PolyDrawArgs &drawargs, TriDrawVarian
for (int i = 0; i < vcount / 3; i++)
{
for (int j = 0; j < 3; j++)
vert[j] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[j] = shade_vertex(*drawargs.objectToClip, *(vinput++));
draw_shaded_triangle(vert, ccw, &args, thread, drawfunc);
}
}
else if (drawargs.mode == TriangleDrawMode::Fan)
{
vert[0] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[1] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[0] = shade_vertex(*drawargs.objectToClip, *(vinput++));
vert[1] = shade_vertex(*drawargs.objectToClip, *(vinput++));
for (int i = 2; i < vcount; i++)
{
vert[2] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[2] = shade_vertex(*drawargs.objectToClip, *(vinput++));
draw_shaded_triangle(vert, ccw, &args, thread, drawfunc);
vert[1] = vert[2];
}
}
else // TriangleDrawMode::Strip
{
vert[0] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[1] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[0] = shade_vertex(*drawargs.objectToClip, *(vinput++));
vert[1] = shade_vertex(*drawargs.objectToClip, *(vinput++));
for (int i = 2; i < vcount; i++)
{
vert[2] = shade_vertex(drawargs.uniforms, *(vinput++));
vert[2] = shade_vertex(*drawargs.objectToClip, *(vinput++));
draw_shaded_triangle(vert, ccw, &args, thread, drawfunc);
vert[0] = vert[1];
vert[1] = vert[2];
@ -154,10 +154,10 @@ void PolyTriangleDrawer::draw_arrays(const PolyDrawArgs &drawargs, TriDrawVarian
}
}
TriVertex PolyTriangleDrawer::shade_vertex(const TriUniforms &uniforms, TriVertex v)
TriVertex PolyTriangleDrawer::shade_vertex(const TriMatrix &objectToClip, TriVertex v)
{
// Apply transform to get clip coordinates:
return uniforms.objectToClip * v;
return objectToClip * v;
}
void PolyTriangleDrawer::draw_shaded_triangle(const TriVertex *vert, bool ccw, TriDrawTriangleArgs *args, WorkerThreadData *thread, void(*drawfunc)(const TriDrawTriangleArgs *, WorkerThreadData *))
@ -341,3 +341,150 @@ FString DrawPolyTrianglesCommand::DebugInfo()
{
return "DrawPolyTriangles";
}
/////////////////////////////////////////////////////////////////////////////
TriMatrix TriMatrix::null()
{
TriMatrix m;
memset(m.matrix, 0, sizeof(m.matrix));
return m;
}
TriMatrix TriMatrix::identity()
{
TriMatrix m = null();
m.matrix[0] = 1.0f;
m.matrix[5] = 1.0f;
m.matrix[10] = 1.0f;
m.matrix[15] = 1.0f;
return m;
}
TriMatrix TriMatrix::translate(float x, float y, float z)
{
TriMatrix m = identity();
m.matrix[0 + 3 * 4] = x;
m.matrix[1 + 3 * 4] = y;
m.matrix[2 + 3 * 4] = z;
return m;
}
TriMatrix TriMatrix::scale(float x, float y, float z)
{
TriMatrix m = null();
m.matrix[0 + 0 * 4] = x;
m.matrix[1 + 1 * 4] = y;
m.matrix[2 + 2 * 4] = z;
m.matrix[3 + 3 * 4] = 1;
return m;
}
TriMatrix TriMatrix::rotate(float angle, float x, float y, float z)
{
float c = cosf(angle);
float s = sinf(angle);
TriMatrix m = null();
m.matrix[0 + 0 * 4] = (x*x*(1.0f - c) + c);
m.matrix[0 + 1 * 4] = (x*y*(1.0f - c) - z*s);
m.matrix[0 + 2 * 4] = (x*z*(1.0f - c) + y*s);
m.matrix[1 + 0 * 4] = (y*x*(1.0f - c) + z*s);
m.matrix[1 + 1 * 4] = (y*y*(1.0f - c) + c);
m.matrix[1 + 2 * 4] = (y*z*(1.0f - c) - x*s);
m.matrix[2 + 0 * 4] = (x*z*(1.0f - c) - y*s);
m.matrix[2 + 1 * 4] = (y*z*(1.0f - c) + x*s);
m.matrix[2 + 2 * 4] = (z*z*(1.0f - c) + c);
m.matrix[3 + 3 * 4] = 1.0f;
return m;
}
TriMatrix TriMatrix::swapYZ()
{
TriMatrix m = null();
m.matrix[0 + 0 * 4] = 1.0f;
m.matrix[1 + 2 * 4] = 1.0f;
m.matrix[2 + 1 * 4] = -1.0f;
m.matrix[3 + 3 * 4] = 1.0f;
return m;
}
TriMatrix TriMatrix::perspective(float fovy, float aspect, float z_near, float z_far)
{
float f = (float)(1.0 / tan(fovy * M_PI / 360.0));
TriMatrix m = null();
m.matrix[0 + 0 * 4] = f / aspect;
m.matrix[1 + 1 * 4] = f;
m.matrix[2 + 2 * 4] = (z_far + z_near) / (z_near - z_far);
m.matrix[2 + 3 * 4] = (2.0f * z_far * z_near) / (z_near - z_far);
m.matrix[3 + 2 * 4] = -1.0f;
return m;
}
TriMatrix TriMatrix::frustum(float left, float right, float bottom, float top, float near, float far)
{
float a = (right + left) / (right - left);
float b = (top + bottom) / (top - bottom);
float c = -(far + near) / (far - near);
float d = -(2.0f * far) / (far - near);
TriMatrix m = null();
m.matrix[0 + 0 * 4] = 2.0f * near / (right - left);
m.matrix[1 + 1 * 4] = 2.0f * near / (top - bottom);
m.matrix[0 + 2 * 4] = a;
m.matrix[1 + 2 * 4] = b;
m.matrix[2 + 2 * 4] = c;
m.matrix[2 + 3 * 4] = d;
m.matrix[3 + 2 * 4] = -1;
return m;
}
TriMatrix TriMatrix::worldToView()
{
TriMatrix m = null();
m.matrix[0 + 0 * 4] = (float)ViewSin;
m.matrix[0 + 1 * 4] = (float)-ViewCos;
m.matrix[1 + 2 * 4] = 1.0f;
m.matrix[2 + 0 * 4] = (float)-ViewCos;
m.matrix[2 + 1 * 4] = (float)-ViewSin;
m.matrix[3 + 3 * 4] = 1.0f;
return m * translate((float)-ViewPos.X, (float)-ViewPos.Y, (float)-ViewPos.Z);
}
TriMatrix TriMatrix::viewToClip()
{
float near = 5.0f;
float far = 65536.0f;
float width = (float)(FocalTangent * near);
float top = (float)(CenterY / InvZtoScale * near);
float bottom = (float)(top - viewheight / InvZtoScale * near);
return frustum(-width, width, bottom, top, near, far);
}
TriMatrix TriMatrix::operator*(const TriMatrix &mult) const
{
TriMatrix result;
for (int x = 0; x < 4; x++)
{
for (int y = 0; y < 4; y++)
{
result.matrix[x + y * 4] =
matrix[0 * 4 + x] * mult.matrix[y * 4 + 0] +
matrix[1 * 4 + x] * mult.matrix[y * 4 + 1] +
matrix[2 * 4 + x] * mult.matrix[y * 4 + 2] +
matrix[3 * 4 + x] * mult.matrix[y * 4 + 3];
}
}
return result;
}
TriVertex TriMatrix::operator*(TriVertex v) const
{
float vx = matrix[0 * 4 + 0] * v.x + matrix[1 * 4 + 0] * v.y + matrix[2 * 4 + 0] * v.z + matrix[3 * 4 + 0] * v.w;
float vy = matrix[0 * 4 + 1] * v.x + matrix[1 * 4 + 1] * v.y + matrix[2 * 4 + 1] * v.z + matrix[3 * 4 + 1] * v.w;
float vz = matrix[0 * 4 + 2] * v.x + matrix[1 * 4 + 2] * v.y + matrix[2 * 4 + 2] * v.z + matrix[3 * 4 + 2] * v.w;
float vw = matrix[0 * 4 + 3] * v.x + matrix[1 * 4 + 3] * v.y + matrix[2 * 4 + 3] * v.z + matrix[3 * 4 + 3] * v.w;
v.x = vx;
v.y = vy;
v.z = vz;
v.w = vw;
return v;
}

View file

@ -22,15 +22,27 @@
#pragma once
#include "r_triangle.h"
#include "r_draw.h"
#include "r_thread.h"
#include "r_compiler/llvmdrawers.h"
#include "r_data/r_translate.h"
class FTexture;
enum class TriangleDrawMode
{
Normal,
Fan,
Strip
};
struct TriDrawTriangleArgs;
class PolyDrawArgs
{
public:
TriUniforms uniforms;
const TriMatrix *objectToClip = nullptr;
const TriVertex *vinput = nullptr;
int vcount = 0;
TriangleDrawMode mode = TriangleDrawMode::Normal;
@ -83,7 +95,7 @@ public:
static void draw(const PolyDrawArgs &args, TriDrawVariant variant, TriBlendMode blendmode);
private:
static TriVertex shade_vertex(const TriUniforms &uniforms, TriVertex v);
static TriVertex shade_vertex(const TriMatrix &objectToClip, TriVertex v);
static void draw_arrays(const PolyDrawArgs &args, TriDrawVariant variant, TriBlendMode blendmode, WorkerThreadData *thread);
static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, TriDrawTriangleArgs *args, WorkerThreadData *thread, void(*drawfunc)(const TriDrawTriangleArgs *, WorkerThreadData *));
static bool cullhalfspace(float clipdistance1, float clipdistance2, float &t1, float &t2);

View file

@ -176,13 +176,13 @@ void RenderPolyWall::Render(const TriMatrix &worldToClip)
}
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
uniforms.light = (uint32_t)(GetLightLevel() / 255.0f * 256.0f);
uniforms.flags = 0;
uniforms.subsectorDepth = SubsectorDepth;
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = 4;
args.mode = TriangleDrawMode::Fan;

View file

@ -99,7 +99,6 @@ void RenderPolyWallSprite::Render(const TriMatrix &worldToClip, AActor *thing, s
bool fullbrightSprite = ((thing->renderflags & RF_FULLBRIGHT) || (thing->flags5 & MF5_BRIGHT));
TriUniforms uniforms;
uniforms.objectToClip = worldToClip;
if (fullbrightSprite || fixedlightlev >= 0 || fixedcolormap)
{
uniforms.light = 256;
@ -114,6 +113,7 @@ void RenderPolyWallSprite::Render(const TriMatrix &worldToClip, AActor *thing, s
PolyDrawArgs args;
args.uniforms = uniforms;
args.objectToClip = &worldToClip;
args.vinput = vertices;
args.vcount = 4;
args.mode = TriangleDrawMode::Fan;

View file

@ -22,7 +22,7 @@
#pragma once
#include "r_triangle.h"
#include "r_poly_triangle.h"
class RenderPolyWallSprite
{

File diff suppressed because it is too large Load diff

View file

@ -1,116 +0,0 @@
/*
** Triangle drawers
** Copyright (c) 2016 Magnus Norddahl
**
** This software is provided 'as-is', without any express or implied
** warranty. In no event will the authors be held liable for any damages
** arising from the use of this software.
**
** Permission is granted to anyone to use this software for any purpose,
** including commercial applications, and to alter it and redistribute it
** freely, subject to the following restrictions:
**
** 1. The origin of this software must not be misrepresented; you must not
** claim that you wrote the original software. If you use this software
** in a product, an acknowledgment in the product documentation would be
** appreciated but is not required.
** 2. Altered source versions must be plainly marked as such, and must not be
** misrepresented as being the original software.
** 3. This notice may not be removed or altered from any source distribution.
**
*/
#ifndef __R_TRIANGLE__
#define __R_TRIANGLE__
#include "r_draw.h"
#include "r_thread.h"
#include "r_compiler/llvmdrawers.h"
class FTexture;
struct ScreenTriangleDrawerArgs;
enum class TriangleDrawMode
{
Normal,
Fan,
Strip
};
class TriangleDrawer
{
public:
static void draw(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, FTexture *texture);
static void fill(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, int solidcolor);
private:
static TriVertex shade_vertex(const TriUniforms &uniforms, TriVertex v);
static void draw_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *));
static void draw_shaded_triangle(const TriVertex *vertices, bool ccw, ScreenTriangleDrawerArgs *args, WorkerThreadData *thread, void(*drawfunc)(const ScreenTriangleDrawerArgs *, WorkerThreadData *));
static bool cullhalfspace(float clipdistance1, float clipdistance2, float &t1, float &t2);
static void clipedge(const TriVertex *verts, TriVertex *clippedvert, int &numclipvert);
static void queue_arrays(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *cliptop, const short *clipbottom, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor);
enum { max_additional_vertices = 16 };
friend class DrawTrianglesCommand;
};
struct ScreenTriangleDrawerArgs
{
uint8_t *dest;
int pitch;
TriVertex *v1;
TriVertex *v2;
TriVertex *v3;
int clipleft;
int clipright;
const short *cliptop;
const short *clipbottom;
const uint8_t *texturePixels;
int textureWidth;
int textureHeight;
int solidcolor;
const TriUniforms *uniforms;
};
class ScreenTriangleDrawer
{
public:
static void draw(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread);
static void fill(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread);
static void draw32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread);
static void fill32(const ScreenTriangleDrawerArgs *args, WorkerThreadData *thread);
private:
static float gradx(float x0, float y0, float x1, float y1, float x2, float y2, float c0, float c1, float c2);
static float grady(float x0, float y0, float x1, float y1, float x2, float y2, float c0, float c1, float c2);
};
class DrawTrianglesCommand : public DrawerCommand
{
public:
DrawTrianglesCommand(const TriUniforms &uniforms, const TriVertex *vinput, int vcount, TriangleDrawMode mode, bool ccw, int clipleft, int clipright, const short *clipdata, const uint8_t *texturePixels, int textureWidth, int textureHeight, int solidcolor);
void Execute(DrawerThread *thread) override;
FString DebugInfo() override;
private:
const TriUniforms uniforms;
const TriVertex *vinput;
int vcount;
TriangleDrawMode mode;
bool ccw;
int clipleft;
int clipright;
const short *clipdata;
const uint8_t *texturePixels;
int textureWidth;
int textureHeight;
int solidcolor;
};
#endif