diff --git a/VisualStudio/VisualStudio.dsw b/VisualStudio/VisualStudio.dsw index fb1d6c8f3..5e0be7b56 100644 --- a/VisualStudio/VisualStudio.dsw +++ b/VisualStudio/VisualStudio.dsw @@ -47,6 +47,9 @@ Package=<4> Begin Project Dependency Project_Dep_Name Core osgDB End Project Dependency + Begin Project Dependency + Project_Dep_Name Core osgGL2 + End Project Dependency }}} ############################################################################### @@ -423,6 +426,9 @@ Package=<4> Project_Dep_Name Core osgFX End Project Dependency Begin Project Dependency + Project_Dep_Name Core osgGL2 + End Project Dependency + Begin Project Dependency Project_Dep_Name Core osgGA End Project Dependency Begin Project Dependency diff --git a/examples/osgshaders/GL2Scene.cpp b/examples/osgshaders/GL2Scene.cpp index 611703430..ba1d4145f 100644 --- a/examples/osgshaders/GL2Scene.cpp +++ b/examples/osgshaders/GL2Scene.cpp @@ -11,7 +11,7 @@ */ /* file: examples/osgshaders/GL2Scene.cpp - * author: Mike Weiblen 2003-09-30 + * author: Mike Weiblen 2003-10-03 * * Compose a scene of several instances of a model, with a different * OpenGL Shading Language shader applied to each. @@ -390,12 +390,12 @@ GL2Scene::reloadShaderSource() LoadShaderSource( ErodedFragObj, "shaders/eroded.frag" ); ErodedProgObj->setUniform( "LightPosition", osg::Vec3(0.0f, 0.0f, 4.0f) ); ErodedProgObj->setUniform( "Scale", 1.0f ); - ErodedProgObj->setUniform( "sampler3d", 6 ); + ErodedProgObj->setSampler( "sampler3d", 6 ); LoadShaderSource( MarbleVertObj, "shaders/marble.vert" ); LoadShaderSource( MarbleFragObj, "shaders/marble.frag" ); - MarbleProgObj->setUniform( "Noise", 1 ); - MarbleProgObj->setUniform( "Sine", 2 ); + MarbleProgObj->setSampler( "Noise", 1 ); + MarbleProgObj->setSampler( "Sine", 2 ); } diff --git a/include/osgFX/Cartoon b/include/osgFX/Cartoon index bdbb174f3..39e42b1d2 100644 --- a/include/osgFX/Cartoon +++ b/include/osgFX/Cartoon @@ -49,9 +49,10 @@ namespace osgFX "the first one draws solid surfaces, the second one draws the outlines. " "A vertex program is used to setup texture coordinates for a sharp lighting " "texture on unit 0 which is generated on-the-fly.\n" - "This effect requires the ARB_vertex_program extension.", + "This effect requires the ARB_vertex_program extension " + "or OpenGL Shading Language.", - "Marco Jez"); + "Marco Jez; OGLSL port by Mike Weiblen"); /** get the outline color */ inline const osg::Vec4 &getOutlineColor() const; diff --git a/include/osgGL2/ProgramObject b/include/osgGL2/ProgramObject index b912c4153..447d753cd 100644 --- a/include/osgGL2/ProgramObject +++ b/include/osgGL2/ProgramObject @@ -11,7 +11,7 @@ */ /* file: include/osgGL2/ProgramObject - * author: Mike Weiblen 2003-09-18 + * author: Mike Weiblen 2003-10-03 * * See http://www.3dlabs.com/opengl2/ for more information regarding * the OpenGL Shading Language. @@ -28,6 +28,7 @@ #include #include #include +#include #include #include diff --git a/src/osgFX/Cartoon.cpp b/src/osgFX/Cartoon.cpp index d2c76a369..64ea4e7bc 100644 --- a/src/osgFX/Cartoon.cpp +++ b/src/osgFX/Cartoon.cpp @@ -11,6 +11,8 @@ #include #include +#include + #include using namespace osgFX; @@ -148,6 +150,121 @@ namespace } +/////////////////////////////////////////////////////////////////////////// +// A port of Marco Jez's "cartoon.cg" to the OpenGL Shading Language +// using osgGL2 by Mike Weiblen 2003-10-03. +// +// This shader is simplified due to limitations in the OGLSL implementation +// in the current 3Dlabs driver. As the OGLSL implementation improves, +// need to revisit and enhance this shader. + +namespace +{ + class OGLSL_Technique : public Technique { + public: + OGLSL_Technique(osg::Material *wf_mat, osg::LineWidth *wf_lw, int lightnum) + : Technique(), wf_mat_(wf_mat), wf_lw_(wf_lw), lightnum_(lightnum) {} + + void getRequiredExtensions(std::vector &extensions) const + { + extensions.push_back( "GL_ARB_shader_objects" ); + extensions.push_back( "GL_ARB_vertex_shader" ); + extensions.push_back( "GL_ARB_fragment_shader" ); + } + + protected: + + void define_passes() + { + // implement pass #1 (solid surfaces) + { + + const char * vert_source = + "const vec3 LightPosition = vec3( 0.0, 2.0, 4.0 );" + "varying float CartoonTexCoord;" + "void main( void )" + "{" + "vec3 eye_space_normal = normalize(gl_NormalMatrix * gl_Normal).xyz;" + "CartoonTexCoord = max(0.0, dot(normalize(LightPosition), eye_space_normal));" + "gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;" + "}"; + + const char * frag_source = + "uniform sampler1D CartoonTexUnit;" + "varying float CartoonTexCoord;" + "void main( void )" + "{" + "gl_FragColor = texture1D( CartoonTexUnit, CartoonTexCoord );" + "}"; + + osg::ref_ptr ss = new osg::StateSet; + + osg::ref_ptr polyoffset = new osg::PolygonOffset; + polyoffset->setFactor(1.0f); + polyoffset->setUnits(1.0f); + ss->setAttributeAndModes(polyoffset.get(), osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON); + + osg::ref_ptr progObj = new osgGL2::ProgramObject; + progObj->addShader( new osgGL2::ShaderObject( osgGL2::ShaderObject::VERTEX, vert_source ) ); + progObj->addShader( new osgGL2::ShaderObject( osgGL2::ShaderObject::FRAGMENT, frag_source ) ); + progObj->setSampler( "CartoonTexUnit", 0 ); + ss->setAttributeAndModes( progObj.get(), osg::StateAttribute::OVERRIDE | osg::StateAttribute::ON); + + ss->setTextureMode(0, GL_TEXTURE_2D, osg::StateAttribute::OVERRIDE | osg::StateAttribute::OFF); + + osg::ref_ptr texture = new osg::Texture1D; + texture->setImage(create_sharp_lighting_map()); + texture->setFilter(osg::Texture::MIN_FILTER, osg::Texture::NEAREST); + texture->setFilter(osg::Texture::MAG_FILTER, osg::Texture::NEAREST); + ss->setTextureAttributeAndModes(0, texture.get(), osg::StateAttribute::OVERRIDE | osg::StateAttribute::ON); + + osg::ref_ptr texenv = new osg::TexEnv; + texenv->setMode(osg::TexEnv::MODULATE); + ss->setTextureAttributeAndModes(0, texenv.get(), osg::StateAttribute::OVERRIDE | osg::StateAttribute::ON); + + addPass(ss.get()); + } + + // implement pass #2 (outlines) + { + osg::ref_ptr ss = new osg::StateSet; + osg::ref_ptr polymode = new osg::PolygonMode; + polymode->setMode(osg::PolygonMode::FRONT_AND_BACK, osg::PolygonMode::LINE); + ss->setAttributeAndModes(polymode.get(), osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON); + + osg::ref_ptr cf = new osg::CullFace; + cf->setMode(osg::CullFace::FRONT); + ss->setAttributeAndModes(cf.get(), osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON); + + wf_lw_->setWidth(2); + ss->setAttributeAndModes(wf_lw_.get(), osg::StateAttribute::OVERRIDE | osg::StateAttribute::ON); + + wf_mat_->setColorMode(osg::Material::OFF); + wf_mat_->setDiffuse(osg::Material::FRONT_AND_BACK, osg::Vec4(0, 0, 0, 1)); + wf_mat_->setAmbient(osg::Material::FRONT_AND_BACK, osg::Vec4(0, 0, 0, 1)); + wf_mat_->setSpecular(osg::Material::FRONT_AND_BACK, osg::Vec4(0, 0, 0, 1)); + wf_mat_->setEmission(osg::Material::FRONT_AND_BACK, osg::Vec4(0, 0, 0, 1)); + ss->setAttributeAndModes(wf_mat_.get(), osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON); + + ss->setMode(GL_LIGHTING, osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON); + ss->setTextureMode(0, GL_TEXTURE_1D, osg::StateAttribute::OVERRIDE|osg::StateAttribute::OFF); + ss->setTextureMode(0, GL_TEXTURE_2D, osg::StateAttribute::OVERRIDE|osg::StateAttribute::OFF); + + addPass(ss.get()); + + } + } + + private: + osg::ref_ptr wf_mat_; + osg::ref_ptr wf_lw_; + int lightnum_; + }; + +} + +/////////////////////////////////////////////////////////////////////////// + Cartoon::Cartoon() : Effect(), wf_mat_(new osg::Material), @@ -167,5 +284,6 @@ Cartoon::Cartoon(const Cartoon ©, const osg::CopyOp ©op) bool Cartoon::define_techniques() { addTechnique(new DefaultTechnique(wf_mat_.get(), wf_lw_.get(), lightnum_)); + addTechnique(new OGLSL_Technique(wf_mat_.get(), wf_lw_.get(), lightnum_)); return true; } diff --git a/src/osgFX/GNUmakefile b/src/osgFX/GNUmakefile index 080b9aa3e..76ce7ed7b 100644 --- a/src/osgFX/GNUmakefile +++ b/src/osgFX/GNUmakefile @@ -13,7 +13,7 @@ CXXFILES =\ Validator.cpp\ -LIBS += -losg -losgDB -losgUtil $(GL_LIBS) $(OTHER_LIBS) $(DYNAMICLIBRARYLIB) +LIBS += -losg -losgDB -losgUtil -losgGL2 $(GL_LIBS) $(OTHER_LIBS) $(DYNAMICLIBRARYLIB) DEF += -DOSGFX_LIBRARY TARGET_BASENAME = osgFX