Example #1
0
void doArcball(
	double * _viewMatrix, 
	double const * _rotationCenter, 
	double const * _projectionMatrix, 
	double const * _initialViewMatrix, 
	//double const * _currentViewMatrix,
	double const * _initialMouse, 
	double const * _currentMouse, 
	bool screenSpaceRadius,
	double radius)
{
	Eigen::Map<Eigen::Vector3d const> rotationCenter(_rotationCenter);
	Eigen::Map<Eigen::Matrix4d const> initialViewMatrix(_initialViewMatrix);
	//Eigen::Map<Eigen::Matrix4d const> currentViewMatrix(_currentViewMatrix);
	Eigen::Map<Eigen::Matrix4d const> projectionMatrix(_projectionMatrix);
	Eigen::Map<Eigen::Matrix4d> viewMatrix(_viewMatrix);

	Eigen::Vector2d initialMouse(_initialMouse);
	Eigen::Vector2d currentMouse(_currentMouse);
	
	Eigen::Quaterniond q;
	Eigen::Vector3d Pa, Pc;
	if (screenSpaceRadius) {
		double aspectRatio = projectionMatrix(1, 1) / projectionMatrix(0, 0);

		initialMouse(0) *= aspectRatio;
		currentMouse(0) *= aspectRatio;

		Pa = mapToSphere(initialMouse, radius);
		Pc = mapToSphere(currentMouse, radius);

		q.setFromTwoVectors(Pa - rotationCenter, Pc - rotationCenter);
	}
	else {
		Pa = mapToSphere(projectionMatrix.inverse(), initialMouse, rotationCenter, radius);
		Pc = mapToSphere(projectionMatrix.inverse(), currentMouse, rotationCenter, radius);

		Eigen::Vector3d a = Pa - rotationCenter, b = Pc - rotationCenter;

#if 0
		std::cout << "Mouse Initial Radius = " << sqrt(a.dot(a)) << " Current Radius = " << sqrt(b.dot(b)) << std::endl;
#endif

		q.setFromTwoVectors(a, b);
	}	

	Eigen::Matrix4d qMat4;
	qMat4.setIdentity();
	qMat4.topLeftCorner<3, 3>() = q.toRotationMatrix();

	Eigen::Matrix4d translate;
	translate.setIdentity();
	translate.topRightCorner<3, 1>() = -rotationCenter;

	Eigen::Matrix4d invTranslate;
	invTranslate.setIdentity();
	invTranslate.topRightCorner<3, 1>() = rotationCenter;
	
    viewMatrix = invTranslate * qMat4 * translate * initialViewMatrix;
}
Example #2
0
void GLWidget::mousePressEvent(QMouseEvent *event)
{
    m_last_p2d = Imath::V2d(event->pos().x(), event->pos().y());
    std::pair<bool, Imath::V3d> map;
    map = mapToSphere(m_last_p2d);
    m_last_pok = map.first;
    m_last_p3d = map.second;
}
Example #3
0
 Quaternionf ArcBall::move(Vec2f p)
 {
     m_EndVector = mapToSphere(p);
     
     Vec3f perp = m_StartVector.cross(m_EndVector);
     if(perp.norm() > 1.0e-5f)
     {
         return Quaternionf(
             m_StartVector.dot(m_EndVector),
             perp.x(),
             perp.y(),
             perp.z()
         );
     }
     
     return Quaternionf::Identity();
 }
Example #4
0
void GLWidget::mouseMoveEvent(QMouseEvent *event)
{
    Imath::V2d newPoint2D(event->pos().x(), event->pos().y());
    
    if ( ((newPoint2D.x < 0) || (newPoint2D.x > width()) ||
       (newPoint2D.y < 0) || (newPoint2D.y > height())) ) {
        event->ignore();
    }

    float value_y = 0;

    std::pair<bool, Imath::V3d> map;
    map = mapToSphere(m_last_p2d);
    bool newPoint_hitSphere = map.first;
    Imath::V3d newPoint3D = map.second;

    float dx = newPoint2D.x - m_last_p2d.x;
    float dy = newPoint2D.y - m_last_p2d.y;
    float w = width();
    float h = height();
    makeCurrent();

    if ( (event->buttons() == Qt::LeftButton & event->modifiers() == Qt::ControlModifier)
        || (event->buttons() == Qt::RightButton & event->modifiers() == Qt::AltModifier) ) {
        m_camera.dolly(Imath::V2d(dx, dy));
    } else if ( (event->buttons() & Qt::MidButton
        || (event->buttons() == Qt::LeftButton & event->modifiers() == Qt::ShiftModifier)) ) {
        m_camera.track(Imath::V2d(dx, dy));
    } else if ( event->buttons() & Qt::LeftButton ) {
        m_rotating = true;
        m_camera.rotate(Imath::V2d(dx, dy));
    }

    m_last_p2d = newPoint2D;
    m_last_p3d = newPoint3D;
    m_last_pok = newPoint_hitSphere;
    
    m_camera.apply();
    updateGL();
}
Example #5
0
void _XArcBall::drag(_XVector2 point,_XVector4& rotate)
{
	mapToSphere(point,m_dragVector);	//Map the point to the sphere
	//Return the quaternion equivalent to the rotation
	_XVector3 perp = m_clickVector * m_dragVector;	//Compute the vector perpendicular to the begin and end vectors
	//Compute the length of the perpendicular vector
	if(perp.getLength() > (1.0e-5))    //if its non-zero
	//if(perp.getLength() >= 0.0f)    //if its non-zero
	{//We're ok, so return the perpendicular vector as the transform after all
		rotate.x = perp.x;
		rotate.y = perp.y;
		rotate.z = perp.z;
		//In the quaternion values, w is cosine (theta / 2), where theta is rotation angle
		rotate.w = m_clickVector.dot(m_dragVector);
	}else                                    //if its zero
	{//The begin and end vectors coincide, so return an identity transform
		rotate.x = 
		rotate.y = 
		rotate.z = 
		rotate.w = 0.0f;
		printf("Error!\n");
	}
}
TerrainPatchData::TerrainPatchData(TerrainQuadtree* tree) :
        tree(tree),
        tessellation(tree->getPlanetarySurface()->getTessellation()),
        vertices(tessellation + 3, std::vector<Ogre::Vector3>(tessellation + 3)),
        normals(tessellation + 3, std::vector<Ogre::Vector3>(tessellation + 3)),
        heights(tessellation + 3, std::vector<Ogre::Real>(tessellation + 3, 0.0)) {
    int patchSize = tree->getSize();
    Ogre::Real halfPatchSize = Ogre::Real(patchSize / 2);
    Ogre::Real delta = (Ogre::Real)patchSize * (1.0 / (Ogre::Real)tessellation);

    Ogre::SceneNode* patchSceneNode = tree->getSceneNode();
    Ogre::SceneNode* planetarySceneNode = tree->getPlanetarySurface()->getSceneNode();

    Ogre::Real planetaryRadius = (Ogre::Real)tree->getPlanetarySurface()->getRadius();

    for (int z = -1; z < tessellation + 2; ++z) {
        for (int x = -1; x < tessellation + 2; ++x) {
            Ogre::Vector3 position(-halfPatchSize + delta * x, 0.0, -halfPatchSize + delta * z);
            Ogre::Vector3 planetaryPosition = planetarySceneNode->convertWorldToLocalPosition(patchSceneNode->convertLocalToWorldPosition(position));
            planetaryPosition = mapToSphere(planetaryPosition, planetaryRadius);
            Ogre::Vector3 normal = planetaryPosition.normalisedCopy();
            Ogre::Real height = tree->getPlanetarySurface()->getNoiseFunction()->getValue(planetaryPosition);

            planetaryPosition = planetarySceneNode->convertLocalToWorldPosition(planetaryPosition);
            position = patchSceneNode->convertWorldToLocalPosition(planetaryPosition);

            normal = (tree->getRootSceneNode()->getOrientation().Inverse() * normal).normalisedCopy();

            vertices[z + 1][x + 1] = position;
            normals[z + 1][x + 1] = normal;
            heights[z + 1][x + 1] = height;
        }
    }

    for (int z = 0; z < tessellation + 1; ++z) {
        for (int x = 0; x < tessellation + 1; ++x) {
            processedPositions.push_back(getVertex(x, z));
            processedNormals.push_back(getVertexNormal(x, z));
            processedTextureCoords.push_back(getNormal(x, z));
        }
    }

    // Add triangles.
    for (int z = 0; z < tessellation; ++z) {
        int zOffset = z * (tessellation + 1);
        for (int x = 0; x < tessellation; ++x) {
            int indices[4] = {
                zOffset + x,
                zOffset + x + 1,
                zOffset + tessellation + 1 + x,
                zOffset + tessellation + 1 + x + 1
            };

            processedIndices.push_back(indices[0]);
            processedIndices.push_back(indices[2]);
            processedIndices.push_back(indices[1]);
            processedIndices.push_back(indices[2]);
            processedIndices.push_back(indices[3]);
            processedIndices.push_back(indices[1]);
        }
    }
}
Ray PointLight::shootRay(){
    double x, y, z;
    mapToSphere(randReal(), randReal(), x, y, z);
    return Ray(pos, Vector(x, y, z));
}
Example #8
0
 void ArcBall::start(Vec2f p)
 {
     m_StartVector = mapToSphere(p);
 }