我的三角形光栅化程序按原样工作,但我想通过指定显式坐标而不是差异来使其更容易使用。不幸的是,我不知道如何计算必要的基础变更矩阵。这可以通过空的" rasterizeCnvTri"功能
以下部分是我的代码,使用PixelToaster库作为帧缓冲:
// TrueColor Example
// How to open a display in truecolor mode and work with 32 bit integer pixels.
// Copyright © Glenn Fiedler, 2004-2005. http://www.pixeltoaster.com
#include "pt/source/PixelToaster.h"
using namespace PixelToaster;
int fbuf[256][256][3];
int zbuf[256][256];
void rasterizeTriangle(int u,int dudx,int dudy,int v,int dvdx,int dvdy,int w,int dwdx,int dwdy,int r,int g,int b)
{
int u_rw = u;
int v_rw = v;
int w_rw = w;
for(int j=0; j<256; j++)
{
int u_pt = u_rw;
int v_pt = v_rw;
int w_pt = w_rw;
for(int i=0; i<256; i++)
{
if(w_pt>=zbuf[i][j] && u_pt>=0 && v_pt>=0 && (u_pt+v_pt)<4096)
{fbuf[i][j][0]=r; fbuf[i][j][1]=g; fbuf[i][j][2]=b; zbuf[i][j]=w_pt;}
u_pt += dudx;
v_pt += dvdx;
w_pt += dwdx;
}
u_rw += dudy;
v_rw += dvdy;
w_rw += dwdy;
}
}
void rasterizeCnvTri(int x1,int x2,int x3,int y1,int y2,int y3,int w1,int w2,int w3,int r,int g,int b)
{
//how to do this?
}
int main()
{
const int width = 256;
const int height = 256;
Display display( "Triangle Rasterizer", width, height, Output::Default, Mode::TrueColor );
vector<TrueColorPixel> pixels( width * height );
rasterizeTriangle(-2048,32,0,-2048,0,32,2048,0,0,255,0,0);
rasterizeTriangle(0,32,-32,-2048,0,32,4096,-16,0,255,255,255);
while ( display.open() )
{
unsigned int index = 0;
for ( int y = 0; y < height; ++y )
{
for ( int x = 0; x < width; ++x )
{
pixels[index].r = fbuf[x][y][0];
pixels[index].g = fbuf[x][y][1];
pixels[index].b = fbuf[x][y][2];
++index;
}
}
display.update( pixels );
}
}
U和V是沿两侧的轴,W是反向深度。所有三个坐标都按4096缩放,因此整数就足够了。
[编辑]
以下代码适用于我(也有基本的视角划分):
void rasterizeCnvTri(int x1,int x2,int x3,int y1,int y2,int y3,int w1,int w2,int w3,int r,int g,int b)
{
int xp1 = (((x1-128)*w1)>>8)+128;
int yp1 = (((y1-128)*w1)>>8)+128;
int xp2 = (((x2-128)*w2)>>8)+128;
int yp2 = (((y2-128)*w2)>>8)+128;
int xp3 = (((x3-128)*w3)>>8)+128;
int yp3 = (((y3-128)*w3)>>8)+128;
int xd2 = xp2-xp1;
int xd3 = xp3-xp1;
int yd2 = yp2-yp1;
int yd3 = yp3-yp1;
int wd2 = w2-w1;
int wd3 = w3-w1;
int plna = (yd2*wd3)-(yd3*wd2);
int plnb = (wd2*xd3)-(wd3*xd2);
int plnc = (xd2*yd3)-(xd3*yd2);
int plnd = -(plna*xp1)-(plnb*yp1)-(plnc*w1);
int invdet = (xd2*yd3)-(yd2*xd3);
int dudx = (-yd3<<12)/invdet;
int dudy = (yd2<<12)/invdet;
int u = (-xp1*dudx)-(yp1*dudy);
int dvdx = (xd3<<12)/invdet;
int dvdy = (-xd2<<12)/invdet;
int v = (-xp1*dvdx)-(yp1*dvdy);
rasterizeTriangle(-u,-dudx,-dudy,-v,-dvdx,-dvdy,-plnd/plnc,-plna/plnc,-plnb/plnc,r,g,b);
}