I would like to know if this code in Geometry serializer is usefull, because it
forbid any BufferObject attachments to BufferData (call to
setUseVertexBufferObjects(false) just kill all BufferObject attached)
Code:
struct GeometryFinishedObjectReadCallback : public
osgDB::FinishedObjectReadCallback
{
virtual void objectRead(osgDB::InputStream&, osg::Object& obj)
{
osg::Geometry& geometry = static_cast<osg::Geometry&>(obj);
if (geometry.getUseVertexBufferObjects())
{
geometry.setUseVertexBufferObjects(false);
geometry.setUseVertexBufferObjects(true);
}
}
};
mp3butcher wrote:
> Hello,
> I've cleaned my previous version of transformFeedBack example in order to
> use TransformFeedbackBufferBinding and a DrawCallback
>
>
> Code:
>
> /* OpenSceneGraph example, osgtransformfeedback
> *
> * 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 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.
> */
>
> /* file: examples/osgtransformfeedback/osgtransformfeedback.cpp
> * author: Julien Valentin 2013-10-01
> * copyright: (C) 2013
> * license: OpenSceneGraph Public License (OSGPL)
> *
> * A demo of GLSL geometry shaders using OSG transform feedback
> *
> */
>
> /* OpenSceneGraph example, osgtransformfeedback
> *
> * 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 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.
> */
>
> /* file: examples/osgtransformfeedback/osgtransformfeedback.cpp
> * author: Julien Valentin 2013-10-01
> * copyright: (C) 2013
> * license: OpenSceneGraph Public License (OSGPL)
> *
> * A demo of GLSL geometry shaders using OSG transform feedback
> *
> */
>
>
> #include <osg/GL2Extensions>
> #include <osg/Notify>
> #include <osg/ref_ptr>
> #include <osg/Geode>
> #include <osg/Geometry>
> #include <osg/Point>
> #include <osg/Vec3>
> #include <osg/Vec4>
> #include <osg/Program>
> #include <osg/Shader>
> #include <osg/BlendFunc>
>
> #include <osg/Uniform>
> #include <osgViewer/Viewer>
>
> #include <osg/BufferIndexBinding>
> #include <osgDB/WriteFile>
>
> #include <iostream>
>
> ///////////////////////////////////////////////////////////////////////////
>
> class SineAnimation: public osg::UniformCallback
> {
> public:
> SineAnimation( float rate = 1.0f, float scale = 1.0f, float offset = 0.0f
> ) :
> _rate(rate), _scale(scale), _offset(offset)
> {}
>
> void operator()( osg::Uniform* uniform, osg::NodeVisitor* nv )
> {
> float angle = _rate * nv->getFrameStamp()->getSimulationTime();
> float value = sinf( angle ) * _scale + _offset;
> uniform->set( value );
> }
>
> private:
> const float _rate;
> const float _scale;
> const float _offset;
> };
>
>
> //////////////////////////////////////////////////////////////////////////////////////
> namespace osg
> {
> class OSG_EXPORT TransformFeedBackDrawCallback: public Drawable::DrawCallback
> {
> protected:
>
> std::vector<osg::ref_ptr<osg::TransformFeedbackBufferBinding> > _tfbbs;
>
> GLuint _index;
> public:
> TransformFeedBackDrawCallback():Drawable::DrawCallback()
> {
> _type=0;
> }
> TransformFeedBackDrawCallback(const Drawable::DrawCallback&dc,const
> CopyOp&co);
>
> /** Get the primitive type of the feedback.
> */
> GLenum getFeedBackType() const
> {
> return _type;
> }
> void setFeedBackType(GLenum e)
> {
> _type=e;
> }
>
>
>
> void
> addTransformFeedbackBufferBinding(osg::TransformFeedbackBufferBinding * tfbb);
> void
> removeTransformFeedbackBufferBinding(osg::TransformFeedbackBufferBinding *
> tfbb);
> osg::TransformFeedbackBufferBinding
> *getTransformFeedbackBufferBinding(const unsigned int &i)const
> {
> return _tfbbs[i];
> }
>
> unsigned int getNumTransformFeedbackBufferBindings()const
> {
> return _tfbbs.size();
> }
>
>
>
>
> META_Object(osg,TransformFeedBackDrawCallback);
>
>
>
> /** do TransformFeedback draw code.*/
> virtual void drawImplementation(osg::RenderInfo& renderInfo,const
> osg::Drawable* drawable ) const;
>
>
> };
> TransformFeedBackDrawCallback:: TransformFeedBackDrawCallback(const
> Drawable::DrawCallback&dc,const CopyOp&co):osg::Drawable::DrawCallback(dc,co)
> {
> }
> void
> TransformFeedBackDrawCallback::addTransformFeedbackBufferBinding(osg::TransformFeedbackBufferBinding
> * tfbb)
> {
> if(tfbb)_tfbbs.push_back(tfbb);
> }
> void
> TransformFeedBackDrawCallback::removeTransformFeedbackBufferBinding(osg::TransformFeedbackBufferBinding
> * tfbb)
> {
>
> for(std::vector<osg::ref_ptr<osg::TransformFeedbackBufferBinding>
> >::iterator i=_tfbbs.begin(); i!=_tfbbs.end(); i++)
> {
> if((*i).get()==tfbb)
> {
>
> _tfbbs.erase(i);
> return;
> }
> }
> }
>
> /** do TransformFeedback draw code.*/
> void TransformFeedBackDrawCallback::drawImplementation(osg::RenderInfo&
> renderInfo,const osg::Drawable* drawable ) const
> {
> osg::GLExtensions* ext = renderInfo.getState()->get<osg::GLExtensions>();
>
> ///required?
> for(std::vector<osg::ref_ptr<osg::TransformFeedbackBufferBinding>
> >::const_iterator i=_tfbbs.begin(); i!=_tfbbs.end(); i++)
> {
> (*i)->apply(*renderInfo.getState());
>
>
> }
>
>
> glEnable(GL_RASTERIZER_DISCARD);
> ext->glBeginTransformFeedback(_type);
> drawable->drawImplementation(renderInfo);
>
> ext->glEndTransformFeedback();
>
> glDisable(GL_RASTERIZER_DISCARD);
>
> ///unbind all TransformFeedbackBufferBindingS
> ext->glBindBufferBase(GL_TRANSFORM_FEEDBACK_BUFFER, 0, 0);
> }
> }
>
> ///////////////////////////////////////////////////////////////////////////
>
> ///////////////////////////////////////////////////////////////////////////
> static const char* RendervertSource =
> {
> "#version 120\n"
> "varying vec4 v_color;\n"
> "void main(void)\n"
> "{\n"
> " v_color = gl_Vertex;\n"
> " gl_Position = gl_ModelViewProjectionMatrix *(gl_Vertex);\n"
> "}\n"
> };
> static const char* vertSource =
> {
> "#version 120\n"
> "#extension GL_EXT_geometry_shader4 : enable\n"
> "varying out vec4 v_color;\n"
> "void main(void)\n"
> "{\n"
> " gl_Position = (gl_Vertex);\n"
> " v_color = gl_Vertex;\n"
> "}\n"
> };
>
>
>
> static const char* geomSource =
> {
> "#version 120\n"
> "#extension GL_EXT_geometry_shader4 : enable\n"
> "uniform float u_anim1;\n"
> " varying in vec4 v_color[];\n"
> " varying vec4 out1;\n"
> "void main(void)\n"
> "{\n"
> " vec4 v =vec4( gl_PositionIn[0].xyz,1);\n"
> " out1 = v + vec4(u_anim1,0.,0.,0.);// gl_Position = v +
> vec4(u_anim1,0.,0.,0.); \n"
> " EmitVertex();\n"
> " EndPrimitive();\n"
> " out1 = v - vec4(u_anim1,0.,0.,0.); // gl_Position = v -
> vec4(u_anim1,0.,0.,0.); \n"
> " EmitVertex();\n"
> " EndPrimitive();\n"
> "\n"
> " out1= v + vec4(0.,1.0-u_anim1,0.,0.);// gl_Position = v +
> vec4(0.,1.0-u_anim1,0.,0.); \n"
> " EmitVertex();\n"
> " EndPrimitive();\n"
> " out1 = v - vec4(0.,1.0-u_anim1,0.,0.); //gl_Position = v -
> vec4(0.,1.0-u_anim1,0.,0.); \n"
> " EmitVertex();\n"
> " EndPrimitive();\n"
> "}\n"
> };
>
>
> static const char* fragSource =
> {
> "#version 120\n"
> "#extension GL_EXT_geometry_shader4 : enable\n"
> "varying vec4 v_color_out;\n"
> "void main(void)\n"
> "{\n"
> " gl_FragColor = vec4(1,0,0,1);//v_color_out;\n"
> "}\n"
> };
>
> osg::Program* createGeneratorShader()
> {
> osg::Program* pgm = new osg::Program;
> pgm->setName( "osg transformfeedback generator demo" );
> pgm->addShader( new osg::Shader( osg::Shader::VERTEX, vertSource ) );
> ///setup Transform FeedBack program
> pgm->setParameter( GL_GEOMETRY_VERTICES_OUT_EXT, 4 );
> pgm->setParameter( GL_GEOMETRY_INPUT_TYPE_EXT, GL_POINTS );
> pgm->setParameter( GL_GEOMETRY_OUTPUT_TYPE_EXT, GL_POINTS );
> pgm->addShader( new osg::Shader( osg::Shader::GEOMETRY, geomSource ) );
> pgm->addTransformFeedBackVarying(std::string("out1"));
> pgm->setTransformFeedBackMode(GL_INTERLEAVED_ATTRIBS);
> return pgm;
> }
>
> osg::Program* createRenderShader()
> {
> osg::Program* pgm = new osg::Program;
> pgm->setName( "osg transformfeedback renderer demo" );
> pgm->addShader( new osg::Shader( osg::Shader::VERTEX, RendervertSource
> ) );
> pgm->addShader( new osg::Shader( osg::Shader::FRAGMENT, fragSource ) );
> return pgm;
> }
> int main( int , char** )
> {
> osg::Geode* root( new osg::Geode );
> osg::ref_ptr<osg::Geometry > somePointsGenerator = new osg::Geometry();
> somePointsGenerator->setName("SomePointsGenerator");
> {
> somePointsGenerator->setUseVertexBufferObjects(true);
> somePointsGenerator->setUseDisplayList(false);
>
> osg::StateSet* sset = somePointsGenerator->getOrCreateStateSet();
> sset->setMode( GL_LIGHTING, osg::StateAttribute::OFF );
> osg::ref_ptr<osg::Vec4Array> vAry = new osg::Vec4Array;
> vAry->push_back( osg::Vec4(0,0,0,1) );
> vAry->push_back( osg::Vec4(0,1,0,1) );
> vAry->push_back( osg::Vec4(1,0,0,1) );
> vAry->push_back( osg::Vec4(1,1,0,1 ));
> somePointsGenerator->addPrimitiveSet( new osg::DrawArrays( GL_POINTS,
> 0, vAry->size() ) );
> somePointsGenerator->setVertexArray( vAry );
>
> osg::ref_ptr<osg::Program> _program=createGeneratorShader() ;
> sset->setAttribute(_program );
>
> // a generic cyclic animation value
> osg::Uniform* u_anim1( new osg::Uniform( "u_anim1", 0.9f ) );
> u_anim1->setUpdateCallback( new SineAnimation( 4, 0.5, 0.5 ) );
> sset->addUniform( u_anim1 );
> }
>
> osg::ref_ptr<osg::Geometry > somePointsRenderer = new osg::Geometry();
> somePointsRenderer->setName("SomePointsRenderer");
> {
> int
> numprimgen=somePointsGenerator->getVertexArray()->getNumElements()*4;
> somePointsRenderer->setUseVertexBufferObjects(true);
> somePointsRenderer->setUseDisplayList(false);
>
> osg::ref_ptr<osg::Vec4Array> vAry2 = new osg::Vec4Array;
> vAry2->resize(numprimgen);
> somePointsRenderer-> setVertexArray(vAry2);
> somePointsRenderer-> addPrimitiveSet( new osg::DrawArrays( GL_LINES,
> 0,numprimgen));
> osg::StateSet* sset = somePointsRenderer-> getOrCreateStateSet();
> sset->setMode( GL_LIGHTING, osg::StateAttribute::OFF );
> sset->setAttribute( createRenderShader() );
>
>
> }
>
> {
> ///setup Transform FeedBack callback
> osg::TransformFeedBackDrawCallback *tfcb=new
> osg::TransformFeedBackDrawCallback();
> osg::TransformFeedbackBufferBinding *tfbb=new
> osg::TransformFeedbackBufferBinding ();
>
> tfbb->setBufferObject(somePointsRenderer->getVertexArray()->getVertexBufferObject());
> somePointsRenderer->getOrCreateVertexBufferObject();
>
> tfbb->setSize(somePointsRenderer->getVertexArray()->getTotalDataSize());
> somePointsGenerator->getStateSet()->setAttribute(tfbb);
>
> tfcb->setFeedBackType(GL_POINTS);
> tfcb->addTransformFeedbackBufferBinding(tfbb);
> somePointsGenerator->setDrawCallback(tfcb);
> }
>
>
> root->addChild(somePointsGenerator);
> root->addChild(somePointsRenderer);
> ///ensure draw sequence
> somePointsGenerator->getStateSet()->setRenderBinDetails(0,"RenderBin");
> somePointsRenderer->getStateSet()->setRenderBinDetails(1,"RenderBin");
>
> osgViewer::Viewer viewer;
> viewer.setSceneData( root );
> return viewer.run();
> }
>
>
>
>
>
>
> I've also do some stuff to serialize it but it requires:
> -the TransformFeedbackDrawCallback to be integrated somewhere in OSG
> (..in osg/Drawable?)
> -a osg::BufferObject,osg::UniforBufferBinding class serializers
>
> Does it seams you reasonable?
> If so I'll post my work on it...
>
>
> [/code]
------------------
Read this topic online here:
http://forum.openscenegraph.org/viewtopic.php?p=67105#67105
_______________________________________________
osg-submissions mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org