kolibrios-gitea/programs/develop/libraries/TinyGL/asm_fork/ztriangle.inc
IgorA 62b33c4994 Fork for library tinygl, assembly version.
Can draw lines, and do some matrix operations.

git-svn-id: svn://kolibrios.org@5153 a494cfbc-eb01-0410-851d-a64ba20cac60
2014-10-31 21:28:24 +00:00

416 lines
7.7 KiB
C++

;
; We draw a triangle with various interpolations
;
t dd ? ;ZBufferPoint*
pr1 dd ? ;ZBufferPoint*
pr2 dd ? ;ZBufferPoint*
l1 dd ? ;ZBufferPoint*
l2 dd ? ;ZBufferPoint*
fdx1 dd ?
fdx2 dd ?
fdy1 dd ?
fdy2 dd ?
fz dd ?
d1 dd ?
d2 dd ?
pz1 dd ? ;unsigned short*
pp1 dd ? ;PIXEL*
part dd ?
update_left dd ?
update_right dd ?
nb_lines dd ?
dx1 dd ?
dy1 dd ?
tmp dd ?
dx2 dd ?
dy2 dd ?
error dd ?
derror dd ?
x1 dd ?
dxdy_min dd ?
dxdy_max dd ?
; warning: x2 is multiplied by 2^16
x2 dd ?
dx2dy2 dd ?
if INTERP_Z eq 1
z1 dd ?
dzdx dd ?
dzdy dd ?
dzdl_min dd ?
dzdl_max dd ?
end if
if INTERP_RGB eq 1
r1 dd ? ;int
drdx dd ?
drdy dd ?
drdl_min dd ?
drdl_max dd ?
g1 dd ?
dgdx dd ?
dgdy dd ?
dgdl_min dd ?
dgdl_max dd ?
b1 dd ?
dbdx dd ?
dbdy dd ?
dbdl_min dd ?
dbdl_max dd ?
end if
if INTERP_ST eq 1
;s1 dd ?
dsdx dd ?
dsdy dd ?
dsdl_min dd ?
dsdl_max dd ?
t1 dd ?
dtdx dd ?
dtdy dd ?
dtdl_min dd ?
dtdl_max dd ?
end if
if INTERP_STZ eq 1
sz1 dd ?
dszdx dd ?
dszdy dd ?
dszdl_min dd ?
dszdl_max dd ?
tz1 dd ?
dtzdx dd ?
dtzdy dd ?
dtzdl_min dd ?
dtzdl_max dd ?
end if
endl
; /* we sort the vertex with increasing y */
; if (p1->y < p0->y) {
; t = p0;
; p0 = p1;
; p1 = t;
; }
; if (p2->y < p0->y) {
; t = p2;
; p2 = p1;
; p1 = p0;
; p0 = t;
; } else if (p2->y < p1->y) {
; t = p1;
; p1 = p2;
; p2 = t;
; }
; we compute dXdx and dXdy for all interpolated values
; fdx1 = p1->x - p0->x;
; fdy1 = p1->y - p0->y;
; fdx2 = p2->x - p0->x;
; fdy2 = p2->y - p0->y;
; fz = fdx1 * fdy2 - fdx2 * fdy1;
; if (fz == 0)
; return;
; fz = 1.0 / fz;
; fdx1 *= fz;
; fdy1 *= fz;
; fdx2 *= fz;
; fdy2 *= fz;
if INTERP_Z eq 1
; d1 = p1->z - p0->z;
; d2 = p2->z - p0->z;
; dzdx = (int) (fdy2 * d1 - fdy1 * d2);
; dzdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_RGB eq 1
; d1 = p1->r - p0->r;
; d2 = p2->r - p0->r;
; drdx = (int) (fdy2 * d1 - fdy1 * d2);
; drdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->g - p0->g;
; d2 = p2->g - p0->g;
; dgdx = (int) (fdy2 * d1 - fdy1 * d2);
; dgdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->b - p0->b;
; d2 = p2->b - p0->b;
; dbdx = (int) (fdy2 * d1 - fdy1 * d2);
; dbdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_ST eq 1
; d1 = p1->s - p0->s;
; d2 = p2->s - p0->s;
; dsdx = (int) (fdy2 * d1 - fdy1 * d2);
; dsdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->t - p0->t;
; d2 = p2->t - p0->t;
; dtdx = (int) (fdy2 * d1 - fdy1 * d2);
; dtdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_STZ eq 1
; {
; float zz;
; zz=(float) p0->z;
; p0->sz= (float) p0->s * zz;
; p0->tz= (float) p0->t * zz;
; zz=(float) p1->z;
; p1->sz= (float) p1->s * zz;
; p1->tz= (float) p1->t * zz;
; zz=(float) p2->z;
; p2->sz= (float) p2->s * zz;
; p2->tz= (float) p2->t * zz;
; d1 = p1->sz - p0->sz;
; d2 = p2->sz - p0->sz;
; dszdx = (fdy2 * d1 - fdy1 * d2);
; dszdy = (fdx1 * d2 - fdx2 * d1);
; d1 = p1->tz - p0->tz;
; d2 = p2->tz - p0->tz;
; dtzdx = (fdy2 * d1 - fdy1 * d2);
; dtzdy = (fdx1 * d2 - fdx2 * d1);
; }
end if
; screen coordinates
; pp1 = (PIXEL *) ((char *) zb->pbuf + zb->linesize * p0->y);
; pz1 = zb->zbuf + p0->y * zb->xsize;
DRAW_INIT
; for(part=0;part<2;part++) {
; if (part == 0) {
; if (fz > 0) {
; update_left=1;
; update_right=1;
; l1=p0;
; l2=p2;
; pr1=p0;
; pr2=p1;
; } else {
; update_left=1;
; update_right=1;
; l1=p0;
; l2=p1;
; pr1=p0;
; pr2=p2;
; }
; nb_lines = p1->y - p0->y;
; } else {
; /* second part */
; if (fz > 0) {
; update_left=0;
; update_right=1;
; pr1=p1;
; pr2=p2;
; } else {
; update_left=1;
; update_right=0;
; l1=p1;
; l2=p2;
; }
; nb_lines = p2->y - p1->y + 1;
; }
; compute the values for the left edge
; if (update_left) {
; dy1 = l2->y - l1->y;
; dx1 = l2->x - l1->x;
; if (dy1 > 0)
; tmp = (dx1 << 16) / dy1;
; else
; tmp = 0;
; x1 = l1->x;
; error = 0;
; derror = tmp & 0x0000ffff;
; dxdy_min = tmp >> 16;
; dxdy_max = dxdy_min + 1;
if INTERP_Z eq 1
; z1=l1->z;
; dzdl_min=(dzdy + dzdx * dxdy_min);
; dzdl_max=dzdl_min + dzdx;
end if
if INTERP_RGB eq 1
; r1=l1->r;
; drdl_min=(drdy + drdx * dxdy_min);
; drdl_max=drdl_min + drdx;
; g1=l1->g;
; dgdl_min=(dgdy + dgdx * dxdy_min);
; dgdl_max=dgdl_min + dgdx;
; b1=l1->b;
; dbdl_min=(dbdy + dbdx * dxdy_min);
; dbdl_max=dbdl_min + dbdx;
end if
if INTERP_ST eq 1
; s1=l1->s;
; dsdl_min=(dsdy + dsdx * dxdy_min);
; dsdl_max=dsdl_min + dsdx;
; t1=l1->t;
; dtdl_min=(dtdy + dtdx * dxdy_min);
; dtdl_max=dtdl_min + dtdx;
end if
if INTERP_STZ eq 1
; sz1=l1->sz;
; dszdl_min=(dszdy + dszdx * dxdy_min);
; dszdl_max=dszdl_min + dszdx;
; tz1=l1->tz;
; dtzdl_min=(dtzdy + dtzdx * dxdy_min);
; dtzdl_max=dtzdl_min + dtzdx;
end if
; }
; /* compute values for the right edge */
; if (update_right) {
; dx2 = (pr2->x - pr1->x);
; dy2 = (pr2->y - pr1->y);
; if (dy2>0)
; dx2dy2 = ( dx2 << 16) / dy2;
; else
; dx2dy2 = 0;
; x2 = pr1->x << 16;
; }
; /* we draw all the scan line of the part */
; while (nb_lines>0) {
; nb_lines--;
;#ifndef DRAW_LINE
; /* generic draw line */
; {
; register PIXEL *pp;
; register int n;
if INTERP_Z eq 1
; register unsigned short *pz;
; register unsigned int z,zz;
end if
if INTERP_RGB eq 1
; register unsigned int or1,og1,ob1;
end if
if INTERP_ST eq 1
; register unsigned int s,t;
end if
if INTERP_STZ eq 1
; float sz,tz;
end if
; n=(x2 >> 16) - x1;
; pp=(PIXEL *)((char *)pp1 + x1 * PSZB);
if INTERP_Z eq 1
; pz=pz1+x1;
; z=z1;
end if
if INTERP_RGB eq 1
; or1 = r1;
; og1 = g1;
; ob1 = b1;
end if
if INTERP_ST eq 1
; s=s1;
; t=t1;
end if
if INTERP_STZ eq 1
; sz=sz1;
; tz=tz1;
end if
; while (n>=3) {
; PUT_PIXEL(0);
; PUT_PIXEL(1);
; PUT_PIXEL(2);
; PUT_PIXEL(3);
if INTERP_Z eq 1
; pz+=4;
end if
; pp=(PIXEL *)((char *)pp + 4 * PSZB);
; n-=4;
; }
; while (n>=0) {
; PUT_PIXEL(0);
if INTERP_Z eq 1
; pz+=1;
end if
; pp=(PIXEL *)((char *)pp + PSZB);
; n-=1;
; }
; }
;#else
; DRAW_LINE();
;#endif
;
; /* left edge */
; error+=derror;
; if (error > 0) {
; error-=0x10000;
; x1+=dxdy_max;
if INTERP_Z eq 1
; z1+=dzdl_max;
end if
if INTERP_RGB eq 1
; r1+=drdl_max;
; g1+=dgdl_max;
; b1+=dbdl_max;
end if
if INTERP_ST eq 1
; s1+=dsdl_max;
; t1+=dtdl_max;
end if
if INTERP_STZ eq 1
; sz1+=dszdl_max;
; tz1+=dtzdl_max;
end if
; } else {
; x1+=dxdy_min;
if INTERP_Z eq 1
; z1+=dzdl_min;
end if
if INTERP_RGB eq 1
; r1+=drdl_min;
; g1+=dgdl_min;
; b1+=dbdl_min;
end if
if INTERP_ST eq 1
; s1+=dsdl_min;
; t1+=dtdl_min;
end if
if INTERP_STZ eq 1
; sz1+=dszdl_min;
; tz1+=dtzdl_min;
end if
; }
;
; /* right edge */
; x2+=dx2dy2;
;
; /* screen coordinates */
; pp1=(PIXEL *)((char *)pp1 + zb->linesize);
; pz1+=zb->xsize;
; }
; }
;}
restore INTERP_Z
restore INTERP_RGB
restore INTERP_ST
restore INTERP_STZ
purge DRAW_INIT
purge DRAW_LINE
purge PUT_PIXEL