--- ray/src/common/bsdf_m.c 2011/04/24 20:16:52 3.13 +++ ray/src/common/bsdf_m.c 2011/07/07 15:25:09 3.18 @@ -1,5 +1,5 @@ #ifndef lint -static const char RCSid[] = "$Id: bsdf_m.c,v 3.13 2011/04/24 20:16:52 greg Exp $"; +static const char RCSid[] = "$Id: bsdf_m.c,v 3.18 2011/07/07 15:25:09 greg Exp $"; #endif /* * bsdf_m.c @@ -11,6 +11,7 @@ static const char RCSid[] = "$Id: bsdf_m.c,v 3.13 2011 * */ +#define _USE_MATH_DEFINES #include "rtio.h" #include #include @@ -86,18 +87,6 @@ fequal(double a, double b) return (a <= 1e-6) & (a >= -1e-6); } -/* Returns the name of the given tag */ -#ifdef ezxml_name -#undef ezxml_name -static char * -ezxml_name(ezxml_t xml) -{ - if (xml == NULL) - return NULL; - return xml->name; -} -#endif - /* Returns the given tag's character content or empty string if none */ #ifdef ezxml_txt #undef ezxml_txt @@ -189,7 +178,7 @@ fo_getndx(const FVECT v, void *p) { ANGLE_BASIS *ab = (ANGLE_BASIS *)p; int li, ndx; - double pol, azi, d; + double pol, azi; if (v == NULL) return -1; @@ -418,6 +407,8 @@ load_bsdf_data(SDData *sd, ezxml_t wdb, int rowinc) int i; /* allocate BSDF component */ sdata = ezxml_txt(ezxml_child(wdb, "WavelengthDataDirection")); + if (!sdata) + return RC_FAIL; /* * Remember that front and back are reversed from WINDOW 6 orientations * Favor their "Front" (incoming light) since that's more often valid @@ -507,7 +498,7 @@ load_bsdf_data(SDData *sd, ezxml_t wdb, int rowinc) df->comp[0].dist = dp; df->comp[0].func = &SDhandleMtx; /* read BSDF data */ - sdata = ezxml_txt(ezxml_child(wdb,"ScatteringData")); + sdata = ezxml_txt(ezxml_child(wdb, "ScatteringData")); if (!sdata || !*sdata) { sprintf(SDerrorDetail, "Missing BSDF ScatteringData in '%s'", sd->name); @@ -521,12 +512,12 @@ load_bsdf_data(SDData *sd, ezxml_t wdb, int rowinc) sd->name); return RC_FORMERR; } - while (*sdnext && isspace(*sdnext)) + while (isspace(*sdnext)) sdnext++; if (*sdnext == ',') sdnext++; if (rowinc) { int r = i/dp->nout; - int c = i - c*dp->nout; + int c = i - r*dp->nout; mBSDF_value(dp,r,c) = atof(sdata); } else dp->bsdf[i] = atof(sdata); @@ -546,6 +537,10 @@ subtract_min(SDMat *sm) for (i = n; --i; ) if (sm->bsdf[i] < minv) minv = sm->bsdf[i]; + + if (minv <= FTINY) + return .0; + for (i = n; i--; ) sm->bsdf[i] -= minv; @@ -571,7 +566,7 @@ extract_diffuse(SDValue *dv, SDSpectralDF *df) c_cmix(&dv->spec, dv->cieY, &dv->spec, ymin, &df->comp[n].cspec[0]); dv->cieY += ymin; } - df->maxHemi -= dv->cieY; /* adjust minimum hemispherical */ + df->maxHemi -= dv->cieY; /* adjust maximum hemispherical */ /* make sure everything is set */ c_ccvt(&dv->spec, C_CSXY+C_CSSPEC); } @@ -580,12 +575,11 @@ extract_diffuse(SDValue *dv, SDSpectralDF *df) SDError SDloadMtx(SDData *sd, ezxml_t wtl) { - ezxml_t wld, wdb; - int rowIn; - struct BSDF_data *dp; - char *txt; - int rval; - + ezxml_t wld, wdb; + int rowIn; + char *txt; + int rval; + /* basic checks and data ordering */ txt = ezxml_txt(ezxml_child(ezxml_child(wtl, "DataDefinition"), "IncidentDataStructure")); if (txt == NULL || !*txt) { @@ -604,12 +598,14 @@ SDloadMtx(SDData *sd, ezxml_t wtl) sd->name); return SDEsupport; } - /* get angle basis */ - rval = load_angle_basis(ezxml_child(ezxml_child(wtl, - "DataDefinition"), "AngleBasis")); - if (rval < 0) - return convert_errcode(rval); - /* load BSDF components */ + /* get angle bases */ + for (wld = ezxml_child(ezxml_child(wtl, "DataDefinition"), "AngleBasis"); + wld != NULL; wld = wld->next) { + rval = load_angle_basis(wld); + if (rval < 0) + return convert_errcode(rval); + } + /* load BSDF components */ for (wld = ezxml_child(wtl, "WavelengthData"); wld != NULL; wld = wld->next) { if (strcasecmp(ezxml_txt(ezxml_child(wld,"Wavelength")), @@ -620,11 +616,11 @@ SDloadMtx(SDData *sd, ezxml_t wtl) if ((rval = load_bsdf_data(sd, wdb, rowIn)) < 0) return convert_errcode(rval); } - /* separate diffuse components */ + /* separate diffuse components */ extract_diffuse(&sd->rLambFront, sd->rf); extract_diffuse(&sd->rLambBack, sd->rb); extract_diffuse(&sd->tLamb, sd->tf); - /* return success */ + /* return success */ return SDEnone; } @@ -643,7 +639,7 @@ SDgetMtxBSDF(float coef[SDmaxCh], const FVECT outVec, i_ndx = mBSDF_incndx(dp, inVec); o_ndx = mBSDF_outndx(dp, outVec); /* try reciprocity if necessary */ - if ((i_ndx < 0) & (o_ndx < 0)) { + if ((i_ndx < 0) & (o_ndx < 0) && dp->ninc == dp->nout) { i_ndx = mBSDF_incndx(dp, outVec); o_ndx = mBSDF_outndx(dp, inVec); } @@ -687,10 +683,11 @@ SDqueryMtxProjSA(double *psa, const FVECT v1, const RR if (out_psa > psa[1]) psa[1] = out_psa; /* fall through */ - case SDqueryMin: case SDqueryVal: if (qflags == SDqueryVal) psa[0] = M_PI; + /* fall through */ + case SDqueryMin: if ((inc_psa > 0) & (inc_psa < psa[0])) psa[0] = inc_psa; if ((out_psa > 0) & (out_psa < psa[0])) @@ -751,7 +748,7 @@ SDgetMtxCDist(const FVECT inVec, SDComponent *sdc) myCD.ob_vec = dp->ob_vec; myCD.calen = dp->nout; reverse = 0; - } else { /* try reciprocity */ + } else if (dp->ninc == dp->nout) { /* try reciprocity */ myCD.indx = mBSDF_outndx(dp, inVec); if (myCD.indx < 0) return NULL; @@ -761,17 +758,15 @@ SDgetMtxCDist(const FVECT inVec, SDComponent *sdc) reverse = 1; } cdlast = NULL; /* check for it in cache list */ - for (cd = (SDMatCDst *)sdc->cdList; - cd != NULL; cd = (SDMatCDst *)cd->next) { + for (cd = (SDMatCDst *)sdc->cdList; cd != NULL; + cdlast = cd, cd = (SDMatCDst *)cd->next) if (cd->indx == myCD.indx && (cd->calen == myCD.calen) & (cd->ob_priv == myCD.ob_priv) & (cd->ob_vec == myCD.ob_vec)) break; - cdlast = cd; - } if (cd == NULL) { /* need to allocate new entry */ cd = (SDMatCDst *)malloc(sizeof(SDMatCDst) + - myCD.calen*sizeof(myCD.carr[0])); + sizeof(myCD.carr[0])*myCD.calen); if (cd == NULL) return NULL; *cd = myCD; /* compute cumulative distribution */ @@ -803,7 +798,7 @@ SDsampMtxCDist(FVECT ioVec, double randX, const SDCDst /* binary search to find index */ ilower = 0; iupper = mcd->calen; while ((i = (iupper + ilower) >> 1) != ilower) - if ((long)target >= (long)mcd->carr[i]) + if (target >= mcd->carr[i]) ilower = i; else iupper = i;