1 /*
2 -----------------------------------------------------------------------------
3 This source file is part of OGRE
4 (Object-oriented Graphics Rendering Engine)
5 For the latest info, see http://www.ogre3d.org/
6 
7 Copyright (c) 2000-2013 Torus Knot Software Ltd
8 Also see acknowledgements in Readme.html
9 
10 You may use this sample code for anything you like, it is not covered by the
11 same license as the rest of the engine.
12 -----------------------------------------------------------------------------
13 */
14 
15 #include "MaterialGenerator.h"
16 
17 #include "OgreStringConverter.h"
18 #include "OgreException.h"
19 
20 #include "OgrePass.h"
21 #include "OgreTechnique.h"
22 
23 #include "OgreHighLevelGpuProgram.h"
24 #include "OgreHighLevelGpuProgramManager.h"
25 
26 using namespace Ogre;
27 
MaterialGenerator()28 MaterialGenerator::MaterialGenerator():
29 	vsMask(0), fsMask(0), matMask(0), mImpl(0)
30 {
31 }
~MaterialGenerator()32 MaterialGenerator::~MaterialGenerator()
33 {
34 	delete mImpl;
35 }
36 
getMaterial(Perm permutation)37 const MaterialPtr &MaterialGenerator::getMaterial(Perm permutation)
38 {
39 	/// Check if material/shader permutation already was generated
40 	MaterialMap::iterator i = mMaterials.find(permutation);
41 	if(i != mMaterials.end())
42 	{
43 		return i->second;
44 	}
45 	else
46 	{
47 		/// Create it
48 		MaterialPtr templ = getTemplateMaterial(permutation & matMask);
49 		GpuProgramPtr vs = getVertexShader(permutation & vsMask);
50 		GpuProgramPtr fs = getFragmentShader(permutation & fsMask);
51 
52 		/// Create material name
53 		String name = materialBaseName + StringConverter::toString(permutation);
54 
55 		std::cerr << name << " " << vs->getName() << " " << fs->getName() << std::endl;
56 		/// Create material from template, and set shaders
57 		MaterialPtr mat = templ->clone(name);
58 		Technique *tech = mat->getTechnique(0);
59 		Pass *pass = tech->getPass(0);
60 		pass->setFragmentProgram(fs->getName());
61 		pass->setVertexProgram(vs->getName());
62 
63 		/// And store it
64 		mMaterials[permutation] = mat;
65 		return mMaterials[permutation];
66 	}
67 }
68 
getVertexShader(Perm permutation)69 const GpuProgramPtr &MaterialGenerator::getVertexShader(Perm permutation)
70 {
71 	ProgramMap::iterator i = mVs.find(permutation);
72 	if(i != mVs.end())
73 	{
74 		return i->second;
75 	}
76 	else
77 	{
78 		/// Create it
79 		mVs[permutation] = mImpl->generateVertexShader(permutation);
80 		return mVs[permutation];
81 	}
82 }
83 
getFragmentShader(Perm permutation)84 const GpuProgramPtr &MaterialGenerator::getFragmentShader(Perm permutation)
85 {
86 	ProgramMap::iterator i = mFs.find(permutation);
87 	if(i != mFs.end())
88 	{
89 		return i->second;
90 	}
91 	else
92 	{
93 		/// Create it
94 		mFs[permutation] = mImpl->generateFragmentShader(permutation);
95 		return mFs[permutation];
96 	}
97 }
98 
getTemplateMaterial(Perm permutation)99 const MaterialPtr &MaterialGenerator::getTemplateMaterial(Perm permutation)
100 {
101 	MaterialMap::iterator i = mTemplateMat.find(permutation);
102 	if(i != mTemplateMat.end())
103 	{
104 		return i->second;
105 	}
106 	else
107 	{
108 		/// Create it
109 		mTemplateMat[permutation] = mImpl->generateTemplateMaterial(permutation);
110 		return mTemplateMat[permutation];
111 	}
112 }
113 
~Impl()114 MaterialGenerator::Impl::~Impl()
115 {
116 }
117 
118