Commit 2b1f1321 authored by Christopher Tenter's avatar Christopher Tenter

Documentation on how to use shader-templates. refs #1314

git-svn-id: http://www.openflipper.org/svnrepo/OpenFlipper/branches/Free@16187 383ad7c9-94d9-4d36-a494-682f7c89f535
parent 2528c76c
......@@ -236,6 +236,64 @@ Multiple shader modifiers can be applied to one shader, but the order of modifie
ShaderCache::getInstance()->getProgram(&shaderDesc, ModifierA_ID | ModifierB_ID);
\endcode
\section shader_template_files Shader template files
Shader generation can be controlled with shader template files.
These template files contain custom shader code and are later extended by the ShaderGenerator.
Obviously, only one template at a time can be used by the ShaderGenerator, so render-plugins
should prefer modifiers to retain combinational flexibility.
Example template:
The depth-peeling effect can also be achieved with templates instead of shader-modifiers.
\code
// declare custom uniforms
uniform sampler2D g_DepthLayer;
// the generator takes care of all essential uniforms
void main()
{
// At first, the generator calculates sg_vScreenPos and sg_cColor for us here
SG_FRAGMENT_BEGIN; // begin code marker, insert generated code here
// customized peeling code
float dp_prevDepth = texture(g_DepthLayer, sg_vScreenPos).x;
if (gl_FragCoord.z <= dp_prevDepth) discard;
// end of fragment shader
SG_FRAGMENT_END; // end code marker
// overwrite color output of generator for peel-layer blending
outFragment = vec4(sg_cColor.rgb * sg_cColor.a, sg_cColor.a);
}
\endcode
Assume that this template file is stored at ShaderDir/DepthPeeling/peelLayer.template,
then the peel shader is assembled as follows:
\code
// QString to fragment shader template
QString qstrInitTemplate = OpenFlipper::Options::shaderDirStr() + QDir::separator() + QString("DepthPeeling/peelLayer.template");
// make temp-copy of ShaderGenDesc
ShaderGenDesc peelDesc = sortedObjects_[k]->shaderDesc;
// specify template string
std::string strTemplateFile = qstrInitTemplate.toStdString();
peelDesc.fragmentTemplateFile = strTemplateFile.c_str();
// query shader-program from cache
GLSL::Program* peelProg = ShaderCache::getInstance()->getProgram(&peelDesc);
\endcode
Keep in mind that this technique eventually overwrites any template set by scenegraph-nodes.
\section acg_debugging_tips_and_tricks Debugging tips and tricks
......
......@@ -92,6 +92,11 @@ GLSL::Program* ACG::ShaderCache::getProgram( const ShaderGenDesc* _desc, unsigne
newEntry.desc = *_desc;
newEntry.usage = _usage;
if (_desc->fragmentTemplateFile)
newEntry.strFragmentTemplate = _desc->fragmentTemplateFile;
if (_desc->vertexTemplateFile)
newEntry.strVertexTemplate = _desc->vertexTemplateFile;
for (CacheList::iterator it = cache_.begin(); it != cache_.end(); ++it)
{
......@@ -180,10 +185,10 @@ int ACG::ShaderCache::compareShaderGenDescs( const CacheEntry* _a, const CacheEn
if (a->textured != b->textured)
return -1;
if (a->vertexTemplateFile != b->vertexTemplateFile)
if (_a->strFragmentTemplate != _b->strFragmentTemplate)
return -1;
if (a->fragmentTemplateFile != b->fragmentTemplateFile)
if (_a->strVertexTemplate != _b->strVertexTemplate)
return -1;
if (a->numLights)
......
......@@ -99,6 +99,11 @@ protected:
{
ShaderGenDesc desc;
unsigned int usage;
// string-pointer in ShaderGenDesc may not be permanent,
// so copy string data here
std::string strVertexTemplate;
std::string strFragmentTemplate;
};
int compareShaderGenDescs(const CacheEntry* _a, const CacheEntry* _b);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment