Dear Robert, I think the fusion distance is not the distance between left and right eyes but is the distance from the center of two eyes to the sight convergence point.
The effect I looking for is that the scene and the prerender textures both have
stereo effect.
The current codes are:
[code]#include "stdafx.h"
#include <osg/Geometry>
#include <osg/MatrixTransform>
#include <osg/Texture2D>
#include <osgDB/ReadFile>
#include <osgDB/FileUtils>
#include <osgViewer/Viewer>
#include <osgGA/TrackballManipulator>
bool loadShaderSource(osg::Shader* obj, const std::string& fileName )
{
std::string fqFileName = osgDB::findDataFile(fileName);
if( fqFileName.length() != 0 )
{
obj->loadShaderSourceFromFile( fqFileName.c_str());
return true;
}
return false;
}
struct RflCameraCallback : public osg::NodeCallback
{
public:
RflCameraCallback(osg::Camera* mCamera):_mCamera(mCamera){}
virtual void operator()(osg::Node* node, osg::NodeVisitor* nv)
{
osg::Camera* rCamera = dynamic_cast<osg::Camera*> (node);
osg::Matrix projectMatrix;
projectMatrix = _mCamera->getProjectionMatrix();
rCamera->setProjectionMatrix(projectMatrix);
osg::Vec3 eye, center, up;
_mCamera->getViewMatrixAsLookAt(eye, center, up);
rCamera->setViewMatrixAsLookAt(eye, center, up);
traverse(node, nv);
}
osg::Camera* _mCamera;
};
osg::Geometry* createRegularSeaSurface()
{
osg::Geometry* seaGeom = new osg::Geometry;
seaGeom->setSupportsDisplayList(false);
osg::Vec3Array* vertices = new osg::Vec3Array; //坐标顶点指针
osg::UIntArray* indeces = new osg::UIntArray; //坐标顶点索引指针
seaGeom->setVertexArray( vertices);
vertices->push_back(osg::Vec3(-40.0, -40.0, 0.0));
vertices->push_back(osg::Vec3(40.0, -40.0, 0.0));
vertices->push_back(osg::Vec3(40.0, 40.0, 0.0));
vertices->push_back(osg::Vec3(-40.0, 40.0, 0.0));
osg::Vec4Array* colors = new osg::Vec4Array;
seaGeom->setColorArray( colors );
seaGeom->setColorBinding( osg::Geometry::BIND_OVERALL );
colors->push_back( osg::Vec4( 1.f, 1.f, 1.f, 1.f ) );
seaGeom->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::QUADS,
0, 4));
return seaGeom;
}
osg::Node* createPreRenderSubGraph(osgViewer::Viewer* viewer, osg::Node*
subgraph)
{
unsigned int tex_width = 512;
unsigned int tex_height = 512;
// create a group to contain the flag and the pre rendering camera.
osg::Group* parent = new osg::Group;
// texture to render to and to use for rendering of flag.
osg::Texture2D* texture2D = new osg::Texture2D;
texture2D->setTextureSize(tex_width, tex_height);
texture2D->setInternalFormat(GL_RGBA);
texture2D->setFilter(osg::Texture2D::MIN_FILTER,osg::Texture2D::LINEAR);
texture2D->setFilter(osg::Texture2D::MAG_FILTER,osg::Texture2D::LINEAR);
osg::Texture* texture = texture2D;
// first create the geometry of the flag of which to view.
{
osg::Geometry* polyGeom = createRegularSeaSurface();
osg::StateSet* seaStateSet = new osg::StateSet;
seaStateSet->setTextureAttributeAndModes(0, texture);
//set shaders for RTT
osg::Program* seaProgramObject = new osg::Program;
{
osg::Shader* seaVertexObject = new osg::Shader(
osg::Shader::VERTEX );
osg::Shader* seaFragmentObject = new osg::Shader(
osg::Shader::FRAGMENT );
seaProgramObject->addShader( seaVertexObject);
seaProgramObject->addShader( seaFragmentObject);
loadShaderSource( seaVertexObject, "shaders/sea.vs" );
loadShaderSource( seaFragmentObject, "shaders/sea.fg" );
seaStateSet->addUniform(new osg::Uniform("rflTex", 0));
seaStateSet->setAttributeAndModes(seaProgramObject);
}
polyGeom->setStateSet(seaStateSet);
osg::Geode* geode = new osg::Geode();
geode->addDrawable(polyGeom);
parent->addChild(geode);
}
// then create the camera node to do the render to texture
{
osg::Camera* rflCamera = new osg::Camera;
osg::Camera* mCamera = viewer->getCamera();
osg::Matrix projectMatrix;
projectMatrix = mCamera->getProjectionMatrix();
rflCamera->setProjectionMatrix(projectMatrix);
osg::Vec3 eye, center, up;
mCamera->getViewMatrixAsLookAt(eye, center, up);
rflCamera->setViewMatrixAsLookAt(eye, center, up);
rflCamera->setClearColor(osg::Vec4(1, 1, 1, 1));
rflCamera->setClearMask(GL_COLOR_BUFFER_BIT |
GL_DEPTH_BUFFER_BIT);
rflCamera->setReferenceFrame(osg::Transform::ABSOLUTE_RF);
rflCamera->setViewport(0,0,tex_width,tex_height);
rflCamera->setRenderOrder(osg::Camera::PRE_RENDER);
rflCamera->setRenderTargetImplementation(osg::Camera::FRAME_BUFFER_OBJECT);
rflCamera->attach(osg::Camera::COLOR_BUFFER, texture);
osg::MatrixTransform* mt = new osg::MatrixTransform;
osg::Matrix s;
s.makeScale(osg::Vec3(1.0, 1.0, -1.0));
mt->setMatrix(s);
mt->addChild(subgraph);
rflCamera->addChild(mt);
rflCamera->setDataVariance(osg::Object::DYNAMIC);
rflCamera->setUpdateCallback(new RflCameraCallback(mCamera));
parent->addChild(rflCamera);
}
return parent;
}
int _tmain(int argc, _TCHAR* argv[])
{
osgViewer::Viewer* viewer = new osgViewer::Viewer();
osg::DisplaySettings* displaysetting = new osg::DisplaySettings();
viewer->setDisplaySettings( displaysetting );
displaysetting->setStereo( true );
osg::Node* loadedModel = osgDB::readNodeFile("cessna.osg");
osg::MatrixTransform* loadedModelTransform = new osg::MatrixTransform;
osg::Matrix mt;
mt.makeTranslate(osg::Vec3(0.0, 0.0, 10.0));
loadedModelTransform->setMatrix(mt);
loadedModelTransform->addChild(loadedModel);
osg::Group* rootNode = new osg::Group();
rootNode->addChild(loadedModelTransform);
rootNode->addChild(createPreRenderSubGraph(viewer,
loadedModelTransform));
viewer->setSceneData( rootNode );
viewer->setCameraManipulator(new osgGA::TrackballManipulator());
while (!viewer->done())
{
static float fusionDistance = 1.0;
fusionDistance += 0.05;
viewer->setFusionDistance(osgUtil::SceneView::USE_FUSION_DISTANCE_VALUE ,
fusionDistance);
viewer->frame();
}
}[/code]
The screen snap is at attachment.
Thank you!
Cheers,
Yongjin[/code]
------------------
Read this topic online here:
http://forum.openscenegraph.org/viewtopic.php?p=13295#13295
<<attachment: result.JPG>>
_______________________________________________ osg-users mailing list [email protected] http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

