Visualization Library v1.0.3

A lightweight C++ OpenGL middleware for 2D/3D graphics

VL     Star     Watch     Fork     Issue

[Download] [Tutorials] [All Classes] [Grouped Classes]

OpenGL Shading Language Tutorial

This tutorial shows how simple it is to use the OpenGL Shading Language with Visualization Library.

pagGuideGLSL.jpg

The example below demostrates the use of vertex shaders, fragment shaders and geometry shaders.

[From App_GLSL.cpp]

class App_GLSL: public BaseDemo
{
public:
  App_GLSL()
  {
  }

  void initEvent()
  {
    if (!Has_GLSL)
    {
      Log::error("OpenGL Shading Language not supported.\n");
      Time::sleep(2000);
      exit(1);
    }

    trackball()->setPivot(vl::vec3(4.5f, 4.5f, 0.0f));

    Log::notify(appletInfo());

    ref<ResourceDatabase> res_db = loadResource("/models/3ds/monkey.3ds");
    mModel = res_db->get<Geometry>(0);
    mModel->computeNormals();
    AABB aabb = mModel->boundingBox();
    mModel->transform( mat4::getTranslation(-aabb.center()) );

    ref<Light> light = new Light;

    ref<GLSLProgram> glsl;

    ref<GLSLVertexShader> perpixellight_vs = new GLSLVertexShader("/glsl/perpixellight.vs");

    //glsl = new GLSLProgram;
    //mGLSL.push_back(glsl);
    //glsl->attachShader( perpixellight_vs.get() );
    //glsl->attachShader( new GLSLFragmentShader("/glsl/perpixellight.fs") );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( new GLSLVertexShader("/glsl/examples/toyball.vs") );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/toyball.fs") );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( perpixellight_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/perpixellight_toon.fs") );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( perpixellight_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/heat.fs") );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( perpixellight_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/perpixellight_interlaced.fs") );

    ref<GLSLVertexShader>   noise_vs   = new GLSLVertexShader("/glsl/examples/noise.vs");
    ref<GLSLFragmentShader> noise3D_fs = new GLSLFragmentShader("/glsl/noise3D.glsl");

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/alien.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/cloud.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/granite.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/marble.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/marble2.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/turbulence.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/woody.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( noise_vs.get() );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/ribbon.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( new GLSLVertexShader("/glsl/examples/noisebump.vs") );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/noisebump.fs") );
    glsl->attachShader( noise3D_fs.get() );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( new GLSLVertexShader("/glsl/examples/hatching.vs") );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/hatching.fs") );

    glsl = new GLSLProgram;
    mGLSL.push_back(glsl);
    glsl->attachShader( new GLSLVertexShader("/glsl/examples/stripes.vs") );
    glsl->attachShader( new GLSLFragmentShader("/glsl/examples/stripes.fs") );

    if (Has_Geometry_Shader)
    {
      glsl = new GLSLProgram;
      mGLSL.push_back(glsl);
      // a vertex shader is always needed when using geometry shaders
      glsl->attachShader( new GLSLVertexShader("/glsl/examples/diffuse.vs") );
      glsl->attachShader( new GLSLGeometryShader("/glsl/examples/triangle_fur.gs") );
      glsl->setGeometryInputType(GIT_TRIANGLES);
      glsl->setGeometryOutputType(GOT_TRIANGLE_STRIP);
      glsl->setGeometryVerticesOut( 3*6 );
    }
    else
    {
      Log::print("Geomery shaders not supported.\n");
    }

    mGLSL.resize(4*4);

    for(int y=0; y<4; ++y)
    {
      for(int x=0; x<4; ++x)
      {
        ref<Effect> fx = new Effect;
        fx->shader()->setRenderState( light.get(), 0 );
        fx->shader()->enable(EN_LIGHTING);
        fx->shader()->enable(EN_DEPTH_TEST);
        // fx->shader()->enable(EN_CULL_FACE);
        GLSLProgram* glsl = mGLSL[x + y*4].get();
        if (glsl)
          fx->shader()->setRenderState(glsl);
        ref<Transform> tr = new Transform;
        real grid= 3.0;
        tr->setLocalAndWorldMatrix( mat4::getTranslation(x*grid, y*grid, 0) );
        sceneManager()->tree()->addActor( mModel.get(), fx.get(), tr.get() );
      }
    }
  }

  void fileDroppedEvent(const std::vector<String>& files)
  {
    ref<ResourceDatabase> db = loadResource(files[0]);
    Geometry* geom = db->get<Geometry>(0);
    if (!geom)
      geom = db->get<Actor>(0)->lod(0)->as<Geometry>();
    if (geom)
    {
      mModel->shallowCopyFrom( *geom );
      mModel->computeBounds();
      AABB aabb = mModel->boundingBox();
      real norm = aabb.width() > aabb.height() ? aabb.width() : aabb.height();
      norm = norm > aabb.depth() ? norm : aabb.depth();
      real scale = 1.5;
      mModel->transform( vl::mat4::getTranslation( -aabb.center() ) );
      mModel->transform( vl::mat4::getScaling( scale / norm, scale / norm, scale / norm ) );
    }
  }

  void updateScene()
  {
  }

protected:
  ref<Geometry> mModel;
  std::vector< ref<GLSLProgram> > mGLSL;
};

// Have fun!


Visualization Library v1.0.3 Reference Documentation
Copyright Michele Bosi. All rights reserved.
Updated on Tue Feb 7 2017 00:55:04.
Permission is granted to use this page to write and publish articles regarding Visualization Library.