Back to index

radiance  4R0+20100331
Defines | Typedefs | Functions | Variables
rhpict2.c File Reference
#include <string.h>
#include "holo.h"
#include "view.h"
#include "random.h"

Go to the source code of this file.

Defines

#define DEPS   0.02 /* depth epsilon */
#define PEPS   0.04 /* pixel value epsilon */
#define MAXRAD   64 /* maximum kernel radius */
#define NNEIGH   5 /* find this many neighbors */
#define NINF   16382
#define MAXRAD2   (MAXRAD*MAXRAD+1)
#define G0NORM   0.286 /* ground zero normalization (1/x integral) */
#define FL4OP(f, i, op)   ((f)[(i)>>5] op (1L<<((i)&0x1f)))
#define CHK4(f, i)   FL4OP(f,i,&)
#define SET4(f, i)   FL4OP(f,i,|=)
#define CLR4(f, i)   FL4OP(f,i,&=~)
#define TGL4(f, i)   FL4OP(f,i,^=)
#define FL4NELS(n)   (((n)+0x1f)>>5)
#define CLR4ALL(f, n)   memset((char *)(f),'\0',FL4NELS(n)*sizeof(int32))
#define isqrt(i2)   (isqrttab[i2])

Typedefs

typedef int( sampfunc )(int h, int v, short nl[NNEIGH][2], int nd[NNEIGH], int n, double *rf)

Functions

void pixFinish (double ransamp)
void pixBeam (BEAM *bp, HDBEAMI *hb)
static void meet_neighbors (int occ, sampfunc *nf, double *dp)
static void reset_flags (void)
static void init_wfunc (void)
static int findneigh (short nl[NNEIGH][2], int nd[NNEIGH], int h, int v, register short(*rnl)[NNEIGH])
void pixBeam (BEAM *bp, register HDBEAMI *hb)
static int kill_occl (int h, int v, register short nl[NNEIGH][2], int nd[NNEIGH], int n, double *rf)
static int smooth_samp (int h, int v, register short nl[NNEIGH][2], int nd[NNEIGH], int n, double *rf)
static int random_samp (int h, int v, register short nl[NNEIGH][2], int nd[NNEIGH], int n, double *rf)

Variables

static const char RCSid [] = "$Id: rhpict2.c,v 3.15 2004/01/01 11:21:55 schorsch Exp $"
static int32 * pixFlags
static float pixWeight [MAXRAD2]
static short isqrttab [MAXRAD2]
VIEW myview
COLORmypixel
float * myweight
float * mydepth
int hres
int vres
static sampfunc kill_occl
static sampfunc smooth_samp
static sampfunc random_samp

Define Documentation

#define CHK4 (   f,
  i 
)    FL4OP(f,i,&)

Definition at line 35 of file rhpict2.c.

#define CLR4 (   f,
  i 
)    FL4OP(f,i,&=~)

Definition at line 37 of file rhpict2.c.

#define CLR4ALL (   f,
  n 
)    memset((char *)(f),'\0',FL4NELS(n)*sizeof(int32))

Definition at line 40 of file rhpict2.c.

#define DEPS   0.02 /* depth epsilon */

Definition at line 15 of file rhpict2.c.

#define FL4NELS (   n)    (((n)+0x1f)>>5)

Definition at line 39 of file rhpict2.c.

#define FL4OP (   f,
  i,
  op 
)    ((f)[(i)>>5] op (1L<<((i)&0x1f)))

Definition at line 34 of file rhpict2.c.

#define G0NORM   0.286 /* ground zero normalization (1/x integral) */

Definition at line 31 of file rhpict2.c.

#define isqrt (   i2)    (isqrttab[i2])

Definition at line 47 of file rhpict2.c.

#define MAXRAD   64 /* maximum kernel radius */

Definition at line 21 of file rhpict2.c.

#define MAXRAD2   (MAXRAD*MAXRAD+1)

Definition at line 29 of file rhpict2.c.

#define NINF   16382

Definition at line 27 of file rhpict2.c.

#define NNEIGH   5 /* find this many neighbors */

Definition at line 24 of file rhpict2.c.

#define PEPS   0.04 /* pixel value epsilon */

Definition at line 18 of file rhpict2.c.

#define SET4 (   f,
  i 
)    FL4OP(f,i,|=)

Definition at line 36 of file rhpict2.c.

#define TGL4 (   f,
  i 
)    FL4OP(f,i,^=)

Definition at line 38 of file rhpict2.c.


Typedef Documentation

typedef int( sampfunc)(int h, int v, short nl[NNEIGH][2], int nd[NNEIGH], int n, double *rf)

Definition at line 58 of file rhpict2.c.


Function Documentation

static int findneigh ( short  nl[NNEIGH][2],
int  nd[NNEIGH],
int  h,
int  v,
register short(*)  rnl[NNEIGH] 
) [static]

Definition at line 318 of file rhpict2.c.

{
       int    nn = 0;
       int    d, n, hoff;
       register int  h2, n2;

       nd[NNEIGH-1] = MAXRAD2;
       for (hoff = 0; hoff < hres; hoff = (hoff<=0) - hoff) {
              h2 = h + hoff;
              if ((h2 < 0) | (h2 >= hres))
                     continue;
              if ((h2-h)*(h2-h) >= nd[NNEIGH-1])
                     break;
              for (n = 0; n < NNEIGH && rnl[h2][n] < NINF; n++) {
                     d = (h2-h)*(h2-h) + (v-rnl[h2][n])*(v-rnl[h2][n]);
                     if ((d == 0) | (d >= nd[NNEIGH-1]))
                            continue;
                     if (nn < NNEIGH)     /* insert neighbor */
                            nn++;
                     for (n2 = nn; n2--; )       {
                            if (!n2 || d >= nd[n2-1]) {
                                   nd[n2] = d;
                                   nl[n2][0] = h2;
                                   nl[n2][1] = rnl[h2][n];
                                   break;
                            }
                            nd[n2] = nd[n2-1];
                            nl[n2][0] = nl[n2-1][0];
                            nl[n2][1] = nl[n2-1][1];
                     }
              }
       }
       return(nn);
}

Here is the caller graph for this function:

static void init_wfunc ( void  ) [static]

Definition at line 302 of file rhpict2.c.

{
       register int  r2;
       register double      d;

       for (r2 = MAXRAD2; --r2; ) {
              d = sqrt((double)r2);
              pixWeight[r2] = G0NORM/d;
              isqrttab[r2] = d + 0.99;
       }
       pixWeight[0] = 1.;
       isqrttab[0] = 0;
}

Here is the caller graph for this function:

static int kill_occl ( int  h,
int  v,
register short  nl[NNEIGH][2],
int  nd[NNEIGH],
int  n,
double *  rf 
) [static]

Definition at line 130 of file rhpict2.c.

{
       short  forequad[2][2];
       int    d;
       register int  i;
       register int32       p;

       if (n <= 0) {
#ifdef DEBUG
              error(WARNING, "neighborless sample in kill_occl");
#endif
              return(1);
       }
       p = v*hres + h;
       forequad[0][0] = forequad[0][1] = forequad[1][0] = forequad[1][1] = 0;
       for (i = n; i--; ) {
              d = isqrt(nd[i]);
              if (mydepth[nl[i][1]*hres+nl[i][0]]*(1.+DEPS*d) < mydepth[p])
                     forequad[nl[i][0]<h][nl[i][1]<v] = 1;
       }
       if (forequad[0][0]+forequad[0][1]+forequad[1][0]+forequad[1][1] > 2) {
              setcolor(mypixel[p], 0., 0., 0.);
              myweight[p] = 0.;    /* occupancy reset afterwards */
       }
       return(1);
}

Here is the call graph for this function:

static void meet_neighbors ( int  occ,
sampfunc nf,
double *  dp 
) [static]

Definition at line 361 of file rhpict2.c.

{
       short  ln[NNEIGH][2];
       int    nd[NNEIGH];
       int    h, v, n, v2;
       register short       (*rnl)[NNEIGH];
                                   /* initialize bottom row list */
       rnl = (short (*)[NNEIGH])malloc(NNEIGH*sizeof(short)*hres);
       CHECK(rnl==NULL, SYSTEM, "out of memory in meet_neighbors");
       for (h = 0; h < hres; h++) {
              for (n = v = 0; v < vres; v++)
                     if (CHK4(pixFlags, v*hres+h)) {
                            rnl[h][n++] = v;
                            if (n >= NNEIGH)
                                   break;
                     }
              while (n < NNEIGH)
                     rnl[h][n++] = NINF;
       }
       v = 0;                      /* do each row */
       for ( ; ; ) {
              for (h = 0; h < hres; h++) {
                     if (!CHK4(pixFlags, v*hres+h) != !occ)
                            continue;     /* occupancy mismatch */
                                          /* find neighbors */
                     n = findneigh(ln, nd, h, v, rnl);
                                          /* call on neighbors */
                     (*nf)(h, v, ln, nd, n, dp);
              }
              if (++v >= vres)            /* reinitialize row list */
                     break;
              for (h = 0; h < hres; h++)
                     for (v2 = rnl[h][NNEIGH-1]+1; v2 < vres; v2++) {
                            if (v2 - v > v - rnl[h][0])
                                   break;        /* not close enough */
                            if (CHK4(pixFlags, v2*hres+h)) {
                                   for (n = 0; n < NNEIGH-1; n++)
                                          rnl[h][n] = rnl[h][n+1];
                                   rnl[h][NNEIGH-1] = v2;
                            }
                     }
       }
       free((void *)rnl);          /* free row list */
}

Here is the call graph for this function:

Here is the caller graph for this function:

void pixBeam ( BEAM bp,
HDBEAMI hb 
)
void pixBeam ( BEAM bp,
register HDBEAMI hb 
)

Definition at line 71 of file rhpict2.c.

{
       GCOORD gc[2];
       register RAYVAL      *rv;
       FVECT  rorg, rdir, wp, ip;
       double d, prox;
       COLOR  col;
       int    n;
       register int32       p;

       if (!hdbcoord(gc, hb->h, hb->b))
              error(CONSISTENCY, "bad beam in render_beam");
       for (n = bp->nrm, rv = hdbray(bp); n--; rv++) {
                                          /* reproject each sample */
              hdray(rorg, rdir, hb->h, gc, rv->r);
              if (rv->d < DCINF) {
                     d = hddepth(hb->h, rv->d);
                     VSUM(wp, rorg, rdir, d);
                     VSUB(ip, wp, myview.vp);
                     d = DOT(ip,rdir);
                     prox = d*d/DOT(ip,ip);      /* cos(diff_angle)^32 */
                     prox *= prox; prox *= prox; prox *= prox; prox *= prox;
              } else {
                     if (myview.type == VT_PAR || myview.vaft > FTINY)
                            continue;            /* inf. off view */
                     VSUM(wp, myview.vp, rdir, FHUGE);
                     prox = 1.;
              }
              viewloc(ip, &myview, wp);   /* frustum clipping */
              if (ip[2] < 0.)
                     continue;
              if (ip[0] < 0. || ip[0] >= 1.)
                     continue;
              if (ip[1] < 0. || ip[1] >= 1.)
                     continue;
              if (myview.vaft > FTINY && ip[2] > myview.vaft - myview.vfore)
                     continue;            /* not exact for VT_PER */
              p = (int)(ip[1]*vres)*hres + (int)(ip[0]*hres);
              if (mydepth[p] > FTINY) {   /* check depth */
                     if (ip[2] > mydepth[p]*(1.+DEPS))
                            continue;
                     if (ip[2] < mydepth[p]*(1.-DEPS)) {
                            setcolor(mypixel[p], 0., 0., 0.);
                            myweight[p] = 0.;
                     }
              }
              colr_color(col, rv->v);
              scalecolor(col, prox);
              addcolor(mypixel[p], col);
              myweight[p] += prox;
              mydepth[p] = ip[2];
       }
}

Here is the call graph for this function:

void pixFinish ( double  ransamp)

Definition at line 267 of file rhpict2.c.

{
       if (pixWeight[0] <= FTINY)
              init_wfunc();        /* initialize weighting function */
       reset_flags();                     /* set occupancy flags */
       meet_neighbors(1,kill_occl,NULL); /* identify occlusion errors */
       reset_flags();                     /* reset occupancy flags */
       if (ransamp >= 0.)          /* spread samples over image */
              meet_neighbors(0,random_samp,&ransamp);
       else
              meet_neighbors(1,smooth_samp,NULL);
       free((void *)pixFlags);            /* free pixel flags */
       pixFlags = NULL;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int random_samp ( int  h,
int  v,
register short  nl[NNEIGH][2],
int  nd[NNEIGH],
int  n,
double *  rf 
) [static]

Definition at line 231 of file rhpict2.c.

{
       float  rnt[NNEIGH];
       double rvar;
       register int32       p, pn;
       register int  ni;

       if (n <= 0)
              return(1);
       p = v*hres + h;
       if (*rf <= FTINY)           /* straight Voronoi regions */
              ni = 0;
       else {                      /* weighted choice */
              DCHECK(nd[n-1]>=MAXRAD2, CONSISTENCY, "out of range neighbor");
              rnt[0] = pixWeight[nd[0]];
              for (ni = 1; ni < n; ni++)
                     rnt[ni] = rnt[ni-1] + pixWeight[nd[ni]];
              rvar = rnt[n-1]*pow(frandom(), 1. / *rf);
              for (ni = 0; rvar > rnt[ni]+FTINY; ni++)
                     ;
       }
       pn = nl[ni][1]*hres + nl[ni][0];
       addcolor(mypixel[p], mypixel[pn]);
       myweight[p] += myweight[pn];
       return(1);
}
static void reset_flags ( void  ) [static]

Definition at line 286 of file rhpict2.c.

{
       register int32       p;

       if (pixFlags == NULL) {
              pixFlags = (int32 *)calloc(FL4NELS(hres*vres), sizeof(int32));
              CHECK(pixFlags==NULL, SYSTEM, "out of memory in reset_flags");
       } else
              CLR4ALL(pixFlags, hres*vres);
       for (p = hres*vres; p--; )
              if (myweight[p] > FTINY)
                     SET4(pixFlags, p);
}

Here is the caller graph for this function:

static int smooth_samp ( int  h,
int  v,
register short  nl[NNEIGH][2],
int  nd[NNEIGH],
int  n,
double *  rf 
) [static]

Definition at line 166 of file rhpict2.c.

{
       int    dis[NNEIGH], ndis;
       COLOR  mykern[MAXRAD2];
       int    maxr2;
       double d;
       register int32       p;
       register int  r2;
       int    i, r, maxr, h2, v2;

       if (n <= 0)
              return(1);
       p = v*hres + h;                           /* build kernel values */
       maxr2 = nd[n-1];
       DCHECK(maxr2>=MAXRAD2, CONSISTENCY, "out of range neighbor");
       maxr = isqrt(maxr2);
       for (v2 = 1; v2 <= maxr; v2++)
              for (h2 = 0; h2 <= v2; h2++) {
                     r2 = h2*h2 + v2*v2;
                     if (r2 > maxr2) break;
                     copycolor(mykern[r2], mypixel[p]);
                     scalecolor(mykern[r2], pixWeight[r2]);
              }
       ndis = 0;                          /* find discontinuities */
       for (i = n; i--; ) {
              r = isqrt(nd[i]);
              d = mydepth[nl[i][1]*hres+nl[i][0]] / mydepth[p];
              d = d>=1. ? d-1. : 1.-d;
              if (d > r*DEPS || bigdiff(mypixel[p],
                            mypixel[nl[i][1]*hres+nl[i][0]], r*PEPS))
                     dis[ndis++] = i;
       }
                                          /* stamp out that kernel */
       for (v2 = v-maxr; v2 <= v+maxr; v2++) {
              if (v2 < 0) v2 = 0;
              else if (v2 >= vres) break;
              for (h2 = h-maxr; h2 <= h+maxr; h2++) {
                     if (h2 < 0) h2 = 0;
                     else if (h2 >= hres) break;
                     r2 = (h2-h)*(h2-h) + (v2-v)*(v2-v);
                     if (r2 > maxr2) continue;
                     if (CHK4(pixFlags, v2*hres+h2))
                            continue;     /* occupied */
                     for (i = ndis; i--; ) {
                            r = (h2-nl[dis[i]][0])*(h2-nl[dis[i]][0]) +
                                   (v2-nl[dis[i]][1])*(v2-nl[dis[i]][1]);
                            if (r < r2) break;
                     }
                     if (i >= 0) continue;       /* outside edge */
                     addcolor(mypixel[v2*hres+h2], mykern[r2]);
                     myweight[v2*hres+h2] += pixWeight[r2] * myweight[p];
              }
       }
       return(1);
}

Here is the call graph for this function:


Variable Documentation

int hres

Definition at line 30 of file rhpict.c.

short isqrttab[MAXRAD2] [static]

Definition at line 45 of file rhpict2.c.

sampfunc kill_occl [static]

Definition at line 60 of file rhpict2.c.

float* mydepth

Definition at line 29 of file rhpict.c.

Definition at line 27 of file rhpict.c.

Definition at line 19 of file rhpict.c.

float* myweight

Definition at line 28 of file rhpict.c.

int32* pixFlags [static]

Definition at line 43 of file rhpict2.c.

float pixWeight[MAXRAD2] [static]

Definition at line 44 of file rhpict2.c.

Definition at line 62 of file rhpict2.c.

const char RCSid[] = "$Id: rhpict2.c,v 3.15 2004/01/01 11:21:55 schorsch Exp $" [static]

Definition at line 2 of file rhpict2.c.

Definition at line 61 of file rhpict2.c.

int vres

Definition at line 30 of file rhpict.c.