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

Comparing ray/src/hd/rhdobj.c (file contents):
Revision 3.3 by gwlarson, Tue Aug 25 18:10:12 1998 UTC vs.
Revision 3.15 by schorsch, Mon Jul 21 22:30:18 2003 UTC

# Line 1 | Line 1
1 /* Copyright (c) 1998 Silicon Graphics, Inc. */
2
1   #ifndef lint
2 < static char SCCSid[] = "$SunId$ SGI";
2 > static const char       RCSid[] = "$Id$";
3   #endif
6
4   /*
5 < * Routines for loading and displaying Radiance objects under OpenGL in rholo.
5 > * Routines for loading and displaying Radiance objects in rholo with GLX.
6   */
7  
8 + #include <string.h>
9 +
10   #include "radogl.h"
11   #include "tonemap.h"
12   #include "rhdisp.h"
13   #include "rhdriver.h"
14   #include "rhdobj.h"
15 + #include "rtprocess.h"
16  
17   extern FILE     *sstdout;               /* user standard output */
18  
# Line 22 | Line 22 | int    (*dobj_lightsamp)() = NULL;     /* pointer to function
22  
23   #define AVGREFL         0.5             /* assumed average reflectance */
24  
25 < #define MAXAC           64              /* maximum number of args */
25 > #define MAXAC           512             /* maximum number of args */
26  
27   #ifndef MINTHRESH
28   #define MINTHRESH       5.0             /* source threshold w.r.t. mean */
# Line 53 | Line 53 | typedef struct dobject {
53          struct dobject  *next;          /* next object in list */
54          char    name[64];               /* object name */
55          FVECT   center;                 /* orig. object center */
56 <        FLOAT   radius;                 /* orig. object radius */
56 >        RREAL   radius;                 /* orig. object radius */
57          int     listid;                 /* GL display list identifier */
58 <        int     rtp[3];                 /* associated rtrace process */
58 >        int     nlists;                 /* number of lists allocated */
59 >        SUBPROC rtp;                    /* associated rtrace process */
60          DLIGHTS *ol;                    /* object lights */
61          FULLXF  xfb;                    /* coordinate transform */
62          short   drawcode;               /* drawing code */
# Line 119 | Line 120 | register DOBJECT       *op;
120          }
121          dobjects = ohead.next;
122          if (!foundlink) {
123 <                glDeleteLists(op->listid, 1);
124 <                close_process(op->rtp);
123 >                glDeleteLists(op->listid, op->nlists);
124 >                close_process(&(op->rtp));
125          }
126          while (op->xfac)
127                  freestr(op->xfav[--op->xfac]);
128 <        free((char *)op);
128 >        free((void *)op);
129          return(1);
130   }
131  
# Line 299 | Line 300 | ssph_compute()                 /* compute source set from sphere sam
300                                                  /* avg. reflected brightness */
301          d = AVGREFL / (double)ncells;  
302          scalecolor(csum, d);
303 <        if (tmCvColors(&dlightsets->larb, TM_NOCHROM, csum, 1) != TM_E_OK)
303 >        if (tmCvColors(&dlightsets->larb, TM_NOCHROM, &csum, 1) != TM_E_OK)
304                  error(CONSISTENCY, "tone mapping problem in ssph_compute");
305                                          /* greedy light source clustering */
306          while (dlightsets->nl < MAXLIGHTS) {
# Line 320 | Line 321 | ssph_compute()                 /* compute source set from sphere sam
321                                  continue;               /* too dim */
322                          ssph_direc(v, alt, azi);        /* else add it in */
323                          VSUM(ls->direc, ls->direc, v, d);
324 <                        ls->omega++;
324 >                        ls->omega += 1.;
325                          addcolor(ls->val, ssamp[alt][azi].val);
326 +                                                        /* remove from list */
327                          setcolor(ssamp[alt][azi].val, 0., 0., 0.);
328 +                        ssamp[alt][azi].nsamp = 0;
329                  }
330                  d = 1./ls->omega;                       /* avg. brightness */
331                  scalecolor(ls->val, d);
# Line 337 | Line 340 | ssph_compute()                 /* compute source set from sphere sam
340          d = 1.0/ncells;
341          scalecolor(dlightsets->lamb, d);
342   done:                                   /* clear sphere sample array */
343 <        bzero((char *)ssamp, sizeof(ssamp));
343 >        memset((void *)ssamp, '\0', sizeof(ssamp));
344          return(ncells);
345   }
346  
# Line 370 | Line 373 | int    force;
373          if (!force)
374                  return(0);
375                                          /* need to compute new light set */
376 <        copystruct(&cvw, &stdview);
376 >        cvw = stdview;
377          cvw.type = VT_PER;
378          VCOPY(cvw.vp, ocent);
379          cvw.vup[0] = 1.; cvw.vup[1] = cvw.vup[2] = 0.;
# Line 404 | Line 407 | int    force;
407                          quit(0);
408          if (!ssph_compute()) {          /* compute light sources from sphere */
409                  dlightsets = dl->next;
410 <                free((char *)dl);
410 >                free((void *)dl);
411                  return(0);
412          }
413          op->ol = dl;
# Line 414 | Line 417 | memerr:
417   }
418  
419  
420 < static int
420 > static
421   cmderror(cn, err)               /* report command error */
422   int     cn;
423   char    *err;
424   {
425          sprintf(errmsg, "%s: %s", rhdcmd[cn], err);
426          error(COMMAND, errmsg);
424        return(cn);
427   }
428  
429  
# Line 430 | Line 432 | dobj_command(cmd, args)                /* run object display command
432   char    *cmd;
433   register char   *args;
434   {
435 +        int     somechange = 0;
436          int     cn, na, doxfm;
437          register int    nn;
438          char    *alist[MAXAC+1], *nm;
# Line 457 | Line 460 | register char  *args;
460                          dobj_load(alist[0], alist[0]);
461                  else if (na == 2)
462                          dobj_load(alist[0], alist[1]);
463 <                else
464 <                        return(cmderror(cn, "need octree [name]"));
463 >                else {
464 >                        cmderror(cn, "need octree [name]");
465 >                        return(0);
466 >                }
467                  break;
468 <        case DO_UNLOAD:                         /* unload an object */
468 >        case DO_UNLOAD:                         /* clear an object */
469                  if (na > 1) goto toomany;
470                  if (na && alist[0][0] == '*')
471 <                        dobj_cleanup();
471 >                        somechange += dobj_cleanup();
472                  else
473 <                        dobj_unload(na ? alist[0] : curname);
473 >                        somechange += dobj_unload(na ? alist[0] : curname);
474                  break;
475          case DO_XFORM:                          /* transform object */
476          case DO_MOVE:
# Line 474 | Line 479 | register char  *args;
479                  } else {
480                          nm = curname; nn = 0;
481                  }
482 <                if (cn == DO_MOVE && nn >= na)
483 <                        return(cmderror(cn, "missing transform"));
484 <                dobj_xform(nm, cn==DO_MOVE, na-nn, alist+nn);
482 >                if (cn == DO_MOVE && nn >= na) {
483 >                        cmderror(cn, "missing transform");
484 >                        return(0);
485 >                }
486 >                somechange += dobj_xform(nm, cn==DO_MOVE, na-nn, alist+nn);
487                  break;
488          case DO_UNMOVE:                         /* undo last transform */
489 <                dobj_unmove();
489 >                somechange += dobj_unmove();
490                  break;
491          case DO_OBJECT:                         /* print object statistics */
492                  if (dobj_putstats(na ? alist[0] : curname, sstdout))
493 <                        if (na && alist[0][0] != '*' &&
494 <                                        strcmp(alist[0], curname))
493 >                        if (na && alist[0][0] != '*' && (curobj == NULL ||
494 >                                        strcmp(alist[0], curobj->name)))
495                                  savedxf(curobj = getdobj(alist[0]));
496                  break;
497          case DO_DUP:                            /* duplicate object */
# Line 493 | Line 500 | register char  *args;
500                                  break;
501                  switch (nn) {
502                  case 0:
503 <                        return(cmderror(cn, "need new object name"));
503 >                        cmderror(cn, "need new object name");
504 >                        return(0);
505                  case 1:
506                          nm = curname;
507                          break;
# Line 506 | Line 514 | register char  *args;
514                  if (!dobj_dup(nm, alist[nn-1]))
515                          break;
516                  if (na > nn)
517 <                        dobj_xform(curname, 1, na-nn, alist+nn);
517 >                        somechange += dobj_xform(curname, 1, na-nn, alist+nn);
518                  else
519                          curobj->drawcode = DO_HIDE;
520                  savedxf(curobj);
# Line 516 | Line 524 | register char  *args;
524          case DO_HIDE:
525                  if (na > 1) goto toomany;
526                  dobj_lighting(na ? alist[0] : curname, cn);
527 +                somechange++;
528                  break;
529          default:
530                  error(CONSISTENCY, "bad command id in dobj_command");
531          }
532 <        dev_view(&odev.v);                      /* redraw */
524 <        return(cn);
532 >        return(somechange);
533   toomany:
534          return(cmderror(cn, "too many arguments"));
535   }
# Line 530 | Line 538 | toomany:
538   dobj_load(oct, nam)             /* create/load an octree object */
539   char    *oct, *nam;
540   {
533        extern char     *getlibpath(), *getpath();
541          char    *fpp, fpath[128];
542          register DOBJECT        *op;
543                                          /* check arguments */
# Line 547 | Line 554 | char   *oct, *nam;
554                  return(0);
555          }
556          if (getdobj(nam) != NULL) {
557 <                error(COMMAND, "name already taken (unload first)");
557 >                error(COMMAND, "name already taken (clear first)");
558                  return(0);
559          }
560                                          /* get octree path */
561 <        if ((fpp = getpath(oct, getlibpath(), R_OK)) == NULL) {
561 >        if ((fpp = getpath(oct, getrlibpath(), R_OK)) == NULL) {
562                  sprintf(errmsg, "cannot find octree \"%s\"", oct);
563                  error(COMMAND, errmsg);
564                  return(0);
# Line 569 | Line 576 | char   *oct, *nam;
576          op->xfav[op->xfac=0] = NULL;
577                                          /* load octree into display list */
578          dolights = 0;
579 <        op->listid = rgl_octlist(fpath, op->center, &op->radius);
579 >        domats = 1;
580 >        op->listid = rgl_octlist(fpath, op->center, &op->radius, &op->nlists);
581                                          /* start rtrace */
582          rtargv[RTARGC-1] = fpath;
583          rtargv[RTARGC] = NULL;
584 <        open_process(op->rtp, rtargv);
584 >        open_process(&(op->rtp), rtargv);
585                                          /* insert into main list */
586          op->next = dobjects;
587          curobj = dobjects = op;
# Line 606 | Line 614 | dobj_cleanup()                         /* free all resources */
614          savedxf(curobj = NULL);
615          while ((lp = dlightsets) != NULL) {
616                  dlightsets = lp->next;
617 <                free((char *)lp);
617 >                free((void *)lp);
618          }
619          return(1);
620   }
621  
622  
623 < dobj_xform(nam, add, ac, av)            /* set/add transform for nam */
623 > dobj_xform(nam, rel, ac, av)            /* set/add transform for nam */
624   char    *nam;
625 < int     add, ac;
625 > int     rel, ac;
626   char    **av;
627   {
628          register DOBJECT        *op;
629 +        FVECT   cent;
630 +        double  rad;
631 +        char    scoord[16];
632 +        int     i;
633  
634          if ((op = getdobj(nam)) == NULL) {
635                  error(COMMAND, "no object");
636                  return(0);
637          }
638 <        if (add) add = op->xfac;
639 <        if (ac + add > MAXAC) {
638 >        if (rel)
639 >                rel = op->xfac + 8;
640 >        if (ac + rel > MAXAC) {
641                  error(COMMAND, "too many transform arguments");
642                  return(0);
643          }
644 <        savedxf(curobj = op);
645 <        if (!add)
644 >        savedxf(curobj = op);           /* remember current transform */
645 >        if (rel && ac == 4 && !strcmp(av[0], "-t"))
646 >                rel = -1;                       /* don't move for translate */
647 >        else {
648 >                getdcent(cent, op);             /* don't move if near orig. */
649 >                rad = getdrad(op);
650 >                if (DOT(cent,cent) < rad*rad)
651 >                        rel = -1;
652 >        }
653 >        if (!rel) {                             /* remove old transform */
654                  while (op->xfac)
655                          freestr(op->xfav[--op->xfac]);
656 +        } else if (rel > 0) {                   /* relative move */
657 +                op->xfav[op->xfac++] = savestr("-t");
658 +                for (i = 0; i < 3; i++) {
659 +                        sprintf(scoord, "%.4e", -cent[i]);
660 +                        op->xfav[op->xfac++] = savestr(scoord);
661 +                }
662 +        }
663          while (ac--)
664                  op->xfav[op->xfac++] = savestr(*av++);
665 +        if (rel > 0) {                          /* move back */
666 +                op->xfav[op->xfac++] = savestr("-t");
667 +                for (i = 0; i < 3; i++) {
668 +                        sprintf(scoord, "%.4e", cent[i]);
669 +                        op->xfav[op->xfac++] = savestr(scoord);
670 +                }
671 +        }
672          op->xfav[op->xfac] = NULL;
673          if (fullxf(&op->xfb, op->xfac, op->xfav) != op->xfac) {
674                  error(COMMAND, "bad transform arguments");
# Line 670 | Line 705 | FILE   *fp;
705                  return(0);
706          }
707          getdcent(ocent, op);
708 <        fprintf(fp, "%s: %s, center [%f %f %f], radius %f", op->name,
708 >        fprintf(fp, "%s: %s, center [%g %g %g], radius %g", op->name,
709                          op->drawcode==DO_HIDE ? "hidden" :
710                          op->drawcode==DO_LIGHT && op->ol!=NULL ? "lighted" :
711                          "shown",
# Line 698 | Line 733 | dobj_unmove()                          /* undo last transform change */
733                  return(0);
734          }
735                                          /* hold last transform */
736 <        bcopy((char *)lastxfav, (char *)txfav,
736 >        memcpy((void *)txfav, (void *)lastxfav,
737                          (txfac=lastxfac)*sizeof(char *));
738                                          /* save this transform */
739 <        bcopy((char *)curobj->xfav, (char *)lastxfav,
739 >        memcpy((void *)lastxfav, (void *)curobj->xfav,
740                          (lastxfac=curobj->xfac)*sizeof(char *));
741                                          /* copy back last transform */
742 <        bcopy((char *)txfav, (char *)curobj->xfav,
742 >        memcpy((void *)curobj->xfav, (void *)txfav,
743                          (curobj->xfac=txfac)*sizeof(char *));
744                                          /* set matrices */
745          fullxf(&curobj->xfb, curobj->xfac, curobj->xfav);
# Line 732 | Line 767 | char   *oldnm, *nam;
767                  return(0);
768          }
769          if (getdobj(nam) != NULL) {
770 <                error(COMMAND, "name already taken (unload first)");
770 >                error(COMMAND, "name already taken (clear first)");
771                  return(0);
772          }
773                                          /* allocate and copy struct */
774          opdup = (DOBJECT *)malloc(sizeof(DOBJECT));
775          if (opdup == NULL)
776                  error(SYSTEM, "out of memory in dobj_dup");
777 <        copystruct(opdup, op);
777 >        *opdup = *op;
778                                          /* rename */
779          strcpy(opdup->name, nam);
780                                          /* get our own copy of transform */
# Line 774 | Line 809 | int    cn;
809          } else if ((op = getdobj(nam)) == NULL) {
810                  error(COMMAND, "unknown object");
811                  return(0);
812 <        } else if ((op->drawcode = cn) == DO_LIGHT)
813 <                getdlights(op, 1);
814 <        else
812 >        } else if ((op->drawcode = cn) == DO_LIGHT) {
813 >                if (!getdlights(op, 1))
814 >                        error(COMMAND, "insufficient samples to light object");
815 >        } else
816                  op->ol = NULL;
817  
818          if (dobj_lightsamp != NULL) {           /* restore beam set */
# Line 826 | Line 862 | FVECT   rorg, rdir;
862                  VCOPY(darr, rorg); VCOPY(darr+3, rdir);
863          }
864                                  /* trace it */
865 <        if (process(op->rtp, darr, darr, sizeof(double),
865 >        if (process(&(op->rtp), (char *)darr, (char *)darr, sizeof(double),
866                          6*sizeof(double)) != sizeof(double))
867                  error(SYSTEM, "rtrace communication error");
868                                  /* return distance */
# Line 836 | Line 872 | FVECT   rorg, rdir;
872   }
873  
874  
875 + int
876   dobj_render()                   /* render our objects in OpenGL */
877   {
878 +        int     nrendered = 0;
879          GLboolean       normalizing;
880          GLfloat vec[4];
881          FVECT   v1;
# Line 848 | Line 886 | dobj_render()                  /* render our objects in OpenGL */
886                  if (op->drawcode != DO_HIDE)
887                          break;
888          if (op == NULL)
889 <                return(1);
889 >                return(0);
890                                          /* set up general rendering params */
891          glGetBooleanv(GL_NORMALIZE, &normalizing);
892 <        glPushAttrib(GL_LIGHTING_BIT|GL_TRANSFORM_BIT|
893 <                        GL_DEPTH_BUFFER_BIT|GL_POLYGON_BIT);
892 >        glPushAttrib(GL_LIGHTING_BIT|GL_TRANSFORM_BIT|GL_ENABLE_BIT|
893 >                GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_POLYGON_BIT);
894          glDepthFunc(GL_LESS);
895          glEnable(GL_DEPTH_TEST);
896          glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE);
# Line 934 | Line 972 | dobj_render()                  /* render our objects in OpenGL */
972                  }
973                                          /* render the display list */
974                  glCallList(op->listid);
975 +                nrendered++;
976                                          /* restore matrix */
977                  if (op->xfac) {
978                          glMatrixMode(GL_MODELVIEW);
# Line 951 | Line 990 | dobj_render()                  /* render our objects in OpenGL */
990          }
991          glPopAttrib();                  /* restore rendering params */
992          rgl_checkerr("rendering objects in dobj_render");
993 <        return(1);
993 >        return(nrendered);
994   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines