예제 #1
0
osg::Vec3d ViewingCore::findDeltaOnPanPlane(double ndcX1, double ndcY1, double ndcX2, double ndcY2)
{
    // Get the view volume far plane value, and the distance from
    // the near to far plane.
    double zNear, zFar;
    osg::Matrixd p = computeProjection();
    if( getOrtho() ) {
        double l, r, b, t;
        p.getOrtho( l, r, b, t, zNear, zFar );
    } else {
        double fovy, aspect;
        p.getPerspective( fovy, aspect, zNear, zFar );
    }
    const double distance = zFar - zNear;

    // Create two points, both in NDC space, and lying on the far plane at the back
    // of the view volume. One is the xy origin, the other with the passed xy parameters.
    osg::Vec4d farPoint0 = osg::Vec4d( ndcX1, ndcY1, 1., 1. );
    osg::Vec4d farPoint1 = osg::Vec4d( ndcX2, ndcY2, 1., 1. );
    if( !getOrtho() ) {
        // Not ortho, so w != 1.0. Multiply by the far plane distance.
        // This yields values in clip coordinates.
        farPoint0 *= zFar;
        farPoint1 *= zFar;
    }

    // Get inverse view & proj matrices to back-transform the
    // two clip coord far points into world space.
    osg::Matrixd v = getMatrix();
    p.invert( p );
    osg::Vec4d wc0 = farPoint0 * p * v;
    osg::Vec4d wc1 = farPoint1 * p * v;

    // Intersect the two world coord points with the pan plane.
    osg::Vec3d result0, result1;
    osg::Vec3d p1( wc0.x(), wc0.y(), wc0.z() );
    osg::Vec3d p0 = getOrtho() ? p1 - ( _viewDir * distance ) : getEyePosition();
    intersectPlaneRay( result0, _panPlane, p0, p1 );
    p1 = osg::Vec3d( wc1.x(), wc1.y(), wc1.z() );
    p0 = getOrtho() ? p1 - ( _viewDir * distance ) : getEyePosition();
    intersectPlaneRay( result1, _panPlane, p0, p1 );

    // Subtract the two plane intersection points to get the delta world coord
    // motion return
    return result1 - result0;
}
예제 #2
0
void ViewingCore::pan( const double ndcX, const double ndcY )
{
    // Get the view volume far plane value, and the distance from
    // the near to far plane.
    double zNear, zFar;
    osg::Matrixd p;

    getZNearZFarProj(zNear, zFar, p);

    const double distance = zFar - zNear;

    // Create two points, both in NDC space, and lying on the far plane at the back
    // of the view volume. One is the xy origin, the other with the passed xy parameters.
    osg::Vec4d farPoint0 = osg::Vec4d( 0., 0., 1., 1. );
    osg::Vec4d farPoint1 = osg::Vec4d( ndcX, ndcY, 1., 1. );
    if( !getOrtho() ) {
        // Not ortho, so w != 1.0. Multiply by the far plane distance.
        // This yields values in clip coordinates.
        farPoint0 *= zFar;
        farPoint1 *= zFar;
    }

    // Get inverse view & proj matrices to back-transform the
    // two clip coord far points into world space.
    osg::Matrixd v = getMatrix();
    p.invert( p );
    osg::Vec4d wc0 = farPoint0 * p * v;
    osg::Vec4d wc1 = farPoint1 * p * v;

    // Intersect the two world coord points with the pan plane.
    osg::Vec3d result0, result1;
    osg::Vec3d p1( wc0.x(), wc0.y(), wc0.z() );
    osg::Vec3d p0 = getOrtho() ? p1 - ( _viewDir * distance ) : getEyePosition();
    intersectPlaneRay( result0, _panPlane, p0, p1 );
    p1 = osg::Vec3d( wc1.x(), wc1.y(), wc1.z() );
    p0 = getOrtho() ? p1 - ( _viewDir * distance ) : getEyePosition();
    intersectPlaneRay( result1, _panPlane, p0, p1 );

    // Subtract the two plane intersection points to get the delta world coord
    // motion and move the view center accordingly.
    osg::Vec3d delta = result1 - result0;
    osg::notify( osg::DEBUG_FP ) << "    delta " << delta << std::endl;
    _viewCenter -= delta;
}
예제 #3
0
bool calcDistToLine(const Ray3f &lineSegmentRay, const Ray3f &ray,
                    float32 &distQuad, float32 &rayParam, float32 &lineSegParam)
{
   Vector3f distNormal = lineSegmentRay.direction.crossProduct(ray.direction);
   if (distNormal*distNormal < EPSILON * EPSILON) return false;
   Vector3f planeRayNormal = ray.direction.crossProduct(distNormal);
   bool iFound = intersectPlaneRay(lineSegmentRay, planeRayNormal, ray.origin, lineSegParam);
   if (!iFound || lineSegParam < 0 || lineSegParam > 1) {
      return false;
   }
   Vector3f planeLineSegNormal = lineSegmentRay.direction.crossProduct(distNormal);
   iFound = intersectPlaneRay(ray, planeLineSegNormal, lineSegmentRay.origin, rayParam);
   if (iFound) {
      Vector3f dist =   lineSegmentRay.origin + lineSegmentRay.direction * lineSegParam
                      -           (ray.origin +            ray.direction * rayParam);
      distQuad = dist*dist;
      return true;
   }
   return false;
}