Create stereo render target, see #43
This commit is contained in:
parent
fcd9344ad5
commit
6b33f0c5b8
5 changed files with 180 additions and 10 deletions
|
@ -92,7 +92,7 @@ public:
|
|||
virtual ~IStereoDisplay();
|
||||
|
||||
/// Sets driver and generates necessary render targets
|
||||
virtual void setDriver(NL3D::UDriver &driver) = 0;
|
||||
virtual void setDriver(NL3D::UDriver *driver) = 0;
|
||||
|
||||
/// Gets the required screen resolution for this device
|
||||
virtual void getScreenResolution(uint &width, uint &height) = 0;
|
||||
|
@ -124,7 +124,7 @@ public:
|
|||
/// Returns non-NULL if a new render target was set
|
||||
virtual UTexture *beginRenderTarget(bool set) = 0;
|
||||
/// Returns true if a render target was fully drawn
|
||||
virtual bool endRenderTarget(bool render) = 0;
|
||||
virtual bool endRenderTarget(bool unset) = 0;
|
||||
|
||||
static const char *getLibraryName(CStereoDeviceInfo::TStereoDeviceLibrary library);
|
||||
static void listDevices(std::vector<CStereoDeviceInfo> &devicesOut);
|
||||
|
|
|
@ -49,14 +49,18 @@
|
|||
|
||||
// NeL includes
|
||||
#include <nel/misc/smart_ptr.h>
|
||||
#include <nel/misc/geom_ext.h>
|
||||
|
||||
// Project includes
|
||||
#include <nel/3d/stereo_hmd.h>
|
||||
#include <nel/3d/frustum.h>
|
||||
#include <nel/3d/viewport.h>
|
||||
#include <nel/3d/u_material.h>
|
||||
|
||||
namespace NL3D {
|
||||
|
||||
class ITexture;
|
||||
class CTextureUser;
|
||||
class CStereoOVRDevicePtr;
|
||||
class CStereoOVRDeviceHandle;
|
||||
|
||||
|
@ -75,7 +79,7 @@ public:
|
|||
virtual ~CStereoOVR();
|
||||
|
||||
/// Sets driver and generates necessary render targets
|
||||
virtual void setDriver(NL3D::UDriver &driver);
|
||||
virtual void setDriver(NL3D::UDriver *driver);
|
||||
|
||||
/// Gets the required screen resolution for this device
|
||||
virtual void getScreenResolution(uint &width, uint &height);
|
||||
|
@ -107,7 +111,7 @@ public:
|
|||
/// Returns non-NULL if a new render target was set, always NULL if not using render targets
|
||||
virtual UTexture *beginRenderTarget(bool set);
|
||||
/// Returns true if a render target was fully drawn, always false if not using render targets
|
||||
virtual bool endRenderTarget(bool render);
|
||||
virtual bool endRenderTarget(bool unset);
|
||||
|
||||
|
||||
/// Get the HMD orientation
|
||||
|
@ -138,6 +142,11 @@ private:
|
|||
CMatrix m_CameraMatrix[NL_STEREO_MAX_USER_CAMERAS];
|
||||
mutable bool m_OrientationCached;
|
||||
mutable NLMISC::CQuat m_OrientationCache;
|
||||
UDriver *m_Driver;
|
||||
NLMISC::CSmartPtr<NL3D::ITexture> m_BarrelTex;
|
||||
NL3D::CTextureUser *m_BarrelTexU;
|
||||
NL3D::UMaterial m_BarrelMat;
|
||||
NLMISC::CQuadUV m_BarrelQuad;
|
||||
|
||||
}; /* class CStereoOVR */
|
||||
|
||||
|
|
|
@ -692,6 +692,7 @@ SOURCE_GROUP(Stereo FILES
|
|||
stereo_hmd.cpp
|
||||
../../include/nel/3d/stereo_hmd.h
|
||||
stereo_ovr.cpp
|
||||
stereo_ovr_fp.cpp
|
||||
../../include/nel/3d/stereo_ovr.h)
|
||||
|
||||
NL_TARGET_LIB(nel3d ${HEADERS} ${SRC})
|
||||
|
|
|
@ -53,6 +53,12 @@
|
|||
// NeL includes
|
||||
// #include <nel/misc/debug.h>
|
||||
#include <nel/3d/u_camera.h>
|
||||
#include <nel/3d/u_driver.h>
|
||||
#include <nel/3d/material.h>
|
||||
#include <nel/3d/texture_bloom.h>
|
||||
#include <nel/3d/texture_user.h>
|
||||
#include <nel/3d/driver_user.h>
|
||||
#include <nel/3d/u_texture.h>
|
||||
|
||||
// Project includes
|
||||
|
||||
|
@ -61,6 +67,8 @@ using namespace std;
|
|||
|
||||
namespace NL3D {
|
||||
|
||||
extern const char *g_StereoOVR_arbfp1;
|
||||
|
||||
namespace {
|
||||
|
||||
class CStereoOVRLog : public OVR::Log
|
||||
|
@ -155,7 +163,7 @@ public:
|
|||
OVR::HMDInfo HMDInfo;
|
||||
};
|
||||
|
||||
CStereoOVR::CStereoOVR(const CStereoOVRDeviceHandle *handle) : m_Stage(0), m_SubStage(0), m_OrientationCached(false)
|
||||
CStereoOVR::CStereoOVR(const CStereoOVRDeviceHandle *handle) : m_Stage(0), m_SubStage(0), m_OrientationCached(false), m_BarrelTexU(NULL)
|
||||
{
|
||||
++s_DeviceCounter;
|
||||
m_DevicePtr = new CStereoOVRDevicePtr();
|
||||
|
@ -194,6 +202,17 @@ CStereoOVR::CStereoOVR(const CStereoOVRDeviceHandle *handle) : m_Stage(0), m_Sub
|
|||
|
||||
CStereoOVR::~CStereoOVR()
|
||||
{
|
||||
if (!m_BarrelMat.empty())
|
||||
{
|
||||
m_BarrelMat.getObjectPtr()->setTexture(0, NULL);
|
||||
m_Driver->deleteMaterial(m_BarrelMat);
|
||||
}
|
||||
delete m_BarrelTexU;
|
||||
m_BarrelTexU = NULL;
|
||||
m_BarrelTex = NULL; // CSmartPtr
|
||||
|
||||
m_Driver = NULL;
|
||||
|
||||
if (m_DevicePtr->SensorDevice)
|
||||
m_DevicePtr->SensorDevice->Release();
|
||||
m_DevicePtr->SensorDevice.Clear();
|
||||
|
@ -206,9 +225,51 @@ CStereoOVR::~CStereoOVR()
|
|||
--s_DeviceCounter;
|
||||
}
|
||||
|
||||
void CStereoOVR::setDriver(NL3D::UDriver &driver)
|
||||
void CStereoOVR::setDriver(NL3D::UDriver *driver)
|
||||
{
|
||||
// ...
|
||||
m_Driver = driver;
|
||||
// Do not allow weird stuff.
|
||||
uint32 width, height;
|
||||
driver->getWindowSize(width, height);
|
||||
nlassert(width == m_DevicePtr->HMDInfo.HResolution);
|
||||
nlassert(height == m_DevicePtr->HMDInfo.VResolution);
|
||||
|
||||
NL3D::IDriver *drvInternal = (static_cast<CDriverUser *>(driver))->getDriver();
|
||||
|
||||
m_BarrelTex = new CTextureBloom(); // lol bloom
|
||||
m_BarrelTex->setReleasable(false);
|
||||
m_BarrelTex->resize(width, height);
|
||||
m_BarrelTex->setFilterMode(ITexture::Linear, ITexture::LinearMipMapOff);
|
||||
m_BarrelTex->setWrapS(ITexture::Clamp);
|
||||
m_BarrelTex->setWrapT(ITexture::Clamp);
|
||||
m_BarrelTex->setRenderTarget(true);
|
||||
drvInternal->setupTexture(*m_BarrelTex);
|
||||
m_BarrelTexU = new CTextureUser(m_BarrelTex);
|
||||
|
||||
m_BarrelMat = m_Driver->createMaterial();
|
||||
NL3D::CMaterial *barrelMat = m_BarrelMat.getObjectPtr();
|
||||
m_BarrelMat.initUnlit();
|
||||
m_BarrelMat.setColor(CRGBA::White);
|
||||
m_BarrelMat.setBlend (false);
|
||||
m_BarrelMat.setAlphaTest (false);
|
||||
barrelMat->setBlendFunc(CMaterial::one, CMaterial::zero);
|
||||
barrelMat->setZWrite(false);
|
||||
barrelMat->setZFunc(CMaterial::always);
|
||||
barrelMat->setDoubleSided(true);
|
||||
barrelMat->setTexture(0, m_BarrelTex);
|
||||
|
||||
m_BarrelQuad.V0 = CVector(0.f, 0.f, 0.5f);
|
||||
m_BarrelQuad.V1 = CVector(1.f, 0.f, 0.5f);
|
||||
m_BarrelQuad.V2 = CVector(1.f, 1.f, 0.5f);
|
||||
m_BarrelQuad.V3 = CVector(0.f, 1.f, 0.5f);
|
||||
|
||||
float newU = drvInternal->isTextureRectangle(m_BarrelTex) ? (float)width : 1.f;
|
||||
float newV = drvInternal->isTextureRectangle(m_BarrelTex) ? (float)height : 1.f;
|
||||
|
||||
m_BarrelQuad.Uv0 = CUV(0.f, 0.f);
|
||||
m_BarrelQuad.Uv1 = CUV(newU, 0.f);
|
||||
m_BarrelQuad.Uv2 = CUV(newU, newV);
|
||||
m_BarrelQuad.Uv3 = CUV(0.f, newV);
|
||||
}
|
||||
|
||||
void CStereoOVR::getScreenResolution(uint &width, uint &height)
|
||||
|
@ -391,15 +452,32 @@ bool CStereoOVR::wantInterface2D()
|
|||
UTexture *CStereoOVR::beginRenderTarget(bool set)
|
||||
{
|
||||
// render target always set before driver clear
|
||||
nlassert(m_SubStage == 1);
|
||||
// nlassert(m_SubStage <= 1);
|
||||
if (m_Stage == 1)
|
||||
{
|
||||
if (set)
|
||||
{
|
||||
(static_cast<CDriverUser *>(m_Driver))->setRenderTarget(*m_BarrelTexU, 0, 0, 0, 0);
|
||||
}
|
||||
return m_BarrelTexU;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/// Returns true if a render target was fully drawn
|
||||
bool CStereoOVR::endRenderTarget( bool render)
|
||||
bool CStereoOVR::endRenderTarget(bool unset)
|
||||
{
|
||||
// after rendering of course
|
||||
nlassert(m_SubStage > 1);
|
||||
// nlassert(m_SubStage > 1);
|
||||
if (m_Stage == 4)
|
||||
{
|
||||
if (unset)
|
||||
{
|
||||
CTextureUser cu;
|
||||
(static_cast<CDriverUser *>(m_Driver))->setRenderTarget(cu);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
82
code/nel/src/3d/stereo_ovr_fp.cpp
Normal file
82
code/nel/src/3d/stereo_ovr_fp.cpp
Normal file
|
@ -0,0 +1,82 @@
|
|||
/************************************************************************************
|
||||
|
||||
Filename : stereo_ovf_fp.cpp
|
||||
Content : Barrel fragment program compiled to a blob of assembly
|
||||
Created : July 01, 2013
|
||||
|
||||
Copyright : Copyright 2012 Oculus VR, Inc. All Rights reserved.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
|
||||
************************************************************************************/
|
||||
|
||||
namespace NL3D {
|
||||
const char *g_StereoOVR_arbfp1 =
|
||||
"!!ARBfp1.0\n"
|
||||
//# cgc version 3.1.0013, build date Apr 18 2012
|
||||
//# command line args: -profile arbfp1
|
||||
//# source file: pp_oculus_vr.cg
|
||||
//#vendor NVIDIA Corporation
|
||||
//#version 3.1.0.13
|
||||
//#profile arbfp1
|
||||
//#program pp_oculus_vr
|
||||
//#semantic pp_oculus_vr.cLensCenter
|
||||
//#semantic pp_oculus_vr.cScreenCenter
|
||||
//#semantic pp_oculus_vr.cScale
|
||||
//#semantic pp_oculus_vr.cScaleIn
|
||||
//#semantic pp_oculus_vr.cHmdWarpParam
|
||||
//#semantic pp_oculus_vr.cTex0 : TEX0
|
||||
//#var float2 texCoord : $vin.TEXCOORD0 : TEX0 : 0 : 1
|
||||
//#var float2 cLensCenter : : c[0] : 1 : 1
|
||||
//#var float2 cScreenCenter : : c[1] : 2 : 1
|
||||
//#var float2 cScale : : c[2] : 3 : 1
|
||||
//#var float2 cScaleIn : : c[3] : 4 : 1
|
||||
//#var float4 cHmdWarpParam : : c[4] : 5 : 1
|
||||
//#var sampler2D cTex0 : TEX0 : texunit 0 : 6 : 1
|
||||
//#var float4 oCol : $vout.COLOR : COL : 7 : 1
|
||||
//#const c[5] = 0.25 0.5 0 1
|
||||
"PARAM c[6] = { program.local[0..4],\n"
|
||||
" { 0.25, 0.5, 0, 1 } };\n"
|
||||
"TEMP R0;\n"
|
||||
"TEMP R1;\n"
|
||||
"ADD R0.xy, fragment.texcoord[0], -c[0];\n"
|
||||
"MUL R0.xy, R0, c[3];\n"
|
||||
"MUL R0.z, R0.y, R0.y;\n"
|
||||
"MAD R0.z, R0.x, R0.x, R0;\n"
|
||||
"MUL R0.w, R0.z, c[4];\n"
|
||||
"MUL R0.w, R0, R0.z;\n"
|
||||
"MAD R1.y, R0.z, c[4], c[4].x;\n"
|
||||
"MUL R1.x, R0.z, c[4].z;\n"
|
||||
"MAD R1.x, R0.z, R1, R1.y;\n"
|
||||
"MAD R0.z, R0.w, R0, R1.x;\n"
|
||||
"MUL R0.xy, R0, R0.z;\n"
|
||||
"MOV R0.zw, c[5].xyxy;\n"
|
||||
"ADD R1.xy, R0.zwzw, c[1];\n"
|
||||
"MUL R0.xy, R0, c[2];\n"
|
||||
"ADD R0.xy, R0, c[0];\n"
|
||||
"MIN R1.xy, R1, R0;\n"
|
||||
"ADD R0.zw, -R0, c[1].xyxy;\n"
|
||||
"MAX R0.zw, R0, R1.xyxy;\n"
|
||||
"ADD R0.zw, R0, -R0.xyxy;\n"
|
||||
"ABS R0.zw, R0;\n"
|
||||
"CMP R0.zw, -R0, c[5].z, c[5].w;\n"
|
||||
"MUL R0.z, R0, R0.w;\n"
|
||||
"ABS R0.z, R0;\n"
|
||||
"CMP R0.z, -R0, c[5], c[5].w;\n"
|
||||
"ABS R1.x, R0.z;\n"
|
||||
"TEX R0, R0, texture[0], 2D;\n"
|
||||
"CMP R1.x, -R1, c[5].z, c[5].w;\n"
|
||||
"CMP result.color, -R1.x, R0, c[5].z;\n"
|
||||
"END\n";
|
||||
//# 28 instructions, 2 R-regs
|
||||
}
|
Loading…
Reference in a new issue