ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/rt/rv3.c
(Generate patch)

Comparing ray/src/rt/rv3.c (file contents):
Revision 2.18 by greg, Mon Jun 13 20:07:56 2005 UTC vs.
Revision 2.41 by greg, Wed Nov 7 18:34:58 2018 UTC

# Line 13 | Line 13 | static const char      RCSid[] = "$Id$";
13  
14   #include  "ray.h"
15   #include  "rpaint.h"
16 + #include  "otypes.h"
17 + #include  "otspecial.h"
18 + #include  "source.h"
19   #include  "random.h"
20  
21   #ifndef WFLUSH
22 < #ifdef SPEED
20 < #define WFLUSH          (5*SPEED)
21 < #else
22 < #define WFLUSH          100             /* flush after this many rays */
22 > #define WFLUSH          64              /* flush after this many primary rays */
23   #endif
24 + #ifndef WFLUSH1
25 + #define WFLUSH1         512             /* or this many total rays */
26   #endif
27  
28 +
29   #ifdef  SMLFLT
30   #define  sscanvec(s,v)  (sscanf(s,"%f %f %f",v,v+1,v+2)==3)
31   #else
32   #define  sscanvec(s,v)  (sscanf(s,"%lf %lf %lf",v,v+1,v+2)==3)
33   #endif
34  
35 + extern int      ray_pnprocs;
36  
37 + static RNUMBER  niflush;                /* flushes since newimage() */
38 +
39   int
40 < getrect(s, r)                           /* get a box */
41 < char  *s;
42 < register RECT  *r;
40 > getrect(                                /* get a box */
41 >        char  *s,
42 >        RECT  *r
43 > )
44   {
45          int  x0, y0, x1, y1;
46  
# Line 78 | Line 85 | register RECT  *r;
85  
86  
87   int
88 < getinterest(s, direc, vec, mp)          /* get area of interest */
89 < char  *s;
90 < int  direc;
91 < FVECT  vec;
92 < double  *mp;
88 > getinterest(            /* get area of interest */
89 >        char  *s,
90 >        int  direc,
91 >        FVECT  vec,
92 >        double  *mp
93 > )
94   {
95          int  x, y;
96          RAY  thisray;
97 <        register int  i;
97 >        int  i;
98  
99          if (sscanf(s, "%lf", mp) != 1)
100                  *mp = 1.0;
# Line 109 | Line 117 | double  *mp;
117                  }
118                  if (!direc || ourview.type == VT_PAR) {
119                          rayorigin(&thisray, PRIMARY, NULL, NULL);
120 <                        if (!localhit(&thisray, &thescene)) {
120 >                        while (localhit(&thisray, &thescene)) {
121 >                                OBJREC  *m = findmaterial(thisray.ro);
122 >                                if (m != NULL && !istransp(m->otype) &&
123 >                                                !isBSDFproxy(m) &&
124 >                                                (thisray.clipset == NULL ||
125 >                                                        !inset(thisray.clipset,
126 >                                                            thisray.ro->omod)))
127 >                                        break;          /* found something */
128 >                                VCOPY(thisray.rorg, thisray.rop);
129 >                                rayclear(&thisray);     /* skip invisible */
130 >                        }
131 >                        if (thisray.ro == NULL) {
132                                  error(COMMAND, "not a local object");
133                                  return(-1);
134                          }
# Line 134 | Line 153 | double  *mp;
153   }
154  
155  
156 < float *         /* keep consistent with COLOR typedef */
157 < greyof(col)                             /* convert color to greyscale */
158 < register COLOR  col;
156 > COLORV *
157 > greyof(                         /* convert color to greyscale */
158 >        COLOR  col
159 > )
160   {
161          static COLOR  gcol;
162          double  b;
# Line 146 | Line 166 | register COLOR  col;
166          return(gcol);
167   }
168  
169 + static void
170 + recolor(                                        /* recolor the given node */
171 +        PNODE *p
172 + )
173 + {
174 +        while (p->kid != NULL) {                /* need to propogate down */
175 +                int  mx = (p->xmin + p->xmax) >> 1;
176 +                int  my = (p->ymin + p->ymax) >> 1;
177 +                int  ki;
178 +                if (p->x >= mx)
179 +                        ki = (p->y >= my) ? UR : DR;
180 +                else
181 +                        ki = (p->y >= my) ? UL : DL;
182 +                pcopy(p, p->kid+ki);
183 +                p = p->kid + ki;
184 +        }
185  
186 < void
187 < paint(p, xmin, ymin, xmax, ymax)        /* compute and paint a rectangle */
188 < register PNODE  *p;
189 < int  xmin, ymin, xmax, ymax;
186 >        (*dev->paintr)(greyscale?greyof(p->v):p->v,
187 >                        p->xmin, p->ymin, p->xmax, p->ymax);
188 > }
189 >
190 > int
191 > paint(                  /* compute and paint a rectangle */
192 >        PNODE  *p
193 > )
194   {
155        static unsigned long  lastflush = 0;
195          static RAY  thisray;
196          double  h, v;
197  
198 <        if (xmax - xmin <= 0 || ymax - ymin <= 0) {     /* empty */
199 <                p->x = xmin;
200 <                p->y = ymin;
198 >        if ((p->xmax <= p->xmin) | (p->ymax <= p->ymin)) {      /* empty */
199 >                p->x = p->xmin;
200 >                p->y = p->ymin;
201                  setcolor(p->v, 0.0, 0.0, 0.0);
202 <                return;
202 >                return(0);
203          }
204                                                  /* jitter ray direction */
205 <        h = xmin + (xmax-xmin)*frandom();
206 <        v = ymin + (ymax-ymin)*frandom();
205 >        p->x = h = p->xmin + (p->xmax-p->xmin)*frandom();
206 >        p->y = v = p->ymin + (p->ymax-p->ymin)*frandom();
207          
208          if ((thisray.rmax = viewray(thisray.rorg, thisray.rdir, &ourview,
209                          h/hresolu, v/vresolu)) < -FTINY) {
210                  setcolor(thisray.rcol, 0.0, 0.0, 0.0);
211 <        } else {
211 >        } else if (!ray_pnprocs) {              /* immediate mode */
212 >                ray_trace(&thisray);
213 >        } else {                                /* queuing mode */
214 >                int     rval;
215                  rayorigin(&thisray, PRIMARY, NULL, NULL);
216 <                samplendx = rand_samp ? random() : samplendx+1;
217 <                rayvalue(&thisray);
216 >                thisray.rno = (RNUMBER)p;
217 >                rval = ray_pqueue(&thisray);
218 >                if (!rval)
219 >                        return(0);
220 >                if (rval < 0)
221 >                        return(-1);
222 >                                                /* get node for returned ray */
223 >                p = (PNODE *)thisray.rno;
224          }
225  
178        p->x = h;
179        p->y = v;
226          copycolor(p->v, thisray.rcol);
227          scalecolor(p->v, exposure);
228  
229 <        (*dev->paintr)(greyscale?greyof(p->v):p->v, xmin, ymin, xmax, ymax);
229 >        recolor(p);                             /* paint it */
230  
231 <        if (dev->flush != NULL && nrays - lastflush >= WFLUSH) {
232 <                lastflush = nrays;
233 <                (*dev->flush)();
231 >        if (dev->flush != NULL) {               /* shall we check for input? */
232 >                static RNUMBER  lastflush = 0;
233 >                RNUMBER         counter = raynum;
234 >                int             flushintvl;
235 >                if (!ray_pnprocs) {
236 >                        counter = nrays;
237 >                        flushintvl = WFLUSH1;
238 >                } else if (ambounce == 0)
239 >                        flushintvl = ray_pnprocs*WFLUSH;
240 >                else if (niflush < WFLUSH)
241 >                        flushintvl = ray_pnprocs*niflush/(ambounce*(ambounce>0)+1);
242 >                else
243 >                        flushintvl = ray_pnprocs*WFLUSH/(ambounce*(ambounce>0)+1);
244 >                if (lastflush > counter)
245 >                        lastflush = 0;          /* counter wrapped */
246 >
247 >                if (counter - lastflush >= flushintvl) {
248 >                        lastflush = counter;
249 >                        (*dev->flush)();
250 >                        niflush++;
251 >                }
252          }
253 +        return(1);
254   }
255  
256  
257 + int
258 + waitrays(void)                                  /* finish up pending rays */
259 + {
260 +        int     nwaited = 0;
261 +        int     rval;
262 +        RAY     raydone;
263 +
264 +        if (!ray_pnprocs)                       /* immediate mode? */
265 +                return(0);
266 +        while ((rval = ray_presult(&raydone, 0)) > 0) {
267 +                PNODE  *p = (PNODE *)raydone.rno;
268 +                copycolor(p->v, raydone.rcol);
269 +                scalecolor(p->v, exposure);
270 +                recolor(p);
271 +                nwaited++;
272 +        }
273 +        if (rval < 0)
274 +                return(-1);
275 +        return(nwaited);
276 + }
277 +
278 +
279   void
280 < newimage()                              /* start a new image */
280 > newimage(                                       /* start a new image */
281 >        char *s
282 > )
283   {
284 +        int             newnp = 0;
285 +                                                /* # rendering procs arg? */
286 +        if (s != NULL)
287 +                sscanf(s, "%d", &newnp);
288                                                  /* free old image */
289          freepkids(&ptrunk);
197                                                /* save reserve memory */
198        fillreserves();
290                                                  /* compute resolution */
291          hresolu = dev->xsiz;
292          vresolu = dev->ysiz;
293          normaspect(viewaspect(&ourview), &dev->pixaspect, &hresolu, &vresolu);
294 <        pframe.l = pframe.d = 0;
295 <        pframe.r = hresolu; pframe.u = vresolu;
294 >        ptrunk.xmin = ptrunk.ymin = pframe.l = pframe.d = 0;
295 >        ptrunk.xmax = pframe.r = hresolu;
296 >        ptrunk.ymax = pframe.u = vresolu;
297          pdepth = 0;
298                                                  /* clear device */
299          (*dev->clear)(hresolu, vresolu);
300 <                                                /* get first value */
301 <        paint(&ptrunk, 0, 0, hresolu, vresolu);
300 >
301 >        if (newparam) {                         /* (re)start rendering procs */
302 >                if (ray_pnprocs)
303 >                        ray_pclose(0);          /* should already be closed */
304 >                if (newnp > 0)
305 >                        nproc = newnp;
306 >                if (nproc > 1)
307 >                        ray_popen(nproc);
308 >                newparam = 0;
309 >        } else if ((newnp > 0) & (newnp != nproc)) {
310 >                if (newnp == 1)                 /* change # rendering procs */
311 >                        ray_pclose(0);
312 >                else if (newnp < ray_pnprocs)
313 >                        ray_pclose(ray_pnprocs - newnp);
314 >                else
315 >                        ray_popen(newnp - ray_pnprocs);
316 >                nproc = newnp;
317 >        }
318 >        niflush = 0;                            /* get first value */
319 >        paint(&ptrunk);
320   }
321  
322  
323   void
324 < redraw()                                /* redraw the image */
324 > redraw(void)                            /* redraw the image */
325   {
326          (*dev->clear)(hresolu, vresolu);
327          (*dev->comout)("redrawing...\n");
# Line 221 | Line 331 | redraw()                               /* redraw the image */
331  
332  
333   void
334 < repaint(xmin, ymin, xmax, ymax)                 /* repaint a region */
335 < int  xmin, ymin, xmax, ymax;
334 > repaint(                                /* repaint a region */
335 >        int  xmin,
336 >        int  ymin,
337 >        int  xmax,
338 >        int  ymax
339 > )
340   {
341          RECT  reg;
342  
343          reg.l = xmin; reg.r = xmax;
344          reg.d = ymin; reg.u = ymax;
345  
346 <        paintrect(&ptrunk, 0, 0, hresolu, vresolu, &reg);
346 >        paintrect(&ptrunk, &reg);
347   }
348  
349  
350   void
351 < paintrect(p, xmin, ymin, xmax, ymax, r)         /* paint picture rectangle */
352 < register PNODE  *p;
353 < int  xmin, ymin, xmax, ymax;
354 < register RECT  *r;
351 > paintrect(                              /* paint picture rectangle */
352 >        PNODE  *p,
353 >        RECT  *r
354 > )
355   {
356          int  mx, my;
357  
358 <        if (xmax - xmin <= 0 || ymax - ymin <= 0)
358 >        if (p->xmax - p->xmin <= 0 || p->ymax - p->ymin <= 0)
359                  return;
360  
361          if (p->kid == NULL) {
362                  (*dev->paintr)(greyscale?greyof(p->v):p->v,
363 <                                xmin, ymin, xmax, ymax);        /* do this */
363 >                        p->xmin, p->ymin, p->xmax, p->ymax);    /* do this */
364                  return;
365          }
366 <        mx = (xmin + xmax) >> 1;                                /* do kids */
367 <        my = (ymin + ymax) >> 1;
366 >        mx = (p->xmin + p->xmax) >> 1;                          /* do kids */
367 >        my = (p->ymin + p->ymax) >> 1;
368          if (mx > r->l) {
369                  if (my > r->d)
370 <                        paintrect(p->kid+DL, xmin, ymin, mx, my, r);
370 >                        paintrect(p->kid+DL, r);
371                  if (my < r->u)
372 <                        paintrect(p->kid+UL, xmin, my, mx, ymax, r);
372 >                        paintrect(p->kid+UL, r);
373          }
374          if (mx < r->r) {
375                  if (my > r->d)
376 <                        paintrect(p->kid+DR, mx, ymin, xmax, my, r);
376 >                        paintrect(p->kid+DR, r);
377                  if (my < r->u)
378 <                        paintrect(p->kid+UR, mx, my, xmax, ymax, r);
378 >                        paintrect(p->kid+UR, r);
379          }
380   }
381  
382  
383   PNODE *
384 < findrect(x, y, p, r, pd)                /* find a rectangle */
385 < int  x, y;
386 < register PNODE  *p;
387 < register RECT  *r;
388 < int  pd;
384 > findrect(                               /* find a rectangle */
385 >        int  x,
386 >        int  y,
387 >        PNODE  *p,
388 >        int  pd
389 > )
390   {
391          int  mx, my;
392  
393          while (p->kid != NULL && pd--) {
394  
395 <                mx = (r->l + r->r) >> 1;
396 <                my = (r->d + r->u) >> 1;
395 >                mx = (p->xmin + p->xmax) >> 1;
396 >                my = (p->ymin + p->ymax) >> 1;
397  
398                  if (x < mx) {
284                        r->r = mx;
399                          if (y < my) {
286                                r->u = my;
400                                  p = p->kid+DL;
401                          } else {
289                                r->d = my;
402                                  p = p->kid+UL;
403                          }
404                  } else {
293                        r->l = mx;
405                          if (y < my) {
295                                r->u = my;
406                                  p = p->kid+DR;
407                          } else {
298                                r->d = my;
408                                  p = p->kid+UR;
409                          }
410                  }
# Line 305 | Line 414 | int  pd;
414  
415  
416   void
417 < scalepict(p, sf)                        /* scale picture values */
418 < register PNODE  *p;
419 < double  sf;
417 > compavg(                                /* recompute averages */
418 >        PNODE   *p
419 > )
420   {
421 +        int     i, navg;
422 +        
423 +        if (p->kid == NULL)
424 +                return;
425 +
426 +        setcolor(p->v, .0, .0, .0);
427 +        navg = 0;
428 +        for (i = 0; i < 4; i++) {
429 +                if (p->kid[i].xmin >= p->kid[i].xmax) continue;
430 +                if (p->kid[i].ymin >= p->kid[i].ymax) continue;
431 +                compavg(p->kid+i);
432 +                addcolor(p->v, p->kid[i].v);
433 +                navg++;
434 +        }
435 +        if (navg > 1)
436 +                scalecolor(p->v, 1./navg);
437 + }
438 +
439 +
440 + void
441 + scalepict(                              /* scale picture values */
442 +        PNODE  *p,
443 +        double  sf
444 + )
445 + {
446          scalecolor(p->v, sf);           /* do this node */
447  
448          if (p->kid == NULL)
# Line 322 | Line 456 | double  sf;
456  
457  
458   void
459 < getpictcolrs(yoff, scan, p, xsiz, ysiz) /* get scanline from picture */
460 < int  yoff;
461 < register COLR  *scan;
462 < register PNODE  *p;
463 < int  xsiz, ysiz;
459 > getpictcolrs(                           /* get scanline from picture */
460 >        int  yoff,
461 >        COLR  *scan,
462 >        PNODE  *p,
463 >        int  xsiz,
464 >        int  ysiz
465 > )
466   {
467 <        register int  mx;
467 >        int  mx;
468          int  my;
469  
470          if (p->kid == NULL) {                   /* do this node */
# Line 353 | Line 489 | int  xsiz, ysiz;
489  
490  
491   void
492 < freepkids(p)                            /* free pnode's children */
493 < register PNODE  *p;
492 > freepkids(                              /* free pnode's children */
493 >        PNODE  *p
494 > )
495   {
496          if (p->kid == NULL)
497                  return;
# Line 368 | Line 505 | register PNODE  *p;
505  
506  
507   void
508 < newview(vp)                             /* change viewing parameters */
509 < register VIEW  *vp;
508 > newview(                                        /* change viewing parameters */
509 >        VIEW  *vp
510 > )
511   {
512          char  *err;
513  
# Line 379 | Line 517 | register VIEW  *vp;
517          } else if (memcmp((char *)vp, (char *)&ourview, sizeof(VIEW))) {
518                  oldview = ourview;
519                  ourview = *vp;
520 <                newimage();
520 >                newimage(NULL);
521          }
522   }
523  
524  
525   void
526 < moveview(angle, elev, mag, vc)                  /* move viewpoint */
527 < double  angle, elev, mag;
528 < FVECT  vc;
526 > moveview(                                       /* move viewpoint */
527 >        double  angle,
528 >        double  elev,
529 >        double  mag,
530 >        FVECT  vc
531 > )
532   {
533          double  d;
393        FVECT  v1;
534          VIEW  nv = ourview;
535 <        register int  i;
535 >        int  i;
536  
537          spinvector(nv.vdir, ourview.vdir, ourview.vup, angle*(PI/180.));
538 <        if (elev != 0.0) {
539 <                fcross(v1, ourview.vup, nv.vdir);
540 <                normalize(v1);
401 <                spinvector(nv.vdir, nv.vdir, v1, elev*(PI/180.));
402 <        }
538 >        if (elev != 0.0)
539 >                geodesic(nv.vdir, nv.vdir, nv.vup, elev*(-PI/180.), GEOD_RAD);
540 >
541          if (nv.type == VT_PAR) {
542                  nv.horiz /= mag;
543                  nv.vert /= mag;
# Line 425 | Line 563 | FVECT  vc;
563  
564  
565   void
566 < pcopy(p1, p2)                           /* copy paint node p1 into p2 */
567 < register PNODE  *p1, *p2;
566 > pcopy(                                  /* copy paint node p1 into p2 */
567 >        PNODE  *p1,
568 >        PNODE  *p2
569 > )
570   {
571          copycolor(p2->v, p1->v);
572          p2->x = p1->x;
# Line 435 | Line 575 | register PNODE  *p1, *p2;
575  
576  
577   void
578 < zoomview(vp, zf)                        /* zoom in or out */
579 < register VIEW  *vp;
580 < double  zf;
578 > zoomview(                               /* zoom in or out */
579 >        VIEW  *vp,
580 >        double  zf
581 > )
582   {
583          switch (vp->type) {
584          case VT_PAR:                            /* parallel view */
# Line 451 | Line 592 | double  zf;
592                  vp->vert /= zf;
593                  if (vp->vert > 360.)
594                          vp->vert = 360.;
595 +                return;
596 +        case VT_PLS:                            /* planisphere fisheye */
597 +                vp->horiz = sin((PI/180./2.)*vp->horiz) /
598 +                                (1.0 + cos((PI/180./2.)*vp->horiz)) / zf;
599 +                vp->horiz *= vp->horiz;
600 +                vp->horiz = (2.*180./PI)*acos((1. - vp->horiz) /
601 +                                                (1. + vp->horiz));
602 +                vp->vert = sin((PI/180./2.)*vp->vert) /
603 +                                (1.0 + cos((PI/180./2.)*vp->vert)) / zf;
604 +                vp->vert *= vp->vert;
605 +                vp->vert = (2.*180./PI)*acos((1. - vp->vert) /
606 +                                                (1. + vp->vert));
607                  return;
608          case VT_CYL:                            /* cylindrical panorama */
609                  vp->horiz /= zf;

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines