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

Comparing ray/src/util/glrad.c (file contents):
Revision 3.2 by gwlarson, Tue Jun 9 12:46:45 1998 UTC vs.
Revision 3.17 by schorsch, Mon Jul 21 22:30:19 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   * Program to display Radiance scene using OpenGL.
6   */
7  
11 #include "radogl.h"
12 #include "view.h"
13 #include "paths.h"
8   #include <sys/types.h>
9   #include <GL/glx.h>
10 + #ifndef NOSTEREO
11 + #include <X11/extensions/SGIStereo.h>
12 + #endif
13   #include <ctype.h>
14 + #include <string.h>
15 + #include <time.h>
16 +
17 + #include "radogl.h"
18 + #include "view.h"
19 + #include "paths.h"
20   #include "glradicon.h"
21 + #include "rtprocess.h"
22  
23   #ifndef MAXVIEW
24   #define MAXVIEW         63              /* maximum number of standard views */
# Line 30 | Line 34 | static char SCCSid[] = "$SunId$ SGI";
34   #define MOVDEG          (-5)            /* degrees to orbit CW/down /frame */
35   #define MOVORB(s)       ((s)&ShiftMask ? 1 : (s)&ControlMask ? -1 : 0)
36  
33 #define MINWIDTH        480             /* minimum graphics window width */
34 #define MINHEIGHT       400             /* minimum graphics window height */
35
37   #define BORWIDTH        5               /* border width */
38  
39   #define  ourscreen      DefaultScreen(ourdisplay)
# Line 65 | Line 66 | struct {
66  
67   int     currentview = 0;                /* current view number */
68   VIEW    thisview = STDVIEW;             /* displayed view */
69 + double  eyedist = 1;                    /* interocular distance */
70   VIEW    lastview;                       /* last recorded view */
71  
72   char    *progname;                      /* global argv[0] */
# Line 73 | Line 75 | char   *scene[MAXSCENE+1];             /* material and scene file l
75   int     nscenef = 0;                    /* number of scene files */
76   char    *octree;                        /* octree name (NULL if unnec.) */
77  
78 < int     rtpd[3];                        /* rtrace process descriptors */
78 > SUBPROC rtpd;                   /* rtrace process descriptors */
79  
80 + int     silent = 0;                     /* run rad silently? */
81   int     backvis = 1;                    /* back faces visible? */
82 + int     stereo = 0;                     /* do stereo? */
83  
84 + #ifdef NOSTEREO
85 + #define setstereobuf(bid)       0
86 + #else
87 + #define setstereobuf(bid)       (glXWaitGL(), \
88 +                                XSGISetStereoBuffer(ourdisplay, gwind, bid), \
89 +                                glXWaitX())
90 + #endif
91 +
92   int     displist;                       /* our scene display list */
93  
94 < int     in_dev_view = 0;                /* currently in dev_view() */
94 > int     no_render = 0;                  /* don't rerender */
95  
96 < extern char     *fgets(), *fgetline(), *atos(), *scan4var();
96 > extern char     *fgetline(), *atos(), *scan4var();
97   extern int      nowarn;                 /* turn warnings off? */
86 extern time_t   time();
98  
99  
100   main(argc, argv)
# Line 103 | Line 114 | char   *argv[];
114                  case 'w':
115                          nowarn = !nowarn;
116                          break;
117 +                case 's':
118 +                        silent = !silent;
119 +                        break;
120 +                case 'S':
121 +                        stereo = !stereo;
122 +                        break;
123                  case 'c':
124                          vwintvl = atoi(argv[++i]);
125                          break;
# Line 114 | Line 131 | char   *argv[];
131                  }
132          if (i >= argc)
133                  goto userr;
134 + #ifdef NOSTEREO
135 +        if (stereo)
136 +                error(INTERNAL, "stereo not supported in this version");
137 + #endif
138                                          /* run rad and get views */
139          runrad(argc-i, argv+i);
140                                          /* check view */
141 <        if (viewsel != NULL && (currentview = findvw(viewsel)) < 0) {
142 <                fprintf(stderr, "%s: no such view\n", viewsel);
143 <                quit(1);
141 >        if (viewsel != NULL) {
142 >                if (viewsel[0] == '-') {
143 >                        char    *ve = viewsel;
144 >                        if (!sscanview(&thisview, viewsel) ||
145 >                                        (ve = setview(&thisview)) != NULL) {
146 >                                fprintf(stderr, "%s: bad view: %s\n",
147 >                                                progname, ve);
148 >                                quit(1);
149 >                        }
150 >                        currentview = -1;
151 >                } else if ((currentview = findvw(viewsel)) < 0) {
152 >                        fprintf(stderr, "%s: no such view: %s\n",
153 >                                                progname, viewsel);
154 >                        quit(1);
155 >                }
156          }
157                                          /* open GL */
158          dev_open(radfile = argv[i]);
159                                          /* load octree or scene files */
160          if (octree != NULL) {
161 <                displist = rgl_octlist(octree, NULL, NULL);
161 >                displist = rgl_octlist(octree, NULL, NULL, NULL);
162                  startrtrace(octree);
163          } else
164 <                displist = rgl_filelist(nscenef, scene);
164 >                displist = rgl_filelist(nscenef, scene, NULL);
165                                          /* set initial view */
166 <        dev_view(vwl[currentview].v);
166 >        dev_view(currentview < 0 ? &thisview : vwl[currentview].v);
167                                          /* input/render loop */
168          while (dev_input(vwintvl))
169                  ;
170                                          /* all done */
171          quit(0);
172   userr:
173 <        fprintf(stderr, "Usage: %s [-w][-c #secs][-v view] rfile [VAR=value]..\n",
173 >        fprintf(stderr,
174 >                "Usage: %s [-w][-s][-b][-S][-v view] rfile [VAR=value]..\n",
175                          argv[0]);
176          quit(1);
177   }
178  
179  
180 + void
181   quit(code)                              /* exit gracefully */
182   int     code;
183   {
184          if (ourdisplay != NULL)
185                  dev_close();
186 <        if (rtpd[2] > 0) {
187 <                if (close_process(rtpd) > 0)
186 >        /* if (rtpd.pid > 0) { */
187 >        if (rtpd.running) {
188 >                if (close_process(&rtpd) > 0)
189                          wputs("bad exit status from rtrace\n");
190 <                rtpd[2] = 0;
190 >                /* rtpd.pid = 0; */
191          }
192          exit(code);
193   }
# Line 167 | Line 203 | char   *octname;
203          if (nowarn) av[ac++] = "-w-";
204          av[ac++] = octname;
205          av[ac] = NULL;
206 <        if (open_process(rtpd, av) <= 0)
206 >        if (open_process(&rtpd, av) <= 0)
207                  error(SYSTEM, "cannot start rtrace process");
208   }
209  
# Line 185 | Line 221 | char   **av;
221                                          /* set rad commmand */
222          strcpy(radcomm, "rad -w -v 0        "); /* look out below! */
223          cp = radcomm + 19;
224 +        if (silent) {
225 +                strcpy(cp, "-s ");
226 +                cp += 3;
227 +        }
228          while (ac--) {
229                  strcpy(cp, *av++);
230                  while (*cp) cp++;
# Line 205 | Line 245 | char   **av;
245                  expval = atof(cp);
246                  if (*cp == '-' | *cp == '+')
247                          expval = pow(2., expval);
248 +                expval *= 0.5;          /* compensate for local shading */
249          }
250 +                                                /* look for eye separation */
251 +        if ((cp = scan4var(buf, sizeof(buf), "EYESEP", fp)) != NULL)
252 +                eyedist = atof(cp);
253                                                  /* look for materials */
254          while ((cp = scan4var(buf, sizeof(buf), "materials", fp)) != NULL) {
255                  nscenef += wordstring(scene+nscenef, cp);
# Line 231 | Line 275 | char   **av;
275          do
276                  if (isview(buf)) {
277                          vwl[nvv].v = (VIEW *)bmalloc(sizeof(VIEW));
278 <                        copystruct(vwl[nvv].v, &stdview);
278 >                        *(vwl[nvv].v) = stdview;
279                          sscanview(vwl[nvv].v, buf);
280                          if ((cp = setview(vwl[nvv++].v)) != NULL) {
281                                  fprintf(stderr, "%s: bad view %d - %s\n",
# Line 246 | Line 290 | char   **av;
290                                                  /* open options file */
291          if ((fp = fopen(optfile, "r")) == NULL)
292                  error(SYSTEM, "cannot open options file");
293 <                                                /* get ambient value */
293 >                                                /* get relevant options */
294          while (fgets(buf, sizeof(buf), fp) != NULL)
295 <                if (!strncmp(buf, "-av ", 4)) {
295 >                if (!strncmp(buf, "-av ", 4))
296                          setcolor(ambval, atof(buf+4),
297                                          atof(sskip2(buf+4,1)),
298                                          atof(sskip2(buf+4,2)));
299 <                        break;
300 <                }
299 >                else if (backvis && !strncmp(buf, "-bv", 3) &&
300 >                                (!buf[3] || strchr("0-FfNn \n",buf[3])!=NULL))
301 >                        backvis = 0;
302          fclose(fp);
303          unlink(optfile);                        /* delete options file */
304   }
# Line 326 | Line 371 | char  *id;
371                                  GLX_DOUBLEBUFFER, GLX_DEPTH_SIZE,15, None};
372          XSetWindowAttributes    ourwinattr;
373          XWMHints        ourxwmhints;
329        XSizeHints      oursizhints;
374                                          /* open display server */
375          ourdisplay = XOpenDisplay(NULL);
376          if (ourdisplay == NULL)
# Line 352 | Line 396 | char  *id;
396          if (gwind == 0)
397                  error(SYSTEM, "cannot create window\n");
398          XStoreName(ourdisplay, gwind, id);
399 + #ifndef NOSTEREO
400 +        if (stereo)                     /* check if stereo working */
401 +                switch (XSGIQueryStereoMode(ourdisplay, gwind)) {
402 +                case STEREO_TOP:
403 +                case STEREO_BOTTOM:
404 +                        break;
405 +                case STEREO_OFF:
406 +                        error(USER,
407 +                "wrong video mode: run \"/usr/gfx/setmon -n STR_TOP\" first");
408 +                case X_STEREO_UNSUPPORTED:
409 +                        error(USER, "stereo not supported on this screen");
410 +                default:
411 +                        error(INTERNAL, "unknown stereo mode");
412 +                }
413 + #endif
414                                          /* set window manager hints */
415          ourxwmhints.flags = InputHint|IconPixmapHint;
416          ourxwmhints.input = True;
417          ourxwmhints.icon_pixmap = XCreateBitmapFromData(ourdisplay,
418                  gwind, glradicon_bits, glradicon_width, glradicon_height);
419          XSetWMHints(ourdisplay, gwind, &ourxwmhints);
361        oursizhints.min_width = MINWIDTH;
362        oursizhints.min_height = MINHEIGHT;
363        oursizhints.flags = PMinSize;
364        XSetNormalHints(ourdisplay, gwind, &oursizhints);
420                                          /* set GLX context */
421          glXMakeCurrent(ourdisplay, gwind, gctx);
422          glEnable(GL_DEPTH_TEST);
423          glDepthFunc(GL_LESS);
424          glShadeModel(GL_SMOOTH);
425          glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
426 <        glLightModelf(GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE);
426 >        glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE);
427          glEnable(GL_LIGHTING);
428 +        glFrontFace(GL_CCW);
429 +        glCullFace(GL_BACK);
430          if (backvis)
431                  glDisable(GL_CULL_FACE);
432 <        else {
376 <                glFrontFace(GL_CCW);
377 <                glCullFace(GL_BACK);
432 >        else
433                  glEnable(GL_CULL_FACE);
379        }
434          glDrawBuffer(GL_BACK);
435                                          /* figure out sensible view */
436          pwidth = (double)DisplayWidthMM(ourdisplay, ourscreen) /
437                          DisplayWidth(ourdisplay, ourscreen);
438          pheight = (double)DisplayHeightMM(ourdisplay, ourscreen) /
439                          DisplayHeight(ourdisplay, ourscreen);
440 +        if (stereo) {                   /* set stereo mode */
441 +                setstereobuf(STEREO_BUFFER_LEFT);
442 +                pheight *= 2.;
443 +        }
444                                          /* map the window */
445          XMapWindow(ourdisplay, gwind);
446 +        no_render++;
447 +        do
448 +                dev_input(0);           /* get resize event */
449 +        while (hres == 0 & vres == 0);
450 +        no_render--;
451          rgl_checkerr("initializing GLX");
452   }
453  
# Line 435 | Line 498 | register VIEW  *nv;
498                          }
499                  }
500                  if (newhres != hres | newvres != vres) {
501 <                        in_dev_view++;
501 >                        no_render++;
502                          XResizeWindow(ourdisplay, gwind, newhres, newvres);
503                          do
504                                  dev_input(0);           /* get resize event */
505                          while (newhres != hres | newvres != vres);
506 <                        in_dev_view--;
506 >                        no_render--;
507                  }
508          }
509 <        copystruct(&thisview, nv);
509 >        thisview = *nv;
510          setglpersp(&thisview);
511          render();
512          return(1);
# Line 492 | Line 555 | int    nsecs;
555  
556   render()                        /* render our display list and swap buffers */
557   {
558 <        if (!mapped)
558 >        double  d;
559 >
560 >        if (!mapped | no_render)
561                  return;
562          glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
563          glCallList(displist);
564 +        if (stereo) {                           /* do right eye for stereo */
565 +                setstereobuf(STEREO_BUFFER_RIGHT);
566 +                glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
567 +                glMatrixMode(GL_MODELVIEW);
568 +                glPushMatrix();
569 +                d = -eyedist / sqrt(thisview.hn2);
570 +                glTranslated(d*thisview.hvec[0], d*thisview.hvec[1],
571 +                                d*thisview.hvec[2]);
572 +                glCallList(displist);
573 +                glMatrixMode(GL_MODELVIEW);
574 +                glPopMatrix();
575 +                setstereobuf(STEREO_BUFFER_LEFT);
576 +        }
577          glXSwapBuffers(ourdisplay, gwind);      /* calls glFlush() */
578          rgl_checkerr("rendering display list");
579   }
# Line 507 | Line 585 | int    dx, dy, mov, orb;
585          VIEW    nv;
586          FVECT   odir, v1, wp;
587          double  d;
510        register int    li;
588                                  /* start with old view */
589 <        copystruct(&nv, &thisview);
589 >        nv = thisview;
590                                  /* change view direction */
591          if ((d = viewray(v1, odir, &thisview,
592                          (dx+.5)/hres, (dy+.5)/vres)) < -FTINY)
# Line 547 | Line 624 | int    dx, dy, mov, orb;
624   }
625  
626  
627 + static
628 + waitabit()                              /* pause a moment */
629 + {
630 +        struct timespec ts;
631 +        ts.tv_sec = 0;
632 +        ts.tv_nsec = 5000000;
633 +        nanosleep(&ts, NULL);
634 + }
635 +
636 +
637   getmove(ebut)                           /* get view change */
638   XButtonPressedEvent     *ebut;
639   {
# Line 557 | Line 644 | XButtonPressedEvent    *ebut;
644          int     rootx, rooty, wx, wy;
645          unsigned int    statemask;
646  
647 <        copylastv("moving");
647 >        copylastv( movorb ? (movdir ? "left/right" : "up/down") :
648 >                        (movdir ? "fore/back" : "rotate") );
649          XNoOp(ourdisplay);
650  
651          while (!XCheckMaskEvent(ourdisplay,
652                          ButtonReleaseMask, levptr(XEvent))) {
653 +                                        /* pause so as not to move too fast */
654 +                waitabit();
655  
656                  if (!XQueryPointer(ourdisplay, gwind, &rootw, &childw,
657                                  &rootx, &rooty, &wx, &wy, &statemask))
# Line 589 | Line 679 | double md;
679   {
680          float   fbuf[6];
681                                  /* check to see if rtrace is running */
682 <        if (rtpd[2] <= 0)
682 >        /* if (rtpd.pid <= 0) */
683 >        if (!rtpd.running)
684                  return(0);
685                                  /* assign origin */
686          fbuf[0] = org[0]; fbuf[1] = org[1]; fbuf[2] = org[2];
# Line 597 | Line 688 | double md;
688          if (md <= FTINY) md = FHUGE;
689          fbuf[3] = dir[0]*md; fbuf[4] = dir[1]*md; fbuf[5] = dir[2]*md;
690                                  /* trace that ray */
691 <        if (process(rtpd, fbuf, fbuf, 4*sizeof(float), 6*sizeof(float)) !=
692 <                        4*sizeof(float))
691 >        if (process(&rtpd, (char *)fbuf, (char *)fbuf,
692 >                        4*sizeof(float), 6*sizeof(float)) != 4*sizeof(float))
693                  error(INTERNAL, "error getting data back from rtrace process");
694          if (fbuf[3] >= .99*FHUGE)
695                  return(0);      /* missed local objects */
# Line 659 | Line 750 | register XKeyPressedEvent  *ekey;
750          case 'l':                       /* retrieve last (premouse) view */
751                  if (lastview.type) {
752                          VIEW    vtmp;
753 <                        copystruct(&vtmp, &thisview);
753 >                        vtmp = thisview;
754                          dev_view(&lastview);
755 <                        copystruct(&lastview, &vtmp);
755 >                        lastview = vtmp;
756                  } else
757                          XBell(ourdisplay, 0);
758                  break;
# Line 729 | Line 820 | int    vwnum;
820                          ;
821          else if (vwnum >= MAXVIEW || vwl[vwnum].v == NULL)
822                  vwnum = 0;
823 <        if (vwnum == currentview)
733 <                return;
734 <        /* copylastv("change view"); */
823 >        copylastv("standard view");
824          dev_view(vwl[currentview=vwnum].v);
825   }
826  
# Line 742 | Line 831 | VIEW   *vp;
831   {
832          FILE    *fp;
833                                          /* check if already in there */
834 <        if (!bcmp(&thisview, vwl[currentview].v, sizeof(VIEW))) {
834 >        if (!memcmp(&thisview, vwl[currentview].v, sizeof(VIEW))) {
835                  error(COMMAND, "view already in standard list");
836                  return;
837          }
# Line 763 | Line 852 | VIEW   *vp;
852          if (currentview >= MAXVIEW)
853                  error(INTERNAL, "too many views in appendview");
854          vwl[currentview].v = (VIEW *)bmalloc(sizeof(VIEW));
855 <        copystruct(vwl[currentview].v, &thisview);
855 >        *(vwl[currentview].v) = thisview;
856          if (nm != NULL)
857                  vwl[currentview].nam = savqstr(nm);
858   }
# Line 777 | Line 866 | char   *cause;
866          if (cause == lastvc)
867                  return;                 /* only record one view per cause */
868          lastvc = cause;
869 <        copystruct(&lastview, &thisview);
869 >        lastview = thisview;
870   }
871  
872  
# Line 804 | Line 893 | register XConfigureEvent  *ersz;
893          glViewport(0, 0, hres=ersz->width, vres=ersz->height);
894          if (hres > maxhres) maxhres = hres;
895          if (vres > maxvres) maxvres = vres;
896 <        if (in_dev_view)
896 >        if (no_render)
897                  return;
898          wa = (vres*pheight)/(hres*pwidth);
899          va = viewaspect(&thisview);

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines