示例#1
0
glm::mat4 CameraOvr::getOrientation(OVR::Quatf orientationQuat, const OVR::Util::Render::StereoEyeParams& eyeParams) {

    orientationQuat.GetEulerAngles<OVR::Axis_Y, OVR::Axis_X, OVR::Axis_Z>(&_hmdRy, &_hmdRx, &_hmdRz);

    OVR::Matrix4f orientation = OVR::Matrix4f::RotationY(_hmdRy+_ry)
                                * OVR::Matrix4f::RotationX(_hmdRx+_rx)
                                * OVR::Matrix4f::RotationZ(_hmdRz+_rz);

    OVR::Matrix4f view = orientation.Inverted() * eyeParams.ViewAdjust;

    return ovrToGlmMat4(view);
}
示例#2
0
/// Scale the parallax translation and head pose motion vector by the head size
/// dictated by the shader. Thanks to the elegant design decision of putting the
/// head's default position at the origin, this is simple.
OVR::Matrix4f _MakeModelviewMatrix(
    ovrPosef eyePose,
    ovrVector3f viewAdjust,
    float chassisYaw,
    ovrVector3f chassisPos,
    float headScale=1.0f)
{
    const OVR::Matrix4f eyePoseMatrix =
        OVR::Matrix4f::Translation(OVR::Vector3f(eyePose.Position) * headScale)
        * OVR::Matrix4f(OVR::Quatf(eyePose.Orientation));

    const OVR::Matrix4f view =
        OVR::Matrix4f::Translation(OVR::Vector3f(viewAdjust) * headScale)
        * eyePoseMatrix.Inverted()
        * OVR::Matrix4f::RotationY(chassisYaw)
        * OVR::Matrix4f::Translation(-OVR::Vector3f(chassisPos));

    return view;
}
示例#3
0
void OVRScene::timestep(double /*absTime*/, double dt)
{
    (void)dt;
    if (m_pHmd == NULL)
        return;

    const ovrTrackingState ts = ovrHmd_GetTrackingState(m_pHmd, ovr_GetTimeInSeconds());
    const ovrVector3f& hp = ts.HeadPose.ThePose.Position;
    glm::vec4 headPt(hp.x, hp.y, hp.z, 1.0f);

    // Get camera pose as a matrix
    const ovrPosef& cp = ts.CameraPose;
    OVR::Matrix4f camMtx = OVR::Matrix4f();
    camMtx *= OVR::Matrix4f::Translation(cp.Position)
        * OVR::Matrix4f(OVR::Quatf(cp.Orientation));

    const glm::mat4 gcamMtx = glm::make_mat4(&camMtx.Inverted().Transposed().M[0][0]);
    headPt = gcamMtx * headPt;
    m_tanFromCameraCenterline.x = fabs(headPt.x / headPt.z);
    m_tanFromCameraCenterline.y = fabs(headPt.y / headPt.z);

#if 0
    std::vector<glm::vec3> txFrustumPts = m_frustumVerts;
    for (std::vector<glm::vec3>::const_iterator it = txFrustumPts.begin();
        it != txFrustumPts.end();
        ++it)
    {
        glm::vec3 pt = *it;
        glm::vec4 pt4(pt, 1.0f);
        pt4 = gcamMtx * pt4;
        pt.x = pt4.x;
        pt.y = pt4.y;
        pt.z = pt4.z;
    }

    // Calculate minimum distance to frustum
    std::vector<glm::ivec3> planeIndices;
    planeIndices.push_back(glm::ivec3(2, 3, 4));
    planeIndices.push_back(glm::ivec3(8, 7, 6));
    planeIndices.push_back(glm::ivec3(2, 3, 7));
    planeIndices.push_back(glm::ivec3(3, 4, 8));
    planeIndices.push_back(glm::ivec3(4, 5, 9));
    planeIndices.push_back(glm::ivec3(5, 2, 6));

    float minDist = 999.0f;
    for (std::vector<glm::ivec3>::const_iterator it = planeIndices.begin();
        it != planeIndices.end();
        ++it)
    {
        const glm::ivec3& idxs = *it;
        // Assume this point has already been transformed
        // If our indices are out of bounds, we're hosed
        const glm::vec3& p1 = txFrustumPts[idxs.x];
        const glm::vec3& p2 = txFrustumPts[idxs.y];
        const glm::vec3& p3 = txFrustumPts[idxs.z];
        const glm::vec3 v1 = p1 - p2;
        const glm::vec3 v2 = p3 - p2;
        const glm::vec3 norm = glm::normalize(glm::cross(v1, v2));
        const glm::vec3 ptDist = headPt - p2;
        const float dist = fabs(glm::dot(norm, ptDist)); // shouldn't need fabs if ordering is correct
        minDist = std::min(minDist, dist);
    }
    m_distanceToFrustum = minDist;
#endif
}