Browse Source

Fixed the FBX material generation more.
Material should not defined light definitions by default since we don't know what the user wants anyhow.
Removed eBumpNormaMap generated materials since this is not working from FBX SDK.

seanpaultaylor 12 years ago
parent
commit
8883c61c3e
3 changed files with 450 additions and 485 deletions
  1. 7 36
      tools/encoder/src/FBXSceneEncoder.cpp
  2. 344 349
      tools/encoder/src/Material.cpp
  3. 99 100
      tools/encoder/src/Material.h

+ 7 - 36
tools/encoder/src/FBXSceneEncoder.cpp

@@ -655,10 +655,6 @@ Material* FBXSceneEncoder::createBaseMaterial(const string& baseMaterialName, Ma
 		baseMaterial->setVertexShader("res/shaders/textured.vert");
         baseMaterial->setFragmentShader("res/shaders/textured.frag");
 
-        if (childMaterial->isLit() && childMaterial->isBumped())
-        {
-			baseMaterial->addDefine("BUMPED");
-        }
         Sampler* sampler = baseMaterial->createSampler(u_diffuseTexture);
         sampler->set("mipmap", "true");
         sampler->set("wrapS", CLAMP);
@@ -675,17 +671,12 @@ Material* FBXSceneEncoder::createBaseMaterial(const string& baseMaterialName, Ma
 	if (childMaterial->isLit())
     {
         baseMaterial->setLit(true);
-		baseMaterial->setUniform("u_inverseTransposeWorldViewMatrix", "INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX");
-		baseMaterial->setUniform("u_directionalLightColor[0]", "1, 1, 1");
-		baseMaterial->setUniform("u_directionalLightDirection[0]", "0, -1, 0");		
+		childMaterial->setUniform("u_inverseTransposeWorldViewMatrix", "INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX");
 
         if (childMaterial->isSpecular())
         {
-            baseMaterial->addDefine(SPECULAR);
-            baseMaterial->setUniform("u_cameraPosition", "CAMERA_WORLD_POSITION");
-        }
-
-		baseMaterial->addDefine("DIRECTIONAL_LIGHT_COUNT 1");		
+            childMaterial->setUniform("u_cameraPosition", "CAMERA_WORLD_POSITION");
+        }		
     }
     assert(baseMaterial);
     return baseMaterial;
@@ -962,7 +953,6 @@ void FBXSceneEncoder::loadMaterialTextures(FbxSurfaceMaterial* fbxMaterial, Mate
                 FbxLayeredTexture *layeredTexture = fbxProperty.GetSrcObject<FbxLayeredTexture>(j);
                 if (layeredTexture)
                 {
-                    //DisplayInt("    Layered Texture: ", j);
                     FbxLayeredTexture *layeredTexture = fbxProperty.GetSrcObject<FbxLayeredTexture>(j);
                     int lNbTextures = layeredTexture->GetSrcObjectCount<FbxTexture>();
                     for (int k = 0; k<lNbTextures; ++k)
@@ -970,22 +960,13 @@ void FBXSceneEncoder::loadMaterialTextures(FbxSurfaceMaterial* fbxMaterial, Mate
                         FbxTexture* fbxTexture = layeredTexture->GetSrcObject<FbxTexture>(k);
                         if (fbxTexture)
                         {
-                            /*
-                            if (pDisplayHeader){
-                                DisplayInt("    Textures connected to Material ", pMaterialIndex);
-                                pDisplayHeader = false;
-                            }
-                            */
 
-                            //NOTE the blend mode is ALWAYS on the LayeredTexture and NOT the one on the texture.
-                            //Why is that?  because one texture can be shared on different layered textures and might
-                            //have different blend modes.
+                            // NOTE the blend mode is ALWAYS on the LayeredTexture and NOT the one on the texture.
+                            // Why is that?  because one texture can be shared on different layered textures and might
+                            // have different blend modes.
 
                             FbxLayeredTexture::EBlendMode lBlendMode;
                             layeredTexture->GetTextureBlendMode(k, lBlendMode);
-                            //DisplayString("    Textures for ", pProperty.GetName());
-                            //DisplayInt("        Texture ", k);
-                            //DisplayTextureInfo(fbxTexture, (int) lBlendMode);
                         }
 
                     }
@@ -1012,19 +993,12 @@ void FBXSceneEncoder::loadMaterialFileTexture(FbxFileTexture* fileTexture, Mater
         if (!material->getSampler("u_diffuseTexture"))
             sampler = material->createSampler("u_diffuseTexture");
     }
-    else if (textureUse == FbxTexture::eBumpNormalMap)
-    {
-        if (!material->getSampler("u_normalmapTexture"))
-            sampler = material->createSampler("u_normalmapTexture");
-    }
     if (sampler)
     {
         sampler->set("absolutePath", fileTexture->GetFileName());
         sampler->set("relativePath", fileTexture->GetRelativeFileName());
         sampler->set("wrapS", fileTexture->GetWrapModeU() == FbxTexture::eClamp ? CLAMP : REPEAT);
         sampler->set("wrapT", fileTexture->GetWrapModeV() == FbxTexture::eClamp ? CLAMP : REPEAT);
-        //sampler->set(MIN_FILTER, LINEAR_MIPMAP_LINEAR);
-        //sampler->set(MAG_FILTER, LINEAR);
 
         if (textureUse == FbxTexture::eStandard)
         {
@@ -1081,7 +1055,7 @@ void FBXSceneEncoder::loadMaterialUniforms(FbxSurfaceMaterial* fbxMaterial, Mate
     if (fbxMaterial->GetClassId().Is(FbxSurfacePhong::ClassId))
     {
         FbxSurfacePhong* phong = FbxCast<FbxSurfacePhong>(fbxMaterial);
-        //FbxDouble specularFactor = phong->SpecularFactor.Get();
+
         if (material->isLit())
         {
             FbxDouble shininess = phong->Shininess.Get();
@@ -1093,9 +1067,6 @@ void FBXSceneEncoder::loadMaterialUniforms(FbxSurfaceMaterial* fbxMaterial, Mate
                 material->addDefine(SPECULAR);
             }
         }
-        //
-        //((FbxSurfacePhong *) fbxMaterial)->GetAmbientColor();
-        //((FbxSurfacePhong *) fbxMaterial)->GetDiffuseColor();
     }
 }
 

+ 344 - 349
tools/encoder/src/Material.cpp

@@ -1,349 +1,344 @@
-#include "Material.h"
-#include "FileIO.h"
-#include "StringUtil.h"
-#include "edtaa3func.h"
-
-namespace gameplay
-{
-
-using std::string;
-using std::vector;
-using std::map;
-
-Material::Material(const std::string& id) :
-    _parent(NULL), _id(id), _lit(false)
-{
-}
-
-Material::Material(const Material& c) :
-    _parent(c._parent),
-    _id(c._id), _lit(false),
-    _vertexShader(c._vertexShader),
-    _fragmentShader(c._fragmentShader),
-    _defines(c._defines),
-    _uniforms(c._uniforms),
-    _renderStates(c._renderStates)
-{
-    for (vector<Sampler*>::const_iterator it = c._samplers.begin(); it != c._samplers.end(); ++it)
-    {
-        _samplers.push_back(new Sampler(**it));
-    }
-}
-
-Material::~Material(void)
-{
-}
-
-const string& Material::getId() const
-{
-    return _id;
-}
-
-void Material::setId(const char* id)
-{
-    if (id)
-        _id.assign(id);
-}
-
-Material* Material::getParent() const
-{
-    return _parent;
-}
-
-void Material::setParent(Material* material)
-{
-    if (material)
-        _parent = material;
-}
-
-void Material::addDefine(const string& name)
-{
-    if (!name.empty())
-    {
-        _defines[name] = string();
-    }
-}
-
-bool Material::isDefined(const string& name) const
-{
-    if (!name.empty())
-    {
-        return _defines.find(name) != _defines.end();
-    }
-    return false;
-}
-
-const char* Material::getUniform(const char* name) const
-{
-    map<string, string>::const_iterator it = _uniforms.find(string(name));
-    if (it != _uniforms.end())
-    {
-        return it->second.c_str();
-    }
-    return NULL;
-}
-
-void Material::setUniform(const string& name, const string& value)
-{
-    _uniforms[name] = value;
-}
-
-const char* Material::getRenderState(const char* name) const
-{
-    map<string, string>::const_iterator it = _renderStates.find(string(name));
-    if (it != _renderStates.end())
-    {
-        return it->second.c_str();
-    }
-    return NULL;
-}
-
-void Material::setRenderState(const string& name, const string& value)
-{
-    if (!name.empty())
-        _renderStates[name] = value;
-}
-
-void Material::setVertexShader(const char* path)
-{
-    if (path)
-        _vertexShader.assign(path);
-}
-
-void Material::setFragmentShader(const char* path)
-{
-    if (path)
-        _fragmentShader.assign(path);
-}
-
-Sampler* Material::createSampler(const string& id)
-{
-    Sampler* sampler = new Sampler(id.c_str());
-    sampler->set("mipmap", "true");
-    sampler->set("wrapS", CLAMP);
-    sampler->set("wrapT", CLAMP);
-    sampler->set(MIN_FILTER, LINEAR_MIPMAP_LINEAR);
-    sampler->set(MAG_FILTER, LINEAR);
-    _samplers.push_back(sampler);
-    return sampler;
-}
-
-Sampler* Material::getSampler(const string& id) const
-{
-    for (vector<Sampler*>::const_iterator it = _samplers.begin(); it != _samplers.end(); ++it)
-    {
-        Sampler* sampler = *it;
-        if (sampler->getId() == id)
-        {
-            return sampler;
-        }
-    }
-    return NULL;
-}
-
-bool Material::isTextured() const
-{
-    return !_samplers.empty();
-}
-
-bool Material::isBumped() const
-{
-    return getSampler("u_normalmapTexture") != NULL;
-}
-
-bool Material::isLit() const
-{
-    return _lit;
-}
-
-bool Material::isSpecular() const
-{
-    return isDefined(SPECULAR);
-}
-
-bool Material::isTextureRepeat() const
-{
-    return isDefined(TEXTURE_REPEAT);
-}
-
-bool Material::isVertexColor() const
-{
-    return isDefined("VERTEX_COLOR");
-}
-
-bool Material::isSkinned() const
-{
-    return isDefined("SKINNING");
-}
-
-bool Material::isModulateAlpha() const
-{
-    return isDefined("MODULATE_ALPHA");
-}
-
-void Material::setLit(bool value)
-{
-    _lit = value;
-}
-
-void Material::writeMaterial(FILE* file)
-{
-    fprintf(file, "material");
-    if (getId().length() > 0)
-    {
-        fprintf(file, " %s", getId().c_str());
-    }
-    if (_parent)
-    {
-         assert(_parent->getId().length() > 0);
-        fprintf(file, " : %s", _parent->getId().c_str());
-    }
-    fprintf(file, "\n");
-    fprintf(file, "{\n");
-    unsigned int indent = 1;
-
-    writeUniforms(file, indent);
-    writeSamplers(file, indent);
-    writeRenderStates(file, indent);
-    writeTechniqueAndPass(file, indent);
-
-    --indent;
-    writeIndent(indent, file);
-    fprintf(file, "}\n");
-}
-
-void Material::writeDefines(FILE* file, unsigned int& indent)
-{
-    writeIndent(indent, file);
-    fprintf(file, "defines = ");
-    for (map<string, string>::const_iterator it = _defines.begin(); it != _defines.end(); ++it)
-    {
-        if (it != _defines.begin())
-        {
-            fprintf(file, ";");
-        }
-        if (it->second.empty())
-        {
-            fprintf(file, "%s", it->first.c_str());
-        }
-        else
-        {
-            fprintf(file, "%s %s", it->first.c_str(), it->second.c_str());
-        }
-    }
-    fprintf(file, "\n");
-}
-
-void Material::writeUniforms(FILE* file, unsigned int& indent)
-{
-    for (map<string, string>::const_iterator it = _uniforms.begin(); it != _uniforms.end(); ++it)
-    {
-        writeIndent(indent, file);
-        fprintf(file, "%s = %s\n", it->first.c_str(), it->second.c_str());
-    }
-    if (!_uniforms.empty())
-    {
-        writeIndent(indent, file);
-        fprintf(file, "\n");
-    }
-}
-
-void Material::writeSamplers(FILE* file, unsigned int& indent)
-{
-    for (vector<Sampler*>::iterator it = _samplers.begin(); it != _samplers.end(); ++it)
-    {
-        Sampler* sampler = *it;
-        Sampler* parentSampler = NULL;
-        if (_parent)
-        {
-            parentSampler = _parent->getSampler(sampler->getId().c_str());
-        }
-        sampler->writeMaterial(file, indent, parentSampler);
-        fprintf(file, "\n");
-    }
-}
-
-void Material::writeRenderStates(FILE* file, unsigned int& indent)
-{
-    if (_renderStates.empty())
-        return;
-    writeIndent(indent, file);
-    fprintf(file, "renderState\n");
-    writeIndent(indent, file);
-    fprintf(file, "{\n");
-    ++indent;
-    for (map<string, string>::const_iterator it = _renderStates.begin(); it != _renderStates.end(); ++it)
-    {
-        writeIndent(indent, file);
-        fprintf(file, "%s = %s\n", it->first.c_str(), it->second.c_str());
-    }
-    --indent;
-    writeIndent(indent, file);
-    fprintf(file, "}\n");
-    writeIndent(indent, file);
-    fprintf(file, "\n");
-}
-
-void Material::writeTechniqueAndPass(FILE* file, unsigned int& indent)
-{
-    if (!_vertexShader.empty() || !_fragmentShader.empty() || !_defines.empty())
-    {
-        bool techniqueWritten = false;
-
-        if (!_vertexShader.empty() || 
-            !_fragmentShader.empty() || 
-            (!_defines.empty() && (!_parent || _parent->_defines != _defines)))
-        {
-            writeTechniqueOpening(file, indent);
-            techniqueWritten = true;
-        }
-        
-        if (!_vertexShader.empty())
-        {
-            writeIndent(indent, file);
-            fprintf(file, "%s = %s\n", "vertexShader", _vertexShader.c_str());
-        }
-        if (!_fragmentShader.empty())
-        {
-            writeIndent(indent, file);
-            fprintf(file, "%s = %s\n", "fragmentShader", _fragmentShader.c_str());
-        }
-        if (!_defines.empty())
-        {
-            if (!_parent || _parent->_defines != _defines)
-            {
-                writeDefines(file, indent);
-            }
-        }
-
-        if (techniqueWritten)
-        {
-            --indent;
-            writeIndent(indent, file);
-            fprintf(file, "}\n");
-
-            --indent;
-            writeIndent(indent, file);
-            fprintf(file, "}\n");
-        }
-    }
-}
-
-void Material::writeTechniqueOpening(FILE* file, unsigned int& indent)
-{
-    // write the techniques
-    writeIndent(indent, file);
-    fprintf(file, "technique\n");
-    writeIndent(indent, file);
-    fprintf(file, "{\n");
-    ++indent;
-
-    // write the passes
-    writeIndent(indent, file);
-    fprintf(file, "pass \n");
-    writeIndent(indent, file);
-    fprintf(file, "{\n");
-    ++indent;
-}
-
-}
+#include "Material.h"
+#include "FileIO.h"
+#include "StringUtil.h"
+#include "edtaa3func.h"
+
+namespace gameplay
+{
+
+using std::string;
+using std::vector;
+using std::map;
+
+Material::Material(const std::string& id) :
+    _parent(NULL), _id(id), _lit(false)
+{
+}
+
+Material::Material(const Material& c) :
+    _parent(c._parent),
+    _id(c._id), _lit(false),
+    _vertexShader(c._vertexShader),
+    _fragmentShader(c._fragmentShader),
+    _defines(c._defines),
+    _uniforms(c._uniforms),
+    _renderStates(c._renderStates)
+{
+    for (vector<Sampler*>::const_iterator it = c._samplers.begin(); it != c._samplers.end(); ++it)
+    {
+        _samplers.push_back(new Sampler(**it));
+    }
+}
+
+Material::~Material(void)
+{
+}
+
+const string& Material::getId() const
+{
+    return _id;
+}
+
+void Material::setId(const char* id)
+{
+    if (id)
+        _id.assign(id);
+}
+
+Material* Material::getParent() const
+{
+    return _parent;
+}
+
+void Material::setParent(Material* material)
+{
+    if (material)
+        _parent = material;
+}
+
+void Material::addDefine(const string& name)
+{
+    if (!name.empty())
+    {
+        _defines[name] = string();
+    }
+}
+
+bool Material::isDefined(const string& name) const
+{
+    if (!name.empty())
+    {
+        return _defines.find(name) != _defines.end();
+    }
+    return false;
+}
+
+const char* Material::getUniform(const char* name) const
+{
+    map<string, string>::const_iterator it = _uniforms.find(string(name));
+    if (it != _uniforms.end())
+    {
+        return it->second.c_str();
+    }
+    return NULL;
+}
+
+void Material::setUniform(const string& name, const string& value)
+{
+    _uniforms[name] = value;
+}
+
+const char* Material::getRenderState(const char* name) const
+{
+    map<string, string>::const_iterator it = _renderStates.find(string(name));
+    if (it != _renderStates.end())
+    {
+        return it->second.c_str();
+    }
+    return NULL;
+}
+
+void Material::setRenderState(const string& name, const string& value)
+{
+    if (!name.empty())
+        _renderStates[name] = value;
+}
+
+void Material::setVertexShader(const char* path)
+{
+    if (path)
+        _vertexShader.assign(path);
+}
+
+void Material::setFragmentShader(const char* path)
+{
+    if (path)
+        _fragmentShader.assign(path);
+}
+
+Sampler* Material::createSampler(const string& id)
+{
+    Sampler* sampler = new Sampler(id.c_str());
+    sampler->set("mipmap", "true");
+    sampler->set("wrapS", CLAMP);
+    sampler->set("wrapT", CLAMP);
+    sampler->set(MIN_FILTER, LINEAR_MIPMAP_LINEAR);
+    sampler->set(MAG_FILTER, LINEAR);
+    _samplers.push_back(sampler);
+    return sampler;
+}
+
+Sampler* Material::getSampler(const string& id) const
+{
+    for (vector<Sampler*>::const_iterator it = _samplers.begin(); it != _samplers.end(); ++it)
+    {
+        Sampler* sampler = *it;
+        if (sampler->getId() == id)
+        {
+            return sampler;
+        }
+    }
+    return NULL;
+}
+
+bool Material::isTextured() const
+{
+    return !_samplers.empty();
+}
+
+bool Material::isLit() const
+{
+    return _lit;
+}
+
+bool Material::isSpecular() const
+{
+    return isDefined(SPECULAR);
+}
+
+bool Material::isTextureRepeat() const
+{
+    return isDefined(TEXTURE_REPEAT);
+}
+
+bool Material::isVertexColor() const
+{
+    return isDefined("VERTEX_COLOR");
+}
+
+bool Material::isSkinned() const
+{
+    return isDefined("SKINNING");
+}
+
+bool Material::isModulateAlpha() const
+{
+    return isDefined("MODULATE_ALPHA");
+}
+
+void Material::setLit(bool value)
+{
+    _lit = value;
+}
+
+void Material::writeMaterial(FILE* file)
+{
+    fprintf(file, "material");
+    if (getId().length() > 0)
+    {
+        fprintf(file, " %s", getId().c_str());
+    }
+    if (_parent)
+    {
+         assert(_parent->getId().length() > 0);
+        fprintf(file, " : %s", _parent->getId().c_str());
+    }
+    fprintf(file, "\n");
+    fprintf(file, "{\n");
+    unsigned int indent = 1;
+
+    writeUniforms(file, indent);
+    writeSamplers(file, indent);
+    writeRenderStates(file, indent);
+    writeTechniqueAndPass(file, indent);
+
+    --indent;
+    writeIndent(indent, file);
+    fprintf(file, "}\n");
+}
+
+void Material::writeDefines(FILE* file, unsigned int& indent)
+{
+    writeIndent(indent, file);
+    fprintf(file, "defines = ");
+    for (map<string, string>::const_iterator it = _defines.begin(); it != _defines.end(); ++it)
+    {
+        if (it != _defines.begin())
+        {
+            fprintf(file, ";");
+        }
+        if (it->second.empty())
+        {
+            fprintf(file, "%s", it->first.c_str());
+        }
+        else
+        {
+            fprintf(file, "%s %s", it->first.c_str(), it->second.c_str());
+        }
+    }
+    fprintf(file, "\n");
+}
+
+void Material::writeUniforms(FILE* file, unsigned int& indent)
+{
+    for (map<string, string>::const_iterator it = _uniforms.begin(); it != _uniforms.end(); ++it)
+    {
+        writeIndent(indent, file);
+        fprintf(file, "%s = %s\n", it->first.c_str(), it->second.c_str());
+    }
+    if (!_uniforms.empty())
+    {
+        writeIndent(indent, file);
+        fprintf(file, "\n");
+    }
+}
+
+void Material::writeSamplers(FILE* file, unsigned int& indent)
+{
+    for (vector<Sampler*>::iterator it = _samplers.begin(); it != _samplers.end(); ++it)
+    {
+        Sampler* sampler = *it;
+        Sampler* parentSampler = NULL;
+        if (_parent)
+        {
+            parentSampler = _parent->getSampler(sampler->getId().c_str());
+        }
+        sampler->writeMaterial(file, indent, parentSampler);
+        fprintf(file, "\n");
+    }
+}
+
+void Material::writeRenderStates(FILE* file, unsigned int& indent)
+{
+    if (_renderStates.empty())
+        return;
+    writeIndent(indent, file);
+    fprintf(file, "renderState\n");
+    writeIndent(indent, file);
+    fprintf(file, "{\n");
+    ++indent;
+    for (map<string, string>::const_iterator it = _renderStates.begin(); it != _renderStates.end(); ++it)
+    {
+        writeIndent(indent, file);
+        fprintf(file, "%s = %s\n", it->first.c_str(), it->second.c_str());
+    }
+    --indent;
+    writeIndent(indent, file);
+    fprintf(file, "}\n");
+    writeIndent(indent, file);
+    fprintf(file, "\n");
+}
+
+void Material::writeTechniqueAndPass(FILE* file, unsigned int& indent)
+{
+    if (!_vertexShader.empty() || !_fragmentShader.empty() || !_defines.empty())
+    {
+        bool techniqueWritten = false;
+
+        if (!_vertexShader.empty() || 
+            !_fragmentShader.empty() || 
+            (!_defines.empty() && (!_parent || _parent->_defines != _defines)))
+        {
+            writeTechniqueOpening(file, indent);
+            techniqueWritten = true;
+        }
+        
+        if (!_vertexShader.empty())
+        {
+            writeIndent(indent, file);
+            fprintf(file, "%s = %s\n", "vertexShader", _vertexShader.c_str());
+        }
+        if (!_fragmentShader.empty())
+        {
+            writeIndent(indent, file);
+            fprintf(file, "%s = %s\n", "fragmentShader", _fragmentShader.c_str());
+        }
+        if (!_defines.empty())
+        {
+            if (!_parent || _parent->_defines != _defines)
+            {
+                writeDefines(file, indent);
+            }
+        }
+
+        if (techniqueWritten)
+        {
+            --indent;
+            writeIndent(indent, file);
+            fprintf(file, "}\n");
+
+            --indent;
+            writeIndent(indent, file);
+            fprintf(file, "}\n");
+        }
+    }
+}
+
+void Material::writeTechniqueOpening(FILE* file, unsigned int& indent)
+{
+    // write the techniques
+    writeIndent(indent, file);
+    fprintf(file, "technique\n");
+    writeIndent(indent, file);
+    fprintf(file, "{\n");
+    ++indent;
+
+    // write the passes
+    writeIndent(indent, file);
+    fprintf(file, "pass \n");
+    writeIndent(indent, file);
+    fprintf(file, "{\n");
+    ++indent;
+}
+
+}

+ 99 - 100
tools/encoder/src/Material.h

@@ -1,100 +1,99 @@
-#ifndef MATERIAL_H_
-#define MATERIAL_H_
-
-#include "Sampler.h"
-#include "Light.h"
-#include "Constants.h"
-
-namespace gameplay
-{
-
-class Material
-{
-public:
-
-    /**
-     * Constructor.
-     */
-    Material(const std::string& id);
-
-    Material(const Material&);
-
-    /**
-     * Destructor.
-     */
-    virtual ~Material(void);
-
-    /**
-     * Returns this material's id string.
-     */
-    const std::string& getId() const;
-
-    /**
-     * Sets this material's id string.
-     */
-    void setId(const char* id);
-
-    Material* getParent() const;
-    void setParent(Material* material);
-
-    void addDefine(const std::string& name);
-    bool isDefined(const std::string& name) const;
-
-    const char* getUniform(const char* name) const;
-    void setUniform(const std::string& name, const std::string& value);
-
-    const char* getRenderState(const char* name) const;
-    void setRenderState(const std::string& name, const std::string& value);
-
-    void setVertexShader(const char* path);
-    void setFragmentShader(const char* path);
-
-    /**
-     * Creates a sampler and adds it to this material.
-     */
-    Sampler* createSampler(const std::string& id);
-    Sampler* getSampler(const std::string& id) const;
-    
-    bool isTextured() const;
-    bool isBumped() const;
-    bool isLit() const;
-    bool isSpecular() const;
-    bool isTextureRepeat() const;
-    bool isVertexColor() const;
-    bool isSkinned() const;
-    bool isModulateAlpha() const;
-
-    void setLit(bool value);
-
-    /**
-     * Writes this material to the given file.
-     */
-    void writeMaterial(FILE* file);
-
-private:
-
-    Material& operator=(const Material&); // Hidden copy assignment operator.
-
-    void writeDefines(FILE* file, unsigned int& indent);
-    void writeUniforms(FILE* file, unsigned int& indent);
-    void writeSamplers(FILE* file, unsigned int& indent);
-    void writeRenderStates(FILE* file, unsigned int& indent);
-    void writeTechniqueAndPass(FILE* file, unsigned int& indent);
-    void writeTechniqueOpening(FILE* file, unsigned int& indent);
-
-private:
-    Material* _parent;
-    std::string _id;
-    std::string _vertexShader;
-    std::string _fragmentShader;
-    bool _lit;
-
-    std::map<std::string, std::string> _defines;
-    std::map<std::string, std::string> _uniforms;
-    std::map<std::string, std::string> _renderStates;
-    std::vector<Sampler*> _samplers;
-};
-
-}
-
-#endif
+#ifndef MATERIAL_H_
+#define MATERIAL_H_
+
+#include "Sampler.h"
+#include "Light.h"
+#include "Constants.h"
+
+namespace gameplay
+{
+
+class Material
+{
+public:
+
+    /**
+     * Constructor.
+     */
+    Material(const std::string& id);
+
+    Material(const Material&);
+
+    /**
+     * Destructor.
+     */
+    virtual ~Material(void);
+
+    /**
+     * Returns this material's id string.
+     */
+    const std::string& getId() const;
+
+    /**
+     * Sets this material's id string.
+     */
+    void setId(const char* id);
+
+    Material* getParent() const;
+    void setParent(Material* material);
+
+    void addDefine(const std::string& name);
+    bool isDefined(const std::string& name) const;
+
+    const char* getUniform(const char* name) const;
+    void setUniform(const std::string& name, const std::string& value);
+
+    const char* getRenderState(const char* name) const;
+    void setRenderState(const std::string& name, const std::string& value);
+
+    void setVertexShader(const char* path);
+    void setFragmentShader(const char* path);
+
+    /**
+     * Creates a sampler and adds it to this material.
+     */
+    Sampler* createSampler(const std::string& id);
+    Sampler* getSampler(const std::string& id) const;
+    
+    bool isTextured() const;
+    bool isLit() const;
+    bool isSpecular() const;
+    bool isTextureRepeat() const;
+    bool isVertexColor() const;
+    bool isSkinned() const;
+    bool isModulateAlpha() const;
+
+    void setLit(bool value);
+
+    /**
+     * Writes this material to the given file.
+     */
+    void writeMaterial(FILE* file);
+
+private:
+
+    Material& operator=(const Material&); // Hidden copy assignment operator.
+
+    void writeDefines(FILE* file, unsigned int& indent);
+    void writeUniforms(FILE* file, unsigned int& indent);
+    void writeSamplers(FILE* file, unsigned int& indent);
+    void writeRenderStates(FILE* file, unsigned int& indent);
+    void writeTechniqueAndPass(FILE* file, unsigned int& indent);
+    void writeTechniqueOpening(FILE* file, unsigned int& indent);
+
+private:
+    Material* _parent;
+    std::string _id;
+    std::string _vertexShader;
+    std::string _fragmentShader;
+    bool _lit;
+
+    std::map<std::string, std::string> _defines;
+    std::map<std::string, std::string> _uniforms;
+    std::map<std::string, std::string> _renderStates;
+    std::vector<Sampler*> _samplers;
+};
+
+}
+
+#endif