void GraphicCamera::MouseMotionEventHandler(int x, int y) {
  int mouse_dx, mouse_dy, d;
  double z;
  Vec3d mouse_pos, dir;
  Vec3d WndX, WndY, WndZ;
  float realy;
  double wx, wy, wz;

  if (CameraMode != kINACTIVE) {
    mouse_dx = x - MousePrevX;
    mouse_dy = y - MousePrevY;

    if (abs(mouse_dx) > abs(mouse_dy)) {
      d = mouse_dx;
    } else {
      d = mouse_dy;
    }

    switch(CameraMode) {

      case kZOOM:
        z = (double) d / 100.0;
        dir = aim_ - pos_;
        if (dir.Norm() < 0.1 && z > 0) {
          z *= 10.0;
          aim_ = aim_ + z * dir;
        }
        pos_ = pos_ + z * dir;
        break;
      case kROTATE:
        dt_azim = ((double) (x - MouseStartX)) / 5.0;
        dt_elev = ((double) (y - MouseStartY)) / 5.0;
        
        loc_dt_azim = ((double) mouse_dx) / 5.0;
        loc_dt_elev = ((double) mouse_dy) / 5.0;

        WndX = {1.0, 0.0, 0.0};
        WndY = {0.0, 1.0, 0.0};

        RotateX(WndX, current_elev + dt_elev);
        RotateY(WndX, current_azim + dt_azim);
        WndX.z() *= -1;
        
        RotateX(WndY, current_elev + dt_elev);
        RotateY(WndY, current_azim + dt_azim);
        WndY.z() *= -1;

        WndZ = (WndX % WndY).Normalization();

        ArbitraryRotate(WndX, WndY, WndZ, loc_dt_elev, 0, pos_, aim_);
        ArbitraryRotate(Vec3d(1, 0, 0), Vec3d(0, 1, 0), Vec3d(0, 0, 1), 0,
                        -loc_dt_azim, pos_, aim_);
        up_ = WndY.Normalization();

        break;
      case kTRANSLATE:

        realy = ViewPort[3] - y - 1;
        gluProject(aim_.x(), aim_.y(), aim_.z(), MvMat.GetPtr(),
                   ProjMat.GetPtr(), ViewPort,
                   &wx, &wy, &wz);

        gluUnProject((GLdouble) x, (GLdouble) realy, wz, MvMat.GetPtr(),
                     ProjMat.GetPtr(),
                     ViewPort, &mouse_pos.x(), &mouse_pos.y(), 
                     &mouse_pos.z());
        
        // move both the camera position and its aim coordinate
        dir = mouse_pos - PrevMousePos;
        pos_ = pos_ - dir;
        aim_ = aim_ - dir;

        PrevMousePos = mouse_pos;
        break;
    }
    MousePrevX = x;
    MousePrevY = y;
  }
}
Example #2
0
void draw_s2fishdome(CAMERA cam) {
  
  // draw a fisheye / warped projection of the geometry
  double r, near, far;
  XYZ vp, vd, vr, vl;
  XYZ vright, vleft, vup;

  // Calculate various view vectors 
  vp = cam.vp;
  vd = cam.vd;
  vr = CrossProduct(vd,cam.vu);
  vl = CrossProduct(cam.vu,vd);
  vd = ArbitraryRotate(vd,cam.fishrotate,vr);
  vup = CrossProduct(vr,vd);
  vright = VectorAdd(vr,vd);
  vleft = VectorAdd(vl,vd);
  near = VectorLength(_s2priv_pmin(),_s2priv_pmax()) / 100;
  far  = MAX(cam.focallength,VectorLength(_s2priv_pmin(),
					     _s2priv_pmax())) * 20;
  
  // Left
  glDrawBuffer(GL_BACK);
  glReadBuffer(GL_BACK);
  glViewport(0,0,TEXTURESIZE,TEXTURESIZE);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  s2Perspective(90.0,1.0,near,far);
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  s2LookAt(vp.x,vp.y,vp.z,vp.x+vleft.x,vp.y+vleft.y,vp.z+vleft.z,vup.x,vup.y,vup.z);
  MakeLighting();
  MakeMaterial();
  MakeGeometry(FALSE, FALSE);
  glBindTexture(GL_TEXTURE_2D,walltextureid[2]);
  glCopyTexSubImage2D(GL_TEXTURE_2D,0,0,0,0,0,TEXTURESIZE,TEXTURESIZE);
    
  // Right
  glDrawBuffer(GL_BACK);
  glReadBuffer(GL_BACK);
  glViewport(0,0,TEXTURESIZE,TEXTURESIZE);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  s2Perspective(90.0,1.0,near,far);
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  s2LookAt(vp.x,vp.y,vp.z,vp.x+vright.x,vp.y+vright.y,vp.z+vright.z,vup.x,vup.y,vup.z);
  MakeLighting();
  MakeMaterial();
  MakeGeometry(FALSE, FALSE);
  glBindTexture(GL_TEXTURE_2D,walltextureid[3]);
  glCopyTexSubImage2D(GL_TEXTURE_2D,0,0,0,0,0,TEXTURESIZE,TEXTURESIZE);
  
  // Top 
  glDrawBuffer(GL_BACK);
  glReadBuffer(GL_BACK);
  glViewport(0,0,TEXTURESIZE,TEXTURESIZE);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  s2Perspective(90.0,1.0,near,far);
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  s2LookAt(vp.x,vp.y,vp.z,vp.x+vup.x,vp.y+vup.y,vp.z+vup.z,-vright.x,-vright.y,-vright.z);
  MakeLighting();
  MakeMaterial();
  MakeGeometry(FALSE, FALSE);
  glBindTexture(GL_TEXTURE_2D,walltextureid[0]);
  glCopyTexSubImage2D(GL_TEXTURE_2D,0,0,0,0,0,TEXTURESIZE,TEXTURESIZE);
  
  // Bottom 
  glDrawBuffer(GL_BACK);
  glReadBuffer(GL_BACK);
  glViewport(0,0,TEXTURESIZE,TEXTURESIZE);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  s2Perspective(90.0,1.0,near,far);
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  s2LookAt(vp.x,vp.y,vp.z,vp.x-vup.x,vp.y-vup.y,vp.z-vup.z,-vleft.x,-vleft.y,-vleft.z);
  MakeLighting();
  MakeMaterial();
  MakeGeometry(FALSE, FALSE);
  glBindTexture(GL_TEXTURE_2D,walltextureid[1]);
  glCopyTexSubImage2D(GL_TEXTURE_2D,0,0,0,0,0,TEXTURESIZE,TEXTURESIZE);
  
  // Remember the graphics state and return it at the end
  glPushAttrib(GL_ALL_ATTRIB_BITS);
  glDisable(GL_LIGHTING);
  glDisable(GL_ALPHA_TEST);
  glDisable(GL_COLOR_MATERIAL);
  glDisable(GL_DITHER);
  //glDisable(GL_FOG);
  glDisable(GL_LINE_SMOOTH);
  glDisable(GL_LINE_STIPPLE);
  glDisable(GL_SCISSOR_TEST);
  glDisable(GL_STENCIL_TEST);
  
  // Setup projections for the dome
  glDrawBuffer(GL_BACK);
  if (_s2fd_options->dometype == WARPMAP)
    glClearColor(0.0,0.0,0.0,0.0);
  else
    glClearColor(0.05,0.05,0.05,0.0);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glViewport(0,0,_s2fd_options->screenwidth,_s2fd_options->screenheight);
  r = _s2fd_options->screenwidth / (double)_s2fd_options->screenheight;
  switch (_s2fd_options->dometype) {
  case TRUNCTOP:
  case TRUNCBOTTOM:
    glOrtho(-r*0.75,r*0.75,-0.75,0.75,0.1,10.0);
    break;
  case HSPHERICAL:
    glOrtho(-r*0.75,r*0.75,-0.75,0.75,0.1,10.0);
    break;
  case VSPHERICAL:
  case WARPMAP:
  default:
    glOrtho(-r,r,-1.0,1.0,0.1,10.0);
    break;
  }
    
  // Create camera projection for dome
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  switch (_s2fd_options->dometype) {
  case TRUNCBOTTOM:
    s2LookAt(0.0,-1.0,0.25,0.0,0.0,0.25,0.0,0.0,1.0);
    break;
  case TRUNCTOP:
    s2LookAt(0.0,-1.0,-0.25,0.0,0.0,-0.25,0.0,0.0,1.0);
    break;
  case HSPHERICAL:
  case VSPHERICAL:
  case WARPMAP:
  default:
    s2LookAt(0.0,-1.0,0.0,0.0,0.0,0.0,0.0,0.0,1.0);
    break;
  }
    
  // Finally draw the dome geometry
  glPolygonMode(GL_FRONT_AND_BACK,GL_FILL);
  glColor3f(1.0,1.0,1.0);
  DrawDome(TRUE,FALSE);

  _s2_fadeinout();
  
  DrawExtras();
  glPopAttrib();
  
}