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

Comparing ray/src/hd/rhd_x11.c (file contents):
Revision 3.9 by gregl, Tue Nov 25 16:52:51 1997 UTC vs.
Revision 3.19 by gregl, Wed Dec 24 16:56:00 1997 UTC

# Line 18 | Line 18 | static char SCCSid[] = "$SunId$ SGI";
18  
19   #include  "x11icon.h"
20  
21 < #define CTRL(c)         ((c)-'@')
21 > #ifndef FEQ
22 > #define FEQ(a,b)        ((a)-(b) <= FTINY && (a)-(b) >= -FTINY)
23 > #endif
24  
25   #define GAMMA           2.2             /* default gamma correction */
26  
27 < #define MOVPCT          10              /* percent distance to move */
27 > #define MOVPCT          7               /* percent distance to move /frame */
28   #define MOVDIR(b)       ((b)==Button1 ? 1 : (b)==Button2 ? 0 : -1)
29 + #define MOVDEG          (-5)            /* degrees to orbit CW/down /frame */
30 + #define MOVORB(s)       ((s)&ShiftMask ? 1 : (s)&ControlMask ? -1 : 0)
31  
32   #define MINWIDTH        480             /* minimum graphics window width */
33   #define MINHEIGHT       400             /* minimum graphics window height */
# Line 95 | Line 99 | char  *id;
99          XWMHints  ourxwmhints;
100          XSizeHints      oursizhints;
101                                          /* set quadtree globals */
98        qtDepthEps = 0.02;
102          qtMinNodesiz = 2;
103                                          /* open display server */
104          ourdisplay = XOpenDisplay(NULL);
# Line 155 | Line 158 | char  *id;
158          oursizhints.min_height = MINHEIGHT;
159          oursizhints.flags = PMinSize;
160          XSetNormalHints(ourdisplay, gwind, &oursizhints);
161 +                                        /* figure out sensible view */
162 +        pwidth = (double)DisplayWidthMM(ourdisplay, ourscreen) /
163 +                        DisplayWidth(ourdisplay, ourscreen);
164 +        pheight = (double)DisplayHeightMM(ourdisplay, ourscreen) /
165 +                        DisplayHeight(ourdisplay, ourscreen);
166 +        copystruct(&odev.v, &stdview);
167 +        odev.v.type = VT_PER;
168                                          /* map the window and get its size */
169          XMapWindow(ourdisplay, gwind);
170 <        dev_input();
170 >        dev_input();                    /* sets size and view angles */
171                                          /* allocate our leaf pile */
172          if (!qtAllocLeaves(DisplayWidth(ourdisplay,ourscreen) *
173                          DisplayHeight(ourdisplay,ourscreen) /
174                          (qtMinNodesiz*qtMinNodesiz)))
175                  error(SYSTEM, "insufficient memory for leaf storage");
166
167                                        /* figure out sensible view */
168        pwidth = (double)DisplayWidthMM(ourdisplay, ourscreen) /
169                        DisplayWidth(ourdisplay, ourscreen);
170        pheight = (double)DisplayHeightMM(ourdisplay, ourscreen) /
171                        DisplayHeight(ourdisplay, ourscreen);
172        copystruct(&odev.v, &stdview);
176          odev.name = id;
174        odev.v.type = VT_PER;
175        odev.v.horiz = 2.*180./PI * atan(0.5/VIEWDIST*pwidth*odev.hres);
176        odev.v.vert = 2.*180./PI * atan(0.5/VIEWDIST*pheight*odev.vres);
177          odev.ifd = ConnectionNumber(ourdisplay);
178   }
179  
# Line 195 | Line 195 | dev_close()                    /* close our display */
195   }
196  
197  
198 + int
199   dev_view(nv)                    /* assign new driver view */
200   VIEW    *nv;
201   {
202 <        if (nv != &odev.v)
202 >        if (nv->type == VT_PAR ||               /* check view legality */
203 >                        nv->horiz > 160. || nv->vert > 160.) {
204 >                error(COMMAND, "illegal view type/angle");
205 >                nv->type = VT_PER;
206 >                nv->horiz = odev.v.horiz;
207 >                nv->vert = odev.v.vert;
208 >                return(0);
209 >        }
210 >        if (nv->vfore > FTINY) {
211 >                error(COMMAND, "cannot handle fore clipping");
212 >                nv->vfore = 0.;
213 >                return(0);
214 >        }
215 >        if (nv != &odev.v) {
216 >                if (!FEQ(nv->horiz,odev.v.horiz) ||     /* resize window? */
217 >                                !FEQ(nv->vert,odev.v.vert)) {
218 >                        int     dw = DisplayWidth(ourdisplay,ourscreen);
219 >                        int     dh = DisplayHeight(ourdisplay,ourscreen);
220 >
221 >                        dw -= 25;       /* for window frame */
222 >                        dh -= 50;
223 >                        odev.hres = 2.*VIEWDIST/pwidth *
224 >                                        tan(PI/180./2.*nv->horiz);
225 >                        odev.vres = 2.*VIEWDIST/pheight *
226 >                                        tan(PI/180./2.*nv->vert);
227 >                        if (odev.hres > dw) {
228 >                                odev.vres = dw * odev.vres / odev.hres;
229 >                                odev.hres = dw;
230 >                        }
231 >                        if (odev.vres > dh) {
232 >                                odev.hres = dh * odev.hres / odev.vres;
233 >                                odev.vres = dh;
234 >                        }
235 >                        XResizeWindow(ourdisplay, gwind, odev.hres, odev.vres);
236 >                        dev_input();    /* wait for resize event */
237 >                }
238                  copystruct(&odev.v, nv);
239 +        }
240          qtReplant();
241 +        return(1);
242   }
243  
244  
# Line 415 | Line 453 | draw_grids()                   /* draw holodeck section grids */
453          static BYTE     gridrgb[3] = {0x0, 0xff, 0xff};
454          unsigned long  pixel;
455  
456 <        if (!mapped || odev.v.type != VT_PER)
456 >        if (!mapped)
457                  return;
458          if (ncolors > 0)
459                  pixel = pixval[get_pixel(gridrgb, xnewcolr)];
# Line 428 | Line 466 | draw_grids()                   /* draw holodeck section grids */
466  
467  
468   static
469 < moveview(dx, dy, move)          /* move our view */
470 < int     dx, dy, move;
469 > moveview(dx, dy, mov, orb)      /* move our view */
470 > int     dx, dy, mov, orb;
471   {
472          VIEW    nv;
473 +        FVECT   odir, v1;
474          double  d;
475 <        register int    i, li;
475 >        register int    li;
476                                  /* start with old view */
477          copystruct(&nv, &odev.v);
478                                  /* change view direction */
479 <        if (move) {
479 >        if (mov | orb) {
480                  if ((li = qtFindLeaf(dx, dy)) < 0)
481                          return(0);      /* not on window */
482 <                for (i = 0; i < 3; i++)
444 <                        nv.vdir[i] = qtL.wp[li][i] - nv.vp[i];
482 >                VSUM(odir, qtL.wp[li], nv.vp, -1.);
483          } else {
484                  if (viewray(nv.vp, nv.vdir, &odev.v,
485                                  (dx+.5)/odev.hres, (dy+.5)/odev.vres) < -FTINY)
486                          return(0);      /* outside view */
487          }
488 <                                /* move viewpoint */
489 <        if (move > 0)
490 <                for (i = 0; i < 3; i++)
491 <                        nv.vp[i] += MOVPCT/100. * nv.vdir[i];
492 <        else if (move < 0)
493 <                for (i = 0; i < 3; i++)
494 <                        nv.vp[i] -= MOVPCT/100. * nv.vdir[i];
495 <        if (move && headlocked) {
496 <                d = 0;          /* bring head back to same height */
497 <                for (i = 0; i < 3; i++)
498 <                        d += odev.v.vup[i] * (odev.v.vp[i] - nv.vp[i]);
499 <                for (i = 0; i < 3; i++)
500 <                        nv.vp[i] += d * odev.v.vup[i];
488 >        if (orb && mov) {               /* orbit left/right */
489 >                spinvector(odir, odir, nv.vup, d=MOVDEG*PI/180.*mov);
490 >                VSUM(nv.vp, qtL.wp[li], odir, -1.);
491 >                spinvector(nv.vdir, nv.vdir, nv.vup, d);
492 >        } else if (orb) {               /* orbit up/down */
493 >                fcross(v1, odir, nv.vup);
494 >                if (normalize(v1) == 0.)
495 >                        return(0);
496 >                spinvector(odir, odir, v1, d=MOVDEG*PI/180.*orb);
497 >                VSUM(nv.vp, qtL.wp[li], odir, -1.);
498 >                spinvector(nv.vdir, nv.vdir, v1, d);
499 >        } else if (mov) {               /* move forward/backward */
500 >                d = MOVPCT/100. * mov;
501 >                VSUM(nv.vp, nv.vp, odir, d);
502          }
503 +        if (!mov ^ !orb && headlocked) {        /* restore head height */
504 +                VSUM(v1, odev.v.vp, nv.vp, -1.);
505 +                d = DOT(v1, odev.v.vup);
506 +                VSUM(nv.vp, nv.vp, odev.v.vup, d);
507 +        }
508          if (setview(&nv) != NULL)
509                  return(0);      /* illegal view */
510          dev_view(&nv);
511 <        inpresflags |= DEV_NEWVIEW;
511 >        inpresflags |= DFL(DC_SETVIEW);
512          return(1);
513   }
514  
# Line 473 | Line 517 | static
517   getmove(ebut)                           /* get view change */
518   XButtonPressedEvent     *ebut;
519   {
520 <        int     whichbutton = ebut->button;
520 >        int     movdir = MOVDIR(ebut->button);
521 >        int     movorb = MOVORB(ebut->state);
522          int     oldnodesiz = qtMinNodesiz;
523          Window  rootw, childw;
524          int     rootx, rooty, wx, wy;
# Line 489 | Line 534 | XButtonPressedEvent    *ebut;
534                                  &rootx, &rooty, &wx, &wy, &statemask))
535                          break;          /* on another screen */
536  
537 <                if (!moveview(wx, odev.vres-1-wy, MOVDIR(whichbutton))) {
537 >                if (!moveview(wx, odev.vres-1-wy, movdir, movorb)) {
538                          sleep(1);
539                          continue;
540                  }
# Line 497 | Line 542 | XButtonPressedEvent    *ebut;
542                  qtUpdate();
543                  draw_grids();
544          }
545 <        if (!(inpresflags & DEV_NEWVIEW)) {     /* do final motion */
546 <                whichbutton = levptr(XButtonReleasedEvent)->button;
545 >        if (!(inpresflags & DFL(DC_SETVIEW))) { /* do final motion */
546 >                movdir = MOVDIR(levptr(XButtonReleasedEvent)->button);
547                  wx = levptr(XButtonReleasedEvent)->x;
548                  wy = levptr(XButtonReleasedEvent)->y;
549 <                moveview(wx, odev.vres-1-wy, MOVDIR(whichbutton));
549 >                moveview(wx, odev.vres-1-wy, movdir, movorb);
550          }
551          dev_flush();
552  
# Line 526 | Line 571 | register XKeyPressedEvent  *ekey;
571          case 'H':                       /* turn off height motion lock */
572                  headlocked = 0;
573                  return;
574 <        case CTRL('S'):
574 >        case 'l':                       /* retrieve last view */
575 >                inpresflags |= DFL(DC_LASTVIEW);
576 >                return;
577          case 'p':                       /* pause computation */
578 <                inpresflags |= DEV_WAIT;
578 >                inpresflags |= DFL(DC_PAUSE);
579                  return;
580          case 'v':                       /* spit out view */
581 <                fputs(VIEWSTR, stderr);
535 <                fprintview(&odev.v, stderr);
536 <                fputc('\n', stderr);
581 >                inpresflags |= DFL(DC_GETVIEW);
582                  return;
538        case CTRL('Q'):
583          case '\n':
584          case '\r':                      /* resume computation */
585 <                inpresflags |= DEV_RESUME;
585 >                inpresflags |= DFL(DC_RESUME);
586                  return;
587          case CTRL('R'):                 /* redraw screen */
588                  if (ncolors > 0)
# Line 546 | Line 590 | register XKeyPressedEvent  *ekey;
590                  qtRedraw(0, 0, odev.hres, odev.vres);
591                  return;
592          case CTRL('L'):                 /* refresh from server */
593 <                if (inpresflags & DEV_REDRAW)
593 >                if (inpresflags & DFL(DC_REDRAW))
594                          return;
595                  XClearWindow(ourdisplay, gwind);
596                  draw_grids();
# Line 554 | Line 598 | register XKeyPressedEvent  *ekey;
598                  qtCompost(100);                 /* unload the old tree */
599                  if (ncolors > 0)
600                          new_ctab(ncolors);
601 <                inpresflags |= DEV_REDRAW;      /* resend values from server */
601 >                inpresflags |= DFL(DC_REDRAW);  /* resend values from server */
602                  return;
603 <        case CTRL('D'):
604 <        case 'Q':
603 >        case 'K':                       /* kill rtrace process(es) */
604 >                inpresflags |= DFL(DC_KILL);
605 >                break;
606 >        case 'R':                       /* restart rtrace */
607 >                inpresflags |= DFL(DC_RESTART);
608 >                break;
609 >        case 'C':                       /* clobber holodeck */
610 >                inpresflags |= DFL(DC_CLOBBER);
611 >                break;
612          case 'q':                       /* quit the program */
613 <                inpresflags |= DEV_SHUTDOWN;
613 >                inpresflags |= DFL(DC_QUIT);
614                  return;
615          default:
616                  XBell(ourdisplay, 0);
# Line 575 | Line 626 | register XExposeEvent  *eexp;
626          if (odev.hres == 0 || odev.vres == 0) { /* first exposure */
627                  odev.hres = eexp->width;
628                  odev.vres = eexp->height;
578                inpresflags |= DEV_NEWSIZE;
629          }
630          qtRedraw(eexp->x, odev.vres - eexp->y - eexp->height,
631                          eexp->x + eexp->width, odev.vres - eexp->y);
# Line 589 | Line 639 | register XConfigureEvent  *ersz;
639          if (ersz->width == odev.hres && ersz->height == odev.vres)
640                  return;
641  
592        if (odev.hres != 0 && odev.vres != 0) {
593                odev.v.horiz = 2.*180./PI * atan(
594                        tan(PI/180./2.*odev.v.horiz) * ersz->width/odev.hres );
595                odev.v.vert = 2.*180./PI * atan(
596                        tan(PI/180./2.*odev.v.vert) * ersz->height/odev.vres );
597                inpresflags |= DEV_NEWVIEW;
598        }
642          odev.hres = ersz->width;
643          odev.vres = ersz->height;
644  
645 <        inpresflags |= DEV_NEWSIZE;
645 >        odev.v.horiz = 2.*180./PI * atan(0.5/VIEWDIST*pwidth*odev.hres);
646 >        odev.v.vert = 2.*180./PI * atan(0.5/VIEWDIST*pheight*odev.vres);
647 >
648 >        inpresflags |= DFL(DC_SETVIEW);
649   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines