--- ray/src/ot/cvmesh.c 2003/09/18 16:53:53 2.7 +++ ray/src/ot/cvmesh.c 2004/11/25 14:45:38 2.10 @@ -1,5 +1,5 @@ #ifndef lint -static const char RCSid[] = "$Id: cvmesh.c,v 2.7 2003/09/18 16:53:53 greg Exp $"; +static const char RCSid[] = "$Id: cvmesh.c,v 2.10 2004/11/25 14:45:38 greg Exp $"; #endif /* * Radiance triangle mesh conversion routines @@ -10,6 +10,7 @@ static const char RCSid[] = "$Id: cvmesh.c,v 2.7 2003/ #include "cvmesh.h" #include "otypes.h" #include "face.h" +#include "tmesh.h" /* * We need to divide faces into triangles and record auxiliary information @@ -36,10 +37,16 @@ MESH *ourmesh = NULL; /* our global mesh data structu FVECT meshbounds[2]; /* mesh bounding box */ +static void add2bounds(FVECT vp, RREAL vc[2]); +static OBJECT cvmeshtri(OBJECT obj); +static OCTREE cvmeshoct(OCTREE ot); + + MESH * -cvinit(nm) /* initialize empty mesh */ -char *nm; +cvinit( /* initialize empty mesh */ + char *nm +) { /* free old mesh, first */ if (ourmesh != NULL) { @@ -69,12 +76,13 @@ nomem: int -cvpoly(mo, n, vp, vn, vc) /* convert a polygon to extended triangles */ -OBJECT mo; -int n; -FVECT *vp; -FVECT *vn; -RREAL (*vc)[2]; +cvpoly( /* convert a polygon to extended triangles */ + OBJECT mo, + int n, + FVECT *vp, + FVECT *vn, + RREAL (*vc)[2] +) { int tcnt = 0; int flags; @@ -131,9 +139,10 @@ RREAL (*vc)[2]; static void -add2bounds(vp, vc) /* add point and uv coordinate to bounds */ -FVECT vp; -RREAL vc[2]; +add2bounds( /* add point and uv coordinate to bounds */ + FVECT vp, + RREAL vc[2] +) { register int j; @@ -155,11 +164,18 @@ RREAL vc[2]; int /* create an extended triangle */ -cvtri(mo, vp1, vp2, vp3, vn1, vn2, vn3, vc1, vc2, vc3) -OBJECT mo; -FVECT vp1, vp2, vp3; -FVECT vn1, vn2, vn3; -RREAL vc1[2], vc2[2], vc3[2]; +cvtri( + OBJECT mo, + FVECT vp1, + FVECT vp2, + FVECT vp3, + FVECT vn1, + FVECT vn2, + FVECT vn3, + RREAL vc1[2], + RREAL vc2[2], + RREAL vc3[2] +) { static OBJECT fobj = OVOID; char buf[32]; @@ -169,9 +185,30 @@ RREAL vc1[2], vc2[2], vc3[2]; OBJREC *fop; int j; - flags = MT_V; - if (vn1 != NULL && vn2 != NULL && vn3 != NULL) - flags |= MT_N; + flags = MT_V; /* check what we have */ + if (vn1 != NULL && vn2 != NULL && vn3 != NULL) { + RREAL *rp; + switch (flat_tri(vp1, vp2, vp3, vn1, vn2, vn3)) { + case ISBENT: + flags |= MT_N; + /* fall through */ + case ISFLAT: + break; + case RVBENT: + flags |= MT_N; + rp = vn1; vn1 = vn3; vn3 = rp; + /* fall through */ + case RVFLAT: + rp = vp1; vp1 = vp3; vp3 = rp; + rp = vc1; vc1 = vc3; vc3 = rp; + break; + case DEGEN: + error(WARNING, "degenerate triangle"); + return(0); + default: + error(INTERNAL, "bad return from flat_tri()"); + } + } if (vc1 != NULL && vc2 != NULL && vc3 != NULL) flags |= MT_UV; if (fobj == OVOID) { /* create new triangle object */ @@ -181,7 +218,7 @@ RREAL vc1[2], vc2[2], vc3[2]; fop = objptr(fobj); fop->omod = mo; fop->otype = OBJ_FACE; - sprintf(buf, "t%d", fobj); + sprintf(buf, "t%ld", fobj); fop->oname = savqstr(buf); fop->oargs.nfargs = 9; fop->oargs.farg = (RREAL *)malloc(9*sizeof(RREAL)); @@ -240,8 +277,9 @@ nomem: static OBJECT -cvmeshtri(obj) /* add an extended triangle to our mesh */ -OBJECT obj; +cvmeshtri( /* add an extended triangle to our mesh */ + OBJECT obj +) { OBJREC *o = objptr(obj); TRIDATA *ts; @@ -277,7 +315,7 @@ OBJECT obj; void -cvmeshbounds() /* set mesh boundaries */ +cvmeshbounds(void) /* set mesh boundaries */ { int i; @@ -304,7 +342,7 @@ cvmeshbounds() /* set mesh boundaries */ double marg; /* expand past endpoints */ marg = (2./(1L<<(8*sizeof(uint16)))) * (ourmesh->uvlim[1][i] - - ourmesh->uvlim[0][i]); + ourmesh->uvlim[0][i]) + FTINY; ourmesh->uvlim[0][i] -= marg; ourmesh->uvlim[1][i] += marg; } @@ -314,8 +352,9 @@ cvmeshbounds() /* set mesh boundaries */ static OCTREE -cvmeshoct(ot) /* convert triangles in subtree */ -OCTREE ot; +cvmeshoct( /* convert triangles in subtree */ + OCTREE ot +) { int i; @@ -339,7 +378,7 @@ OCTREE ot; MESH * -cvmesh() /* convert mesh and octree leaf nodes */ +cvmesh(void) /* convert mesh and octree leaf nodes */ { if (ourmesh == NULL) return(NULL);