bool Viewer::on_motion_notify_event(GdkEventMotion* event) { DEBUG_MSG("Stub: Motion at " << event->x << ", " << event->y ); Point2D dMouse(event->x - m_lastMouse[0], event->y - m_lastMouse[1]); bool b1,b2,b3; b1 = event->state & GDK_BUTTON1_MASK; b2 = event->state & GDK_BUTTON2_MASK; b3 = event->state & GDK_BUTTON3_MASK; //track ball mode if (m_mode == POSITION) { // do x,y translation if (b1) { double translationScale = 50.0; Vector3D translate(dMouse[0] / translationScale, -dMouse[1] / translationScale , 0); Matrix4x4 t = translation(translate); m_trackballTranslation = m_trackballTranslation * t; } if (b2) { Vector3D translate(0.0, 0.0, dMouse[1]/ 35.0); Matrix4x4 t = translation(translate); m_trackballTranslation = m_trackballTranslation * t; } if (b3) { /* * Track ball rotations are being used. */ float fDiameter; int iCenterX, iCenterY; float fNewModX, fNewModY, fOldModX, fOldModY; /* vCalcRotVec expects new and old positions in relation to the center of the * trackball circle which is centered in the middle of the window and * half the smaller of nWinWidth or nWinHeight. */ fDiameter = (get_width() < get_height()) ? (float)get_width() * 0.5f : (float)get_height() * 0.5f; iCenterX = get_width() / 2; iCenterY = get_height() / 2; fOldModX = m_lastMouse[0] - iCenterX; fOldModY = m_lastMouse[1] - iCenterY; fNewModX = event->x - iCenterX; fNewModY = event->y - iCenterY; float fRotVecX, fRotVecY, fRotVecZ; vCalcRotVec(fNewModX, fNewModY, fOldModX, fOldModY, fDiameter, &fRotVecX, &fRotVecY, &fRotVecZ); /* Negate Y component since Y axis increases downwards * in screen space and upwards in OpenGL. */ Matrix4x4 mNewMat = vAxisRotMatrix(fRotVecX, -fRotVecY, fRotVecZ); // Since all these matrices are meant to be loaded // into the OpenGL matrix stack, we need to transpose the // rotation matrix (since OpenGL wants rows stored // in columns) //vTransposeMatrix(mNewMat); //vRightMultiply(mRotations, mNewMat); m_trackballRotation = m_trackballRotation * mNewMat; } DEBUG_MSG("trackballMatrix: Translation\n" << m_trackballTranslation << "Rotation\n" << m_trackballRotation); } else { // JOINT manipulation mode // rotate head up down relative to y when b2 // rotate head left right with x motion when b3 // grab all selected nodes // grab their parents // rotate their joint left/right, up/down for (std::list<SceneNode*>::const_iterator it = m_selected.begin(), end = m_selected.end(); it != end; ++it) { assert((*it)->is_selected()); SceneNode *parent = (*it)->jointParent(); // check if parent is joint node DEBUG_MSG("Rotating: " << (*it)->name()); assert(parent); DEBUG_MSG("Parent: name " << parent->name()); assert(parent->is_joint()); JointNode *joint = dynamic_cast<JointNode*>(parent); assert(joint); double rotationScale = -3.0; if (b2) { // rotate in degrees joint->rotate( dMouse[1] / rotationScale, 0.0); } if (b3) { joint->rotate(0.0, dMouse[0] / rotationScale); } } } m_lastMouse = Point2D(event->x, event->y); invalidate(); return true; }