mirror of
https://github.com/TorqueGameEngines/Torque3D.git
synced 2026-01-19 20:24:49 +00:00
Oculus Rift Improvements
- Now requires OVR SDK 0.2.5 - New chromatic aberration correction shader. Can be disabled by setting $pref::OculusVR::UseChromaticAberrationCorrection to false prior to enabling Rift display (such as for screen shots). - FXAA on by default when using full screen on the Rift. - Can now manually override IPD from script. Otherwise value set in profile is used. - Raw sensor data now available through input events (set $OculusVR::GenerateSensorRawEvents to true) and console methods. The raw data is acceleration, angular velocity, and magnetometer reading. - Can determine if magnetometer calibration data is available using a console method in order to notify the user.
This commit is contained in:
parent
8d2fcf2456
commit
85730dfb59
|
|
@ -42,6 +42,7 @@ IMPLEMENT_CONOBJECT(BarrelDistortionPostEffect);
|
|||
BarrelDistortionPostEffect::BarrelDistortionPostEffect()
|
||||
: PostEffect(),
|
||||
mHmdWarpParamSC(NULL),
|
||||
mHmdChromaAbSC(NULL),
|
||||
mScaleSC(NULL),
|
||||
mScaleInSC(NULL),
|
||||
mLensCenterSC(NULL),
|
||||
|
|
@ -85,23 +86,22 @@ void BarrelDistortionPostEffect::onRemove()
|
|||
|
||||
void BarrelDistortionPostEffect::_setupConstants( const SceneRenderState *state )
|
||||
{
|
||||
// Test if setup is required before calling the parent method as the parent method
|
||||
// will set up the shader constants buffer for us.
|
||||
bool setupRequired = mShaderConsts.isNull();
|
||||
|
||||
Parent::_setupConstants(state);
|
||||
|
||||
// Define the shader constants
|
||||
if(!mHmdWarpParamSC)
|
||||
if(setupRequired)
|
||||
{
|
||||
mHmdWarpParamSC = mShader->getShaderConstHandle( "$HmdWarpParam" );
|
||||
|
||||
if(!mScaleSC)
|
||||
mHmdChromaAbSC = mShader->getShaderConstHandle( "$HmdChromaAbParam" );
|
||||
mScaleSC = mShader->getShaderConstHandle( "$Scale" );
|
||||
|
||||
if(!mScaleInSC)
|
||||
mScaleInSC = mShader->getShaderConstHandle( "$ScaleIn" );
|
||||
|
||||
if(!mLensCenterSC)
|
||||
mLensCenterSC = mShader->getShaderConstHandle( "$LensCenter" );
|
||||
|
||||
if(!mScreenCenterSC)
|
||||
mScreenCenterSC = mShader->getShaderConstHandle( "$ScreenCenter" );
|
||||
}
|
||||
|
||||
const Point2I &resolution = GFX->getActiveRenderTarget()->getSize();
|
||||
F32 widthScale = 0.5f;
|
||||
|
|
@ -119,6 +119,12 @@ void BarrelDistortionPostEffect::_setupConstants( const SceneRenderState *state
|
|||
mShaderConsts->set( mHmdWarpParamSC, distortion );
|
||||
}
|
||||
|
||||
if(mHmdChromaAbSC->isValid())
|
||||
{
|
||||
const Point4F& correction = hmd->getChromaticAbCorrection();
|
||||
mShaderConsts->set( mHmdChromaAbSC, correction );
|
||||
}
|
||||
|
||||
if(mScaleSC->isValid())
|
||||
{
|
||||
F32 scaleFactor = hmd->getDistortionScale();
|
||||
|
|
@ -149,6 +155,11 @@ void BarrelDistortionPostEffect::_setupConstants( const SceneRenderState *state
|
|||
mShaderConsts->set( mHmdWarpParamSC, Point4F(0.0f, 0.0f, 0.0f, 0.0f) );
|
||||
}
|
||||
|
||||
if(mHmdChromaAbSC->isValid())
|
||||
{
|
||||
mShaderConsts->set( mHmdChromaAbSC, Point4F(1.0f, 0.0f, 1.0f, 0.0f) );
|
||||
}
|
||||
|
||||
if(mScaleSC->isValid())
|
||||
{
|
||||
mShaderConsts->set( mScaleSC, Point2F(1.0f, 1.0f) );
|
||||
|
|
|
|||
|
|
@ -31,6 +31,7 @@ class BarrelDistortionPostEffect : public PostEffect
|
|||
|
||||
protected:
|
||||
GFXShaderConstHandle *mHmdWarpParamSC;
|
||||
GFXShaderConstHandle *mHmdChromaAbSC;
|
||||
GFXShaderConstHandle *mScaleSC;
|
||||
GFXShaderConstHandle *mScaleInSC;
|
||||
GFXShaderConstHandle *mLensCenterSC;
|
||||
|
|
|
|||
|
|
@ -60,12 +60,16 @@ bool OculusVRDevice::smEnableDevice = true;
|
|||
|
||||
bool OculusVRDevice::smSimulateHMD = true;
|
||||
|
||||
bool OculusVRDevice::smUseChromaticAberrationCorrection = true;
|
||||
|
||||
bool OculusVRDevice::smGenerateAngleAxisRotationEvents = true;
|
||||
bool OculusVRDevice::smGenerateEulerRotationEvents = false;
|
||||
|
||||
bool OculusVRDevice::smGenerateRotationAsAxisEvents = false;
|
||||
F32 OculusVRDevice::smMaximumAxisAngle = 25.0f;
|
||||
|
||||
bool OculusVRDevice::smGenerateSensorRawEvents = false;
|
||||
|
||||
bool OculusVRDevice::smGenerateWholeFrameEvents = false;
|
||||
|
||||
OculusVRDevice::OculusVRDevice()
|
||||
|
|
@ -99,6 +103,10 @@ void OculusVRDevice::staticInit()
|
|||
"@brief If true, the Oculus VR device will be enabled, if present.\n\n"
|
||||
"@ingroup Game");
|
||||
|
||||
Con::addVariable("pref::OculusVR::UseChromaticAberrationCorrection", TypeBool, &smUseChromaticAberrationCorrection,
|
||||
"@brief If true, Use the chromatic aberration correction version of the Oculus VR barrel distortion shader.\n\n"
|
||||
"@ingroup Game");
|
||||
|
||||
Con::addVariable("OculusVR::GenerateAngleAxisRotationEvents", TypeBool, &smGenerateAngleAxisRotationEvents,
|
||||
"@brief If true, broadcast sensor rotation events as angled axis.\n\n"
|
||||
"@ingroup Game");
|
||||
|
|
@ -114,6 +122,10 @@ void OculusVRDevice::staticInit()
|
|||
"Should range from 0 to 90 degrees.\n\n"
|
||||
"@ingroup Game");
|
||||
|
||||
Con::addVariable("OculusVR::GenerateSensorRawEvents", TypeBool, &smGenerateSensorRawEvents,
|
||||
"@brief If ture, broadcast sensor raw data: acceleration, angular velocity, magnetometer reading.\n\n"
|
||||
"@ingroup Game");
|
||||
|
||||
Con::addVariable("OculusVR::GenerateWholeFrameEvents", TypeBool, &smGenerateWholeFrameEvents,
|
||||
"@brief Indicates that a whole frame event should be generated and frames should be buffered.\n\n"
|
||||
"@ingroup Game");
|
||||
|
|
@ -313,7 +325,7 @@ bool OculusVRDevice::process()
|
|||
// Process each sensor
|
||||
for(U32 i=0; i<mSensorDevices.size(); ++i)
|
||||
{
|
||||
mSensorDevices[i]->process(mDeviceType, smGenerateAngleAxisRotationEvents, smGenerateEulerRotationEvents, smGenerateRotationAsAxisEvents, maxAxisRadius);
|
||||
mSensorDevices[i]->process(mDeviceType, smGenerateAngleAxisRotationEvents, smGenerateEulerRotationEvents, smGenerateRotationAsAxisEvents, maxAxisRadius, smGenerateSensorRawEvents);
|
||||
}
|
||||
|
||||
return true;
|
||||
|
|
@ -391,6 +403,22 @@ const OculusVRHMDDevice* OculusVRDevice::getHMDDevice(U32 index) const
|
|||
return mHMDDevices[index];
|
||||
}
|
||||
|
||||
F32 OculusVRDevice::getHMDCurrentIPD(U32 index)
|
||||
{
|
||||
if(index >= mHMDDevices.size())
|
||||
return -1.0f;
|
||||
|
||||
return mHMDDevices[index]->getIPD();
|
||||
}
|
||||
|
||||
void OculusVRDevice::setHMDCurrentIPD(U32 index, F32 ipd)
|
||||
{
|
||||
if(index >= mHMDDevices.size())
|
||||
return;
|
||||
|
||||
return mHMDDevices[index]->setIPD(ipd, mScaleInputTexture);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
const OculusVRSensorDevice* OculusVRDevice::getSensorDevice(U32 index) const
|
||||
|
|
@ -409,6 +437,30 @@ EulerF OculusVRDevice::getSensorEulerRotation(U32 index)
|
|||
return mSensorDevices[index]->getEulerRotation();
|
||||
}
|
||||
|
||||
VectorF OculusVRDevice::getSensorAcceleration(U32 index)
|
||||
{
|
||||
if(index >= mSensorDevices.size())
|
||||
return Point3F::Zero;
|
||||
|
||||
return mSensorDevices[index]->getAcceleration();
|
||||
}
|
||||
|
||||
EulerF OculusVRDevice::getSensorAngularVelocity(U32 index)
|
||||
{
|
||||
if(index >= mSensorDevices.size())
|
||||
return Point3F::Zero;
|
||||
|
||||
return mSensorDevices[index]->getAngularVelocity();
|
||||
}
|
||||
|
||||
VectorF OculusVRDevice::getSensorMagnetometer(U32 index)
|
||||
{
|
||||
if(index >= mSensorDevices.size())
|
||||
return Point3F::Zero;
|
||||
|
||||
return mSensorDevices[index]->getMagnetometer();
|
||||
}
|
||||
|
||||
F32 OculusVRDevice::getSensorPredictionTime(U32 index)
|
||||
{
|
||||
const OculusVRSensorDevice* sensor = getSensorDevice(index);
|
||||
|
|
@ -438,6 +490,57 @@ void OculusVRDevice::setAllSensorPredictionTime(F32 dt)
|
|||
}
|
||||
}
|
||||
|
||||
bool OculusVRDevice::getSensorGravityCorrection(U32 index)
|
||||
{
|
||||
const OculusVRSensorDevice* sensor = getSensorDevice(index);
|
||||
if(!sensor || !sensor->isValid())
|
||||
return false;
|
||||
|
||||
return sensor->getGravityCorrection();
|
||||
}
|
||||
|
||||
void OculusVRDevice::setSensorGravityCorrection(U32 index, bool state)
|
||||
{
|
||||
if(index >= mSensorDevices.size())
|
||||
return;
|
||||
|
||||
OculusVRSensorDevice* sensor = mSensorDevices[index];
|
||||
if(!sensor->isValid())
|
||||
return;
|
||||
|
||||
sensor->setGravityCorrection(state);
|
||||
}
|
||||
|
||||
bool OculusVRDevice::getSensorYawCorrection(U32 index)
|
||||
{
|
||||
const OculusVRSensorDevice* sensor = getSensorDevice(index);
|
||||
if(!sensor || !sensor->isValid())
|
||||
return false;
|
||||
|
||||
return sensor->getYawCorrection();
|
||||
}
|
||||
|
||||
void OculusVRDevice::setSensorYawCorrection(U32 index, bool state)
|
||||
{
|
||||
if(index >= mSensorDevices.size())
|
||||
return;
|
||||
|
||||
OculusVRSensorDevice* sensor = mSensorDevices[index];
|
||||
if(!sensor->isValid())
|
||||
return;
|
||||
|
||||
sensor->setYawCorrection(state);
|
||||
}
|
||||
|
||||
bool OculusVRDevice::getSensorMagnetometerCalibrated(U32 index)
|
||||
{
|
||||
const OculusVRSensorDevice* sensor = getSensorDevice(index);
|
||||
if(!sensor || !sensor->isValid())
|
||||
return false;
|
||||
|
||||
return sensor->getMagnetometerCalibrationAvailable();
|
||||
}
|
||||
|
||||
void OculusVRDevice::resetAllSensors()
|
||||
{
|
||||
// Reset each sensor
|
||||
|
|
@ -628,6 +731,46 @@ DefineEngineFunction(getOVRHMDDisplayDeviceName, const char*, (S32 index),,
|
|||
return hmd->getDisplayDeviceName();
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDDisplayDeviceId, S32, (S32 index),,
|
||||
"@brief MacOS display ID.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@return The ID of the HMD display device, if any.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
const OculusVRHMDDevice* hmd = OCULUSVRDEV->getHMDDevice(index);
|
||||
if(!hmd)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
return hmd->getDisplayDeviceId();
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDDisplayDesktopPos, Point2I, (S32 index),,
|
||||
"@brief Desktop coordinate position of the screen (can be negative; may not be present on all platforms).\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@return Position of the screen.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return Point2I::Zero;
|
||||
}
|
||||
|
||||
const OculusVRHMDDevice* hmd = OCULUSVRDEV->getHMDDevice(index);
|
||||
if(!hmd)
|
||||
{
|
||||
return Point2I::Zero;
|
||||
}
|
||||
|
||||
return hmd->getDesktopPosition();
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDResolution, Point2I, (S32 index),,
|
||||
"@brief Provides the OVR HMD screen resolution.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
|
|
@ -672,6 +815,78 @@ DefineEngineFunction(getOVRHMDDistortionCoefficients, String, (S32 index),,
|
|||
return buf;
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDChromaticAbCorrection, String, (S32 index),,
|
||||
"@brief Provides the OVR HMD chromatic aberration correction values.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@return A four component string with the chromatic aberration correction values.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return "1 0 1 0";
|
||||
}
|
||||
|
||||
const OculusVRHMDDevice* hmd = OCULUSVRDEV->getHMDDevice(index);
|
||||
if(!hmd)
|
||||
{
|
||||
return "1 0 1 0";
|
||||
}
|
||||
|
||||
const Point4F& c = hmd->getChromaticAbCorrection();
|
||||
char buf[256];
|
||||
dSprintf(buf, 256, "%g %g %g %g", c.x, c.y, c.z, c.w);
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDProfileIPD, F32, (S32 index),,
|
||||
"@brief Physical distance between the user's eye centers as defined by the current profile.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@return The profile IPD.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return -1.0f;
|
||||
}
|
||||
|
||||
const OculusVRHMDDevice* hmd = OCULUSVRDEV->getHMDDevice(index);
|
||||
if(!hmd)
|
||||
{
|
||||
return -1.0f;
|
||||
}
|
||||
|
||||
return hmd->getProfileIPD();
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDCurrentIPD, F32, (S32 index),,
|
||||
"@brief Physical distance between the user's eye centers.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@return The current IPD.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return -1.0f;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getHMDCurrentIPD(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(setOVRHMDCurrentIPD, void, (S32 index, F32 ipd),,
|
||||
"@brief Set the physical distance between the user's eye centers.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
"@param ipd The IPD to use.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
OCULUSVRDEV->setHMDCurrentIPD(index, ipd);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRHMDEyeXOffsets, Point2F, (S32 index),,
|
||||
"@brief Provides the OVR HMD eye x offsets in uv coordinates.\n\n"
|
||||
"@param index The HMD index.\n"
|
||||
|
|
@ -787,6 +1002,49 @@ DefineEngineFunction(getOVRSensorEulerRotation, Point3F, (S32 index),,
|
|||
return Point3F(mRadToDeg(rot.x), mRadToDeg(rot.y), mRadToDeg(rot.z));
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorAcceleration, Point3F, (S32 index),,
|
||||
"@brief Get the acceleration values for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return The acceleration values of the Oculus VR sensor, in m/s^2.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return Point3F::Zero;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getSensorAcceleration(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorAngVelocity, Point3F, (S32 index),,
|
||||
"@brief Get the angular velocity values for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return The angular velocity values of the Oculus VR sensor, in degrees/s.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return Point3F::Zero;
|
||||
}
|
||||
|
||||
EulerF rot = OCULUSVRDEV->getSensorAngularVelocity(index);
|
||||
return Point3F(mRadToDeg(rot.x), mRadToDeg(rot.y), mRadToDeg(rot.z));
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorMagnetometer, Point3F, (S32 index),,
|
||||
"@brief Get the magnetometer reading (direction and field strength) for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return The magnetometer reading (direction and field strength) of the Oculus VR sensor, in Gauss.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return Point3F::Zero;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getSensorMagnetometer(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorPredictionTime, F32, (S32 index),,
|
||||
"@brief Get the prediction time set for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
|
|
@ -828,6 +1086,78 @@ DefineEngineFunction(setAllSensorPredictionTime, void, (F32 dt),,
|
|||
OCULUSVRDEV->setAllSensorPredictionTime(dt);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorGravityCorrection, bool, (S32 index),,
|
||||
"@brief Get the gravity correction state for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return True if gravity correction (for pitch and roll) is active.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getSensorGravityCorrection(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(setOVRSensorGravityCorrection, void, (S32 index, bool state),,
|
||||
"@brief Set the gravity correction state for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@param state The gravity correction state to change to.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
OCULUSVRDEV->setSensorGravityCorrection(index, state);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorYawCorrection, bool, (S32 index),,
|
||||
"@brief Get the yaw correction state for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return True if yaw correction (using magnetometer calibration data) is active.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getSensorYawCorrection(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(setOVRSensorYawCorrection, void, (S32 index, bool state),,
|
||||
"@brief Set the yaw correction state for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@param state The yaw correction state to change to.\n"
|
||||
"@note Yaw correction cannot be enabled if the user has disabled it through "
|
||||
"the Oculus VR control panel.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
OCULUSVRDEV->setSensorYawCorrection(index, state);
|
||||
}
|
||||
|
||||
DefineEngineFunction(getOVRSensorMagnetometerCalibrated, bool, (S32 index),,
|
||||
"@brief Get the magnetometer calibrated data state for the given sensor index.\n\n"
|
||||
"@param index The sensor index.\n"
|
||||
"@return True if magnetometer calibration data is available.\n"
|
||||
"@ingroup Game")
|
||||
{
|
||||
if(!ManagedSingleton<OculusVRDevice>::instanceOrNull())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return OCULUSVRDEV->getSensorMagnetometerCalibrated(index);
|
||||
}
|
||||
|
||||
DefineEngineFunction(ovrResetAllSensors, void, (),,
|
||||
"@brief Resets all Oculus VR sensors.\n\n"
|
||||
"This resets all sensor orientations such that their 'normal' rotation "
|
||||
|
|
|
|||
|
|
@ -44,6 +44,10 @@ public:
|
|||
// If no HMD is present simulate it being available
|
||||
static bool smSimulateHMD;
|
||||
|
||||
// Use the chromatic aberration correction version of the barrel
|
||||
// distortion shader.
|
||||
static bool smUseChromaticAberrationCorrection;
|
||||
|
||||
// Type of rotation events to broadcast
|
||||
static bool smGenerateAngleAxisRotationEvents;
|
||||
static bool smGenerateEulerRotationEvents;
|
||||
|
|
@ -55,6 +59,9 @@ public:
|
|||
// as measured from a vector pointing straight up (in degrees)
|
||||
static F32 smMaximumAxisAngle;
|
||||
|
||||
// Broadcast sensor raw data: acceleration, angular velocity, magnetometer reading
|
||||
static bool smGenerateSensorRawEvents;
|
||||
|
||||
// Indicates that a whole frame event should be generated and frames
|
||||
// should be buffered.
|
||||
static bool smGenerateWholeFrameEvents;
|
||||
|
|
@ -131,14 +138,24 @@ public:
|
|||
// HMDs
|
||||
U32 getHMDCount() const { return mHMDDevices.size(); }
|
||||
const OculusVRHMDDevice* getHMDDevice(U32 index) const;
|
||||
F32 getHMDCurrentIPD(U32 index);
|
||||
void setHMDCurrentIPD(U32 index, F32 ipd);
|
||||
|
||||
// Sensors
|
||||
U32 getSensorCount() const { return mSensorDevices.size(); }
|
||||
const OculusVRSensorDevice* getSensorDevice(U32 index) const;
|
||||
EulerF getSensorEulerRotation(U32 index);
|
||||
VectorF getSensorAcceleration(U32 index);
|
||||
EulerF getSensorAngularVelocity(U32 index);
|
||||
VectorF getSensorMagnetometer(U32 index);
|
||||
F32 getSensorPredictionTime(U32 index);
|
||||
void setSensorPredictionTime(U32 index, F32 dt);
|
||||
void setAllSensorPredictionTime(F32 dt);
|
||||
bool getSensorGravityCorrection(U32 index);
|
||||
void setSensorGravityCorrection(U32 index, bool state);
|
||||
bool getSensorYawCorrection(U32 index);
|
||||
void setSensorYawCorrection(U32 index, bool state);
|
||||
bool getSensorMagnetometerCalibrated(U32 index);
|
||||
void resetAllSensors();
|
||||
|
||||
public:
|
||||
|
|
|
|||
|
|
@ -58,6 +58,10 @@ void OculusVRHMDDevice::set(OVR::HMDDevice* hmd, OVR::HMDInfo& info, bool calcul
|
|||
mVersion = info.Version;
|
||||
|
||||
mDisplayDeviceName = info.DisplayDeviceName;
|
||||
mDisplayId = info.DisplayId;
|
||||
|
||||
mDesktopPosition.x = info.DesktopX;
|
||||
mDesktopPosition.y = info.DesktopY;
|
||||
|
||||
mResolution.x = info.HResolution;
|
||||
mResolution.y = info.VResolution;
|
||||
|
|
@ -68,13 +72,19 @@ void OculusVRHMDDevice::set(OVR::HMDDevice* hmd, OVR::HMDInfo& info, bool calcul
|
|||
mVerticalEyeCenter = info.VScreenCenter;
|
||||
mEyeToScreen = info.EyeToScreenDistance;
|
||||
mLensSeparation = info.LensSeparationDistance;
|
||||
mInterpupillaryDistance = info.InterpupillaryDistance;
|
||||
mProfileInterpupillaryDistance = info.InterpupillaryDistance;
|
||||
mInterpupillaryDistance = mProfileInterpupillaryDistance;
|
||||
|
||||
mKDistortion.x = info.DistortionK[0];
|
||||
mKDistortion.y = info.DistortionK[1];
|
||||
mKDistortion.z = info.DistortionK[2];
|
||||
mKDistortion.w = info.DistortionK[3];
|
||||
|
||||
mChromaticAbCorrection.x = info.ChromaAbCorrection[0];
|
||||
mChromaticAbCorrection.y = info.ChromaAbCorrection[1];
|
||||
mChromaticAbCorrection.z = info.ChromaAbCorrection[2];
|
||||
mChromaticAbCorrection.w = info.ChromaAbCorrection[3];
|
||||
|
||||
// Calculated values
|
||||
calculateValues(calculateDistortionScale);
|
||||
|
||||
|
|
@ -109,13 +119,27 @@ void OculusVRHMDDevice::createSimulatedPreviewRift(bool calculateDistortionScale
|
|||
mVerticalEyeCenter = 0.046799999f;
|
||||
mEyeToScreen = 0.041000001f;
|
||||
mLensSeparation = 0.064000003f;
|
||||
mInterpupillaryDistance = 0.064000003f;
|
||||
mProfileInterpupillaryDistance = 0.064000003f;
|
||||
mInterpupillaryDistance = mProfileInterpupillaryDistance;
|
||||
|
||||
mKDistortion.x = 1.0000000f;
|
||||
mKDistortion.y = 0.22000000f;
|
||||
mKDistortion.z = 0.23999999f;
|
||||
mKDistortion.w = 0.00000000f;
|
||||
|
||||
mChromaticAbCorrection.x = 0.995999f;
|
||||
mChromaticAbCorrection.y = -0.004f;
|
||||
mChromaticAbCorrection.z = 1.014f;
|
||||
mChromaticAbCorrection.z = 0.0f;
|
||||
|
||||
calculateValues(calculateDistortionScale);
|
||||
}
|
||||
|
||||
void OculusVRHMDDevice::setIPD(F32 ipd, bool calculateDistortionScale)
|
||||
{
|
||||
mInterpupillaryDistance = ipd;
|
||||
|
||||
// Recalculate as some values rely on the IPD
|
||||
calculateValues(calculateDistortionScale);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -54,6 +54,12 @@ protected:
|
|||
// Windows display device name used in EnumDisplaySettings/CreateDC
|
||||
String mDisplayDeviceName;
|
||||
|
||||
// MacOS display ID
|
||||
S32 mDisplayId;
|
||||
|
||||
// Desktop coordinate position of the screen (can be negative; may not be present on all platforms)
|
||||
Point2I mDesktopPosition;
|
||||
|
||||
// Whole screen resolution
|
||||
Point2I mResolution;
|
||||
|
||||
|
|
@ -70,6 +76,9 @@ protected:
|
|||
// Physical distance between lens centers, in meters
|
||||
F32 mLensSeparation;
|
||||
|
||||
// Physical distance between the user's eye centers as defined in the current profile
|
||||
F32 mProfileInterpupillaryDistance;
|
||||
|
||||
// Physical distance between the user's eye centers
|
||||
F32 mInterpupillaryDistance;
|
||||
|
||||
|
|
@ -79,6 +88,9 @@ protected:
|
|||
// Radial distortion correction coefficients used by the barrel distortion shader
|
||||
Point4F mKDistortion;
|
||||
|
||||
// Chromatic aberration correction coefficients
|
||||
Point4F mChromaticAbCorrection;
|
||||
|
||||
// Calculated values of eye x offset from center in normalized (uv) coordinates
|
||||
// where each eye is 0..1. Used for the mono to stereo postFX to simulate an
|
||||
// eye offset of the camera. The x component is the left eye, the y component
|
||||
|
|
@ -137,6 +149,12 @@ public:
|
|||
// Windows display device name used in EnumDisplaySettings/CreateDC
|
||||
const char* getDisplayDeviceName() const { return mDisplayDeviceName.c_str(); }
|
||||
|
||||
// MacOS display ID
|
||||
S32 getDisplayDeviceId() const { return mDisplayId; }
|
||||
|
||||
// Desktop coordinate position of the screen (can be negative; may not be present on all platforms)
|
||||
const Point2I& getDesktopPosition() const { return mDesktopPosition; }
|
||||
|
||||
// Whole screen resolution
|
||||
const Point2I& getResolution() const { return mResolution; }
|
||||
|
||||
|
|
@ -153,15 +171,24 @@ public:
|
|||
// Physical distance between lens centers, in meters
|
||||
F32 getLensSeparation() const { return mLensSeparation; }
|
||||
|
||||
// Physical distance between the user's eye centers as defined by the current profile
|
||||
F32 getProfileIPD() const { return mProfileInterpupillaryDistance; }
|
||||
|
||||
// Physical distance between the user's eye centers
|
||||
F32 getIPD() const { return mInterpupillaryDistance; }
|
||||
|
||||
// Set a new physical distance between the user's eye centers
|
||||
void setIPD(F32 ipd, bool calculateDistortionScale);
|
||||
|
||||
// Provides the IPD of one eye as a Point3F
|
||||
const Point3F& getEyeWorldOffset() const { return mEyeWorldOffset; }
|
||||
|
||||
// Radial distortion correction coefficients used by the barrel distortion shader
|
||||
const Point4F& getKDistortion() const { return mKDistortion; }
|
||||
|
||||
// Chromatic aberration correction coefficients used by the barrel distortion shader
|
||||
const Point4F& getChromaticAbCorrection() const { return mChromaticAbCorrection; }
|
||||
|
||||
// Calculated values of eye x offset from center in normalized (uv) coordinates.
|
||||
const Point2F& getEyeUVOffset() const { return mEyeUVOffset; }
|
||||
|
||||
|
|
|
|||
|
|
@ -56,6 +56,24 @@ void OculusVRSensorData::setData(OVR::SensorFusion& data, const F32& maxAxisRadi
|
|||
// Sensor rotation as axis
|
||||
OculusVRUtil::calculateAxisRotation(mRot, maxAxisRadius, mRotAxis);
|
||||
|
||||
// Sensor raw values
|
||||
OVR::Vector3f accel = data.GetAcceleration();
|
||||
OculusVRUtil::convertAcceleration(accel, mAcceleration);
|
||||
|
||||
OVR::Vector3f angVel = data.GetAngularVelocity();
|
||||
OculusVRUtil::convertAngularVelocity(angVel, mAngVelocity);
|
||||
|
||||
OVR::Vector3f mag;
|
||||
if(data.HasMagCalibration() && data.IsYawCorrectionEnabled())
|
||||
{
|
||||
mag = data.GetCalibratedMagnetometer();
|
||||
}
|
||||
else
|
||||
{
|
||||
mag = data.GetMagnetometer();
|
||||
}
|
||||
OculusVRUtil::convertMagnetometer(mag, mMagnetometer);
|
||||
|
||||
mDataSet = true;
|
||||
}
|
||||
|
||||
|
|
@ -69,6 +87,11 @@ void OculusVRSensorData::simulateData(const F32& maxAxisRadius)
|
|||
// Sensor rotation as axis
|
||||
OculusVRUtil::calculateAxisRotation(mRot, maxAxisRadius, mRotAxis);
|
||||
|
||||
// Sensor raw values
|
||||
mAcceleration.zero();
|
||||
mAngVelocity.zero();
|
||||
mMagnetometer.zero();
|
||||
|
||||
mDataSet = true;
|
||||
}
|
||||
|
||||
|
|
@ -92,5 +115,19 @@ U32 OculusVRSensorData::compare(OculusVRSensorData* other)
|
|||
result |= DIFF_ROTAXISY;
|
||||
}
|
||||
|
||||
// Check raw values
|
||||
if(mAcceleration.x != other->mAcceleration.x || mAcceleration.y != other->mAcceleration.y || mAcceleration.z != other->mAcceleration.z || !mDataSet)
|
||||
{
|
||||
result |= DIFF_ACCEL;
|
||||
}
|
||||
if(mAngVelocity.x != other->mAngVelocity.x || mAngVelocity.y != other->mAngVelocity.y || mAngVelocity.z != other->mAngVelocity.z || !mDataSet)
|
||||
{
|
||||
result |= DIFF_ANGVEL;
|
||||
}
|
||||
if(mMagnetometer.x != other->mMagnetometer.x || mMagnetometer.y != other->mMagnetometer.y || mMagnetometer.z != other->mMagnetometer.z || !mDataSet)
|
||||
{
|
||||
result |= DIFF_MAG;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -36,8 +36,12 @@ struct OculusVRSensorData
|
|||
DIFF_ROT = (1<<0),
|
||||
DIFF_ROTAXISX = (1<<1),
|
||||
DIFF_ROTAXISY = (1<<2),
|
||||
DIFF_ACCEL = (1<<3),
|
||||
DIFF_ANGVEL = (1<<4),
|
||||
DIFF_MAG = (1<<5),
|
||||
|
||||
DIFF_ROTAXIS = (DIFF_ROTAXISX | DIFF_ROTAXISY),
|
||||
DIFF_RAW = (DIFF_ACCEL | DIFF_ANGVEL | DIFF_MAG),
|
||||
};
|
||||
|
||||
bool mDataSet;
|
||||
|
|
@ -50,6 +54,11 @@ struct OculusVRSensorData
|
|||
// Controller rotation as axis x, y
|
||||
Point2F mRotAxis;
|
||||
|
||||
// Raw values
|
||||
VectorF mAcceleration;
|
||||
EulerF mAngVelocity;
|
||||
VectorF mMagnetometer;
|
||||
|
||||
OculusVRSensorData();
|
||||
|
||||
/// Reset the data
|
||||
|
|
|
|||
|
|
@ -29,6 +29,9 @@ U32 OculusVRSensorDevice::OVR_SENSORROT[OculusVRConstants::MaxSensors] = {0};
|
|||
U32 OculusVRSensorDevice::OVR_SENSORROTANG[OculusVRConstants::MaxSensors] = {0};
|
||||
U32 OculusVRSensorDevice::OVR_SENSORROTAXISX[OculusVRConstants::MaxSensors] = {0};
|
||||
U32 OculusVRSensorDevice::OVR_SENSORROTAXISY[OculusVRConstants::MaxSensors] = {0};
|
||||
U32 OculusVRSensorDevice::OVR_SENSORACCELERATION[OculusVRConstants::MaxSensors] = {0};
|
||||
U32 OculusVRSensorDevice::OVR_SENSORANGVEL[OculusVRConstants::MaxSensors] = {0};
|
||||
U32 OculusVRSensorDevice::OVR_SENSORMAGNETOMETER[OculusVRConstants::MaxSensors] = {0};
|
||||
|
||||
OculusVRSensorDevice::OculusVRSensorDevice()
|
||||
{
|
||||
|
|
@ -74,6 +77,7 @@ void OculusVRSensorDevice::set(OVR::SensorDevice* sensor, OVR::SensorInfo& info,
|
|||
|
||||
mDevice = sensor;
|
||||
mSensorFusion.AttachToSensor(sensor);
|
||||
mYawCorrectionDisabled = !mSensorFusion.IsYawCorrectionEnabled();
|
||||
|
||||
// DeviceInfo
|
||||
mProductName = info.ProductName;
|
||||
|
|
@ -110,6 +114,7 @@ void OculusVRSensorDevice::createSimulatedPreviewRift(S32 actionCodeIndex)
|
|||
{
|
||||
mIsValid = false;
|
||||
mIsSimulation = true;
|
||||
mYawCorrectionDisabled = true;
|
||||
|
||||
// DeviceInfo
|
||||
mProductName = "Tracker DK";
|
||||
|
|
@ -145,6 +150,10 @@ void OculusVRSensorDevice::buildCodeTable()
|
|||
|
||||
OVR_SENSORROTAXISX[i] = INPUTMGR->getNextDeviceCode();
|
||||
OVR_SENSORROTAXISY[i] = INPUTMGR->getNextDeviceCode();
|
||||
|
||||
OVR_SENSORACCELERATION[i] = INPUTMGR->getNextDeviceCode();
|
||||
OVR_SENSORANGVEL[i] = INPUTMGR->getNextDeviceCode();
|
||||
OVR_SENSORMAGNETOMETER[i] = INPUTMGR->getNextDeviceCode();
|
||||
}
|
||||
|
||||
// Build out the virtual map
|
||||
|
|
@ -155,16 +164,27 @@ void OculusVRSensorDevice::buildCodeTable()
|
|||
INPUTMGR->addVirtualMap( buffer, SI_ROT, OVR_SENSORROT[i] );
|
||||
|
||||
dSprintf(buffer, 64, "ovr_sensorrotang%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_ROT, OVR_SENSORROTANG[i] );
|
||||
INPUTMGR->addVirtualMap( buffer, SI_POS, OVR_SENSORROTANG[i] );
|
||||
|
||||
dSprintf(buffer, 64, "ovr_sensorrotaxisx%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_AXIS, OVR_SENSORROTAXISX[i] );
|
||||
dSprintf(buffer, 64, "ovr_sensorrotaxisy%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_AXIS, OVR_SENSORROTAXISY[i] );
|
||||
|
||||
dSprintf(buffer, 64, "ovr_sensoracceleration%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_POS, OVR_SENSORACCELERATION[i] );
|
||||
|
||||
dSprintf(buffer, 64, "ovr_sensorangvel%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_POS, OVR_SENSORANGVEL[i] );
|
||||
|
||||
dSprintf(buffer, 64, "ovr_sensormagnetometer%d", i);
|
||||
INPUTMGR->addVirtualMap( buffer, SI_POS, OVR_SENSORMAGNETOMETER[i] );
|
||||
}
|
||||
}
|
||||
|
||||
bool OculusVRSensorDevice::process(U32 deviceType, bool generateRotAsAngAxis, bool generateRotAsEuler, bool generateRotationAsAxisEvents, F32 maxAxisRadius)
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
bool OculusVRSensorDevice::process(U32 deviceType, bool generateRotAsAngAxis, bool generateRotAsEuler, bool generateRotationAsAxisEvents, F32 maxAxisRadius, bool generateRawSensor)
|
||||
{
|
||||
if(!mIsValid)
|
||||
return false;
|
||||
|
|
@ -215,9 +235,32 @@ bool OculusVRSensorDevice::process(U32 deviceType, bool generateRotAsAngAxis, bo
|
|||
INPUTMGR->buildInputEvent(deviceType, OculusVRConstants::DefaultOVRBase, SI_AXIS, OVR_SENSORROTAXISY[mActionCodeIndex], SI_MOVE, currentBuffer->mRotAxis.y);
|
||||
}
|
||||
|
||||
// Raw sensor event
|
||||
if(generateRawSensor && diff & OculusVRSensorData::DIFF_RAW)
|
||||
{
|
||||
if(diff & OculusVRSensorData::DIFF_ACCEL)
|
||||
INPUTMGR->buildInputEvent(deviceType, OculusVRConstants::DefaultOVRBase, SI_POS, OVR_SENSORACCELERATION[mActionCodeIndex], SI_MOVE, currentBuffer->mAcceleration);
|
||||
|
||||
if(diff & OculusVRSensorData::DIFF_ANGVEL)
|
||||
{
|
||||
// Convert angles to degrees
|
||||
VectorF angles;
|
||||
for(U32 i=0; i<3; ++i)
|
||||
{
|
||||
angles[i] = mRadToDeg(currentBuffer->mAngVelocity[i]);
|
||||
}
|
||||
INPUTMGR->buildInputEvent(deviceType, OculusVRConstants::DefaultOVRBase, SI_POS, OVR_SENSORANGVEL[mActionCodeIndex], SI_MOVE, angles);
|
||||
}
|
||||
|
||||
if(diff & OculusVRSensorData::DIFF_MAG)
|
||||
INPUTMGR->buildInputEvent(deviceType, OculusVRConstants::DefaultOVRBase, SI_POS, OVR_SENSORMAGNETOMETER[mActionCodeIndex], SI_MOVE, currentBuffer->mMagnetometer);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
void OculusVRSensorDevice::reset()
|
||||
{
|
||||
if(!mIsValid)
|
||||
|
|
@ -242,6 +285,51 @@ void OculusVRSensorDevice::setPredictionTime(F32 dt)
|
|||
mSensorFusion.SetPrediction(dt);
|
||||
}
|
||||
|
||||
bool OculusVRSensorDevice::getGravityCorrection() const
|
||||
{
|
||||
if(!mIsValid)
|
||||
return false;
|
||||
|
||||
return mSensorFusion.IsGravityEnabled();
|
||||
}
|
||||
|
||||
void OculusVRSensorDevice::setGravityCorrection(bool state)
|
||||
{
|
||||
if(!mIsValid)
|
||||
return;
|
||||
|
||||
mSensorFusion.SetGravityEnabled(state);
|
||||
}
|
||||
|
||||
bool OculusVRSensorDevice::getYawCorrection() const
|
||||
{
|
||||
if(!mIsValid)
|
||||
return false;
|
||||
|
||||
return mSensorFusion.IsYawCorrectionEnabled();
|
||||
}
|
||||
|
||||
void OculusVRSensorDevice::setYawCorrection(bool state)
|
||||
{
|
||||
if(!mIsValid)
|
||||
return;
|
||||
|
||||
if(mYawCorrectionDisabled || !mSensorFusion.HasMagCalibration())
|
||||
return;
|
||||
|
||||
mSensorFusion.SetYawCorrectionEnabled(state);
|
||||
}
|
||||
|
||||
bool OculusVRSensorDevice::getMagnetometerCalibrationAvailable() const
|
||||
{
|
||||
if(!mIsValid)
|
||||
return false;
|
||||
|
||||
return mSensorFusion.HasMagCalibration();
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
EulerF OculusVRSensorDevice::getEulerRotation()
|
||||
{
|
||||
if(!mIsValid)
|
||||
|
|
@ -263,3 +351,82 @@ EulerF OculusVRSensorDevice::getEulerRotation()
|
|||
|
||||
return rot;
|
||||
}
|
||||
|
||||
EulerF OculusVRSensorDevice::getRawEulerRotation()
|
||||
{
|
||||
if(!mIsValid)
|
||||
return Point3F::Zero;
|
||||
|
||||
OVR::Quatf orientation;
|
||||
orientation = mSensorFusion.GetOrientation();
|
||||
|
||||
// Sensor rotation in Euler format
|
||||
EulerF rot;
|
||||
OculusVRUtil::convertRotation(orientation, rot);
|
||||
|
||||
return rot;
|
||||
}
|
||||
|
||||
VectorF OculusVRSensorDevice::getAcceleration()
|
||||
{
|
||||
if(!mIsValid)
|
||||
return VectorF::Zero;
|
||||
|
||||
OVR::Vector3f a = mSensorFusion.GetAcceleration();
|
||||
|
||||
// Sensor acceleration in VectorF format
|
||||
VectorF acceleration;
|
||||
OculusVRUtil::convertAcceleration(a, acceleration);
|
||||
|
||||
return acceleration;
|
||||
}
|
||||
|
||||
EulerF OculusVRSensorDevice::getAngularVelocity()
|
||||
{
|
||||
if(!mIsValid)
|
||||
return EulerF::Zero;
|
||||
|
||||
OVR::Vector3f v = mSensorFusion.GetAngularVelocity();
|
||||
|
||||
// Sensor angular velocity in EulerF format
|
||||
EulerF vel;
|
||||
OculusVRUtil::convertAngularVelocity(v, vel);
|
||||
|
||||
return vel;
|
||||
}
|
||||
|
||||
VectorF OculusVRSensorDevice::getMagnetometer()
|
||||
{
|
||||
if(!mIsValid)
|
||||
return VectorF::Zero;
|
||||
|
||||
OVR::Vector3f m;
|
||||
if(mSensorFusion.HasMagCalibration() && mSensorFusion.IsYawCorrectionEnabled())
|
||||
{
|
||||
m = mSensorFusion.GetCalibratedMagnetometer();
|
||||
}
|
||||
else
|
||||
{
|
||||
m = mSensorFusion.GetMagnetometer();
|
||||
}
|
||||
|
||||
// Sensor magnetometer reading in VectorF format
|
||||
VectorF mag;
|
||||
OculusVRUtil::convertMagnetometer(m, mag);
|
||||
|
||||
return mag;
|
||||
}
|
||||
|
||||
VectorF OculusVRSensorDevice::getRawMagnetometer()
|
||||
{
|
||||
if(!mIsValid)
|
||||
return VectorF::Zero;
|
||||
|
||||
OVR::Vector3f m = mSensorFusion.GetMagnetometer();
|
||||
|
||||
// Sensor magnetometer reading in VectorF format
|
||||
VectorF mag;
|
||||
OculusVRUtil::convertMagnetometer(m, mag);
|
||||
|
||||
return mag;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -50,6 +50,10 @@ public:
|
|||
static U32 OVR_SENSORROTAXISX[OculusVRConstants::MaxSensors]; // SI_AXIS
|
||||
static U32 OVR_SENSORROTAXISY[OculusVRConstants::MaxSensors];
|
||||
|
||||
static U32 OVR_SENSORACCELERATION[OculusVRConstants::MaxSensors]; // SI_POS
|
||||
static U32 OVR_SENSORANGVEL[OculusVRConstants::MaxSensors]; // SI_POS but is EulerF
|
||||
static U32 OVR_SENSORMAGNETOMETER[OculusVRConstants::MaxSensors]; // SI_POS
|
||||
|
||||
protected:
|
||||
bool mIsValid;
|
||||
|
||||
|
|
@ -69,6 +73,9 @@ protected:
|
|||
U16 mProductId;
|
||||
String mSerialNumber;
|
||||
|
||||
// Has yaw correction been disabled by the control panel
|
||||
bool mYawCorrectionDisabled;
|
||||
|
||||
// Assigned by the OculusVRDevice
|
||||
S32 mActionCodeIndex;
|
||||
|
||||
|
|
@ -99,7 +106,7 @@ public:
|
|||
bool isValid() const {return mIsValid;}
|
||||
bool isSimulated() {return mIsSimulation;}
|
||||
|
||||
bool process(U32 deviceType, bool generateRotAsAngAxis, bool generateRotAsEuler, bool generateRotationAsAxisEvents, F32 maxAxisRadius);
|
||||
bool process(U32 deviceType, bool generateRotAsAngAxis, bool generateRotAsEuler, bool generateRotationAsAxisEvents, F32 maxAxisRadius, bool generateRawSensor);
|
||||
|
||||
void reset();
|
||||
|
||||
|
|
@ -109,6 +116,26 @@ public:
|
|||
// Set the prediction time for the sensor fusion. The time is in seconds.
|
||||
void setPredictionTime(F32 dt);
|
||||
|
||||
// Is gravity correction enabled for pitch and roll
|
||||
bool getGravityCorrection() const;
|
||||
|
||||
// Set the pitch and roll gravity correction
|
||||
void setGravityCorrection(bool state);
|
||||
|
||||
// Has yaw correction been disabled using the control panel
|
||||
bool getYawCorrectionUserDisabled() const { return mYawCorrectionDisabled; }
|
||||
|
||||
// Is yaw correction enabled
|
||||
bool getYawCorrection() const;
|
||||
|
||||
// Set the yaw correction. Note: if magnetometer calibration data is not present,
|
||||
// or user has disabled yaw correction in the control panel, this method will
|
||||
// not enable it.
|
||||
void setYawCorrection(bool state);
|
||||
|
||||
// Is magnetometer calibration data available for this sensor
|
||||
bool getMagnetometerCalibrationAvailable() const;
|
||||
|
||||
const char* getProductName() { return mProductName.c_str(); }
|
||||
const char* getManufacturer() { return mManufacturer.c_str(); }
|
||||
U32 getVersion() { return mVersion; }
|
||||
|
|
@ -116,7 +143,24 @@ public:
|
|||
U16 getProductId() { return mProductId; }
|
||||
const char* getSerialNumber() { return mSerialNumber; }
|
||||
|
||||
// Get the current rotation of the sensor. Uses prediction if set.
|
||||
EulerF getEulerRotation();
|
||||
|
||||
// Get the current rotation of the sensor.
|
||||
EulerF getRawEulerRotation();
|
||||
|
||||
// Get the current absolute acceleration reading, in m/s^2
|
||||
VectorF getAcceleration();
|
||||
|
||||
// Get the current angular velocity reading, in rad/s
|
||||
EulerF getAngularVelocity();
|
||||
|
||||
// Get the current magnetometer reading (direction and field strength), in Gauss.
|
||||
// Uses magnetometer calibration if set.
|
||||
VectorF getMagnetometer();
|
||||
|
||||
// Get the current raw magnetometer reading (direction and field strength), in Gauss
|
||||
VectorF getRawMagnetometer();
|
||||
};
|
||||
|
||||
#endif // _OCULUSVRSENSORDEVICE_H_
|
||||
|
|
|
|||
|
|
@ -73,4 +73,19 @@ void calculateAxisRotation(const MatrixF& inRotation, const F32& maxAxisRadius,
|
|||
outRotation.y = axis.y;
|
||||
}
|
||||
|
||||
}
|
||||
void convertAcceleration(OVR::Vector3f& inAcceleration, VectorF& outAcceleration)
|
||||
{
|
||||
outAcceleration.set(inAcceleration.x, -inAcceleration.z, inAcceleration.y);
|
||||
}
|
||||
|
||||
void convertAngularVelocity(OVR::Vector3f& inAngVel, EulerF& outAngVel)
|
||||
{
|
||||
outAngVel.set(-inAngVel.x, inAngVel.z, -inAngVel.y);
|
||||
}
|
||||
|
||||
void convertMagnetometer(OVR::Vector3f& inMagnetometer, VectorF& outMagnetometer)
|
||||
{
|
||||
outMagnetometer.set(inMagnetometer.x, -inMagnetometer.z, inMagnetometer.y);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -37,6 +37,15 @@ namespace OculusVRUtil
|
|||
|
||||
/// Calcualte a sensor's rotation as if it were a thumb stick axis
|
||||
void calculateAxisRotation(const MatrixF& inRotation, const F32& maxAxisRadius, Point2F& outRotation);
|
||||
|
||||
/// Convert an OVR sensor's acceleration to Torque 3D vector (in m/s^2)
|
||||
void convertAcceleration(OVR::Vector3f& inAcceleration, VectorF& outAcceleration);
|
||||
|
||||
/// Convert OVR sensor's angular velocity to Torque 3D Euler angles (in radians/s)
|
||||
void convertAngularVelocity(OVR::Vector3f& inAngVel, EulerF& outAngVel);
|
||||
|
||||
/// Convert an OVR sensor's magnetometer reading (direction and field strength) to Torque 3D vector (in Gauss)
|
||||
void convertMagnetometer(OVR::Vector3f& inMagnetometer, VectorF& outMagnetometer);
|
||||
}
|
||||
|
||||
#endif // _OCULUSVRUTIL_H_
|
||||
|
|
|
|||
|
|
@ -63,7 +63,14 @@ function enableOculusVRDisplay(%gameConnection, %trueStereoRendering)
|
|||
|
||||
if(%trueStereoRendering)
|
||||
{
|
||||
OVRBarrelDistortionPostFX.isEnabled = true;
|
||||
if($pref::OculusVR::UseChromaticAberrationCorrection)
|
||||
{
|
||||
OVRBarrelDistortionChromaPostFX.isEnabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
OVRBarrelDistortionPostFX.isEnabled = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
@ -81,6 +88,7 @@ function disableOculusVRDisplay(%gameConnection)
|
|||
%gameConnection.clearDisplayDevice();
|
||||
PlayGui.renderStyle = "standard";
|
||||
OVRBarrelDistortionPostFX.isEnabled = false;
|
||||
OVRBarrelDistortionChromaPostFX.isEnabled = false;
|
||||
OVRBarrelDistortionMonoPostFX.isEnabled = false;
|
||||
}
|
||||
|
||||
|
|
@ -112,7 +120,7 @@ function setStandardOculusVRControlScheme(%gameConnection)
|
|||
function setVideoModeForOculusVRDisplay(%fullscreen)
|
||||
{
|
||||
%res = getOVRHMDResolution(0);
|
||||
Canvas.setVideoMode(%res.x, %res.y, %fullscreen, 32, 0);
|
||||
Canvas.setVideoMode(%res.x, %res.y, %fullscreen, 32, 4);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
|
|
|||
|
|
@ -44,6 +44,14 @@ singleton ShaderData( OVRBarrelDistortionShader )
|
|||
pixVersion = 2.0;
|
||||
};
|
||||
|
||||
singleton ShaderData( OVRBarrelDistortionChromaShader )
|
||||
{
|
||||
DXVertexShaderFile = "shaders/common/postFx/postFxV.hlsl";
|
||||
DXPixelShaderFile = "shaders/common/postFx/oculusvr/barrelDistortionChromaP.hlsl";
|
||||
|
||||
pixVersion = 2.0;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// GFX state blocks
|
||||
//-----------------------------------------------------------------------------
|
||||
|
|
@ -78,6 +86,32 @@ singleton BarrelDistortionPostEffect( OVRBarrelDistortionPostFX )
|
|||
scaleOutput = 1.25;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Barrel Distortion with Chromatic Aberration Correction PostFx
|
||||
//
|
||||
// To be used with the Oculus Rift.
|
||||
// Expects a stereo pair to exist on the back buffer and then applies the
|
||||
// appropriate barrel distortion.
|
||||
// This version applies a chromatic aberration correction during the
|
||||
// barrel distortion.
|
||||
//-----------------------------------------------------------------------------
|
||||
singleton BarrelDistortionPostEffect( OVRBarrelDistortionChromaPostFX )
|
||||
{
|
||||
isEnabled = false;
|
||||
allowReflectPass = false;
|
||||
|
||||
renderTime = "PFXAfterDiffuse";
|
||||
renderPriority = 100;
|
||||
|
||||
// The barrel distortion
|
||||
shader = OVRBarrelDistortionChromaShader;
|
||||
stateBlock = OVRBarrelDistortionStateBlock;
|
||||
|
||||
texture[0] = "$backBuffer";
|
||||
|
||||
scaleOutput = 1.25;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Barrel Distortion Mono PostFx
|
||||
//
|
||||
|
|
|
|||
|
|
@ -0,0 +1,95 @@
|
|||
//-----------------------------------------------------------------------------
|
||||
// Copyright (c) 2012 GarageGames, LLC
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to
|
||||
// deal in the Software without restriction, including without limitation the
|
||||
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||
// sell copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||
// IN THE SOFTWARE.
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
#include "shadergen:/autogenConditioners.h"
|
||||
#include "../postFx.hlsl"
|
||||
#include "../../torque.hlsl"
|
||||
|
||||
uniform sampler2D backBuffer : register(S0);
|
||||
|
||||
uniform float3 LensCenter; // x=Left X, y=Right X, z=Y
|
||||
uniform float2 ScreenCenter;
|
||||
uniform float2 Scale;
|
||||
uniform float2 ScaleIn;
|
||||
uniform float4 HmdWarpParam;
|
||||
uniform float4 HmdChromaAbParam; // Chromatic aberration correction
|
||||
|
||||
float4 main( PFXVertToPix IN ) : COLOR0
|
||||
{
|
||||
float2 texCoord;
|
||||
float xOffset;
|
||||
float2 lensCenter;
|
||||
lensCenter.y = LensCenter.z;
|
||||
if(IN.uv0.x < 0.5)
|
||||
{
|
||||
texCoord.x = IN.uv0.x;
|
||||
texCoord.y = IN.uv0.y;
|
||||
xOffset = 0.0;
|
||||
lensCenter.x = LensCenter.x;
|
||||
}
|
||||
else
|
||||
{
|
||||
texCoord.x = IN.uv0.x - 0.5;
|
||||
texCoord.y = IN.uv0.y;
|
||||
xOffset = 0.5;
|
||||
lensCenter.x = LensCenter.y;
|
||||
}
|
||||
|
||||
// Scales input texture coordinates for distortion.
|
||||
// ScaleIn maps texture coordinates to Scales to ([-1, 1]), although top/bottom will be
|
||||
// larger due to aspect ratio.
|
||||
float2 theta = (texCoord - lensCenter) * ScaleIn; // Scales to [-1, 1]
|
||||
float rSq = theta.x * theta.x + theta.y * theta.y;
|
||||
float2 theta1 = theta * (HmdWarpParam.x + HmdWarpParam.y * rSq + HmdWarpParam.z * rSq * rSq + HmdWarpParam.w * rSq * rSq * rSq);
|
||||
|
||||
// Detect whether blue texture coordinates are out of range
|
||||
// since these will scaled out the furthest.
|
||||
float2 thetaBlue = theta1 * (HmdChromaAbParam.z + HmdChromaAbParam.w * rSq);
|
||||
float2 tcBlue = lensCenter + Scale * thetaBlue;
|
||||
|
||||
float4 color;
|
||||
if (any(clamp(tcBlue, ScreenCenter-float2(0.25,0.5), ScreenCenter+float2(0.25, 0.5)) - tcBlue))
|
||||
{
|
||||
color = float4(0,0,0,0);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Now do blue texture lookup.
|
||||
tcBlue.x += xOffset;
|
||||
float blue = tex2D(backBuffer, tcBlue).b;
|
||||
|
||||
// Do green lookup (no scaling).
|
||||
float2 tcGreen = lensCenter + Scale * theta1;
|
||||
tcGreen.x += xOffset;
|
||||
float green = tex2D(backBuffer, tcGreen).g;
|
||||
|
||||
// Do red scale and lookup.
|
||||
float2 thetaRed = theta1 * (HmdChromaAbParam.x + HmdChromaAbParam.y * rSq);
|
||||
float2 tcRed = lensCenter + Scale * thetaRed;
|
||||
tcRed.x += xOffset;
|
||||
float red = tex2D(backBuffer, tcRed).r;
|
||||
|
||||
color = float4(red, green, blue, 1);
|
||||
}
|
||||
|
||||
return color;
|
||||
}
|
||||
|
|
@ -63,7 +63,14 @@ function enableOculusVRDisplay(%gameConnection, %trueStereoRendering)
|
|||
|
||||
if(%trueStereoRendering)
|
||||
{
|
||||
OVRBarrelDistortionPostFX.isEnabled = true;
|
||||
if($pref::OculusVR::UseChromaticAberrationCorrection)
|
||||
{
|
||||
OVRBarrelDistortionChromaPostFX.isEnabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
OVRBarrelDistortionPostFX.isEnabled = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
@ -81,6 +88,7 @@ function disableOculusVRDisplay(%gameConnection)
|
|||
%gameConnection.clearDisplayDevice();
|
||||
PlayGui.renderStyle = "standard";
|
||||
OVRBarrelDistortionPostFX.isEnabled = false;
|
||||
OVRBarrelDistortionChromaPostFX.isEnabled = false;
|
||||
OVRBarrelDistortionMonoPostFX.isEnabled = false;
|
||||
}
|
||||
|
||||
|
|
@ -112,7 +120,7 @@ function setStandardOculusVRControlScheme(%gameConnection)
|
|||
function setVideoModeForOculusVRDisplay(%fullscreen)
|
||||
{
|
||||
%res = getOVRHMDResolution(0);
|
||||
Canvas.setVideoMode(%res.x, %res.y, %fullscreen, 32, 0);
|
||||
Canvas.setVideoMode(%res.x, %res.y, %fullscreen, 32, 4);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
|
|
|||
|
|
@ -44,6 +44,14 @@ singleton ShaderData( OVRBarrelDistortionShader )
|
|||
pixVersion = 2.0;
|
||||
};
|
||||
|
||||
singleton ShaderData( OVRBarrelDistortionChromaShader )
|
||||
{
|
||||
DXVertexShaderFile = "shaders/common/postFx/postFxV.hlsl";
|
||||
DXPixelShaderFile = "shaders/common/postFx/oculusvr/barrelDistortionChromaP.hlsl";
|
||||
|
||||
pixVersion = 2.0;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// GFX state blocks
|
||||
//-----------------------------------------------------------------------------
|
||||
|
|
@ -78,6 +86,32 @@ singleton BarrelDistortionPostEffect( OVRBarrelDistortionPostFX )
|
|||
scaleOutput = 1.25;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Barrel Distortion with Chromatic Aberration Correction PostFx
|
||||
//
|
||||
// To be used with the Oculus Rift.
|
||||
// Expects a stereo pair to exist on the back buffer and then applies the
|
||||
// appropriate barrel distortion.
|
||||
// This version applies a chromatic aberration correction during the
|
||||
// barrel distortion.
|
||||
//-----------------------------------------------------------------------------
|
||||
singleton BarrelDistortionPostEffect( OVRBarrelDistortionChromaPostFX )
|
||||
{
|
||||
isEnabled = false;
|
||||
allowReflectPass = false;
|
||||
|
||||
renderTime = "PFXAfterDiffuse";
|
||||
renderPriority = 100;
|
||||
|
||||
// The barrel distortion
|
||||
shader = OVRBarrelDistortionChromaShader;
|
||||
stateBlock = OVRBarrelDistortionStateBlock;
|
||||
|
||||
texture[0] = "$backBuffer";
|
||||
|
||||
scaleOutput = 1.25;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Barrel Distortion Mono PostFx
|
||||
//
|
||||
|
|
|
|||
|
|
@ -0,0 +1,95 @@
|
|||
//-----------------------------------------------------------------------------
|
||||
// Copyright (c) 2012 GarageGames, LLC
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to
|
||||
// deal in the Software without restriction, including without limitation the
|
||||
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||
// sell copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
||||
// IN THE SOFTWARE.
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
#include "shadergen:/autogenConditioners.h"
|
||||
#include "../postFx.hlsl"
|
||||
#include "../../torque.hlsl"
|
||||
|
||||
uniform sampler2D backBuffer : register(S0);
|
||||
|
||||
uniform float3 LensCenter; // x=Left X, y=Right X, z=Y
|
||||
uniform float2 ScreenCenter;
|
||||
uniform float2 Scale;
|
||||
uniform float2 ScaleIn;
|
||||
uniform float4 HmdWarpParam;
|
||||
uniform float4 HmdChromaAbParam; // Chromatic aberration correction
|
||||
|
||||
float4 main( PFXVertToPix IN ) : COLOR0
|
||||
{
|
||||
float2 texCoord;
|
||||
float xOffset;
|
||||
float2 lensCenter;
|
||||
lensCenter.y = LensCenter.z;
|
||||
if(IN.uv0.x < 0.5)
|
||||
{
|
||||
texCoord.x = IN.uv0.x;
|
||||
texCoord.y = IN.uv0.y;
|
||||
xOffset = 0.0;
|
||||
lensCenter.x = LensCenter.x;
|
||||
}
|
||||
else
|
||||
{
|
||||
texCoord.x = IN.uv0.x - 0.5;
|
||||
texCoord.y = IN.uv0.y;
|
||||
xOffset = 0.5;
|
||||
lensCenter.x = LensCenter.y;
|
||||
}
|
||||
|
||||
// Scales input texture coordinates for distortion.
|
||||
// ScaleIn maps texture coordinates to Scales to ([-1, 1]), although top/bottom will be
|
||||
// larger due to aspect ratio.
|
||||
float2 theta = (texCoord - lensCenter) * ScaleIn; // Scales to [-1, 1]
|
||||
float rSq = theta.x * theta.x + theta.y * theta.y;
|
||||
float2 theta1 = theta * (HmdWarpParam.x + HmdWarpParam.y * rSq + HmdWarpParam.z * rSq * rSq + HmdWarpParam.w * rSq * rSq * rSq);
|
||||
|
||||
// Detect whether blue texture coordinates are out of range
|
||||
// since these will scaled out the furthest.
|
||||
float2 thetaBlue = theta1 * (HmdChromaAbParam.z + HmdChromaAbParam.w * rSq);
|
||||
float2 tcBlue = lensCenter + Scale * thetaBlue;
|
||||
|
||||
float4 color;
|
||||
if (any(clamp(tcBlue, ScreenCenter-float2(0.25,0.5), ScreenCenter+float2(0.25, 0.5)) - tcBlue))
|
||||
{
|
||||
color = float4(0,0,0,0);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Now do blue texture lookup.
|
||||
tcBlue.x += xOffset;
|
||||
float blue = tex2D(backBuffer, tcBlue).b;
|
||||
|
||||
// Do green lookup (no scaling).
|
||||
float2 tcGreen = lensCenter + Scale * theta1;
|
||||
tcGreen.x += xOffset;
|
||||
float green = tex2D(backBuffer, tcGreen).g;
|
||||
|
||||
// Do red scale and lookup.
|
||||
float2 thetaRed = theta1 * (HmdChromaAbParam.x + HmdChromaAbParam.y * rSq);
|
||||
float2 tcRed = lensCenter + Scale * thetaRed;
|
||||
tcRed.x += xOffset;
|
||||
float red = tex2D(backBuffer, tcRed).r;
|
||||
|
||||
color = float4(red, green, blue, 1);
|
||||
}
|
||||
|
||||
return color;
|
||||
}
|
||||
Loading…
Reference in a new issue