As I moved my rendering into centralized Renderer class, I can't use direct GL calls (glUniform*) to set uniforms where I know their value, but I have to pass them all as a part of draw command to renderer. Perfectly I'd have something like:
[source lang="cpp"]std::map< std::string, Uniform > uniforms;uniforms["mvp"] = Uniform(glm::mat4(0.0));uniforms["alpha"] = Uniform(0.56f);glm::vec4 sunpos = world->getsunpos();uniforms["sunpos"] = Uniform(sunpos);[/source]
For now I need support for: float, int, vec2, vec3, vec4, mat4, but later I may also need uniform structs. From what I know this is typical variant class that stores values of different types. I wanted to ask you for best solution, because the one I managed to hack so far is not perfect, is a bit bloated with nasty switches and requires me to initialize Uniform only by passing "new" into constructor (so this doesn't work: Uniform(mvp) or Uniform(glm::mat4(0.0)), only this: Uniform(new glm::mat4(mvp)).
I will show code for one sample value:
[source lang="cpp"]UniformValue::UniformValue(std::string name, glm::vec2* value){ m_Name = name; m_Data = static_cast< void* >(value); m_Type = UniformValue::Vec2;}UniformValue::~UniformValue(){ switch(m_Type) { case Vec2: delete static_cast< glm::vec2* >(m_Data); break; }}glm::vec2 UniformValue::ToVec2() const{ return *(static_cast< glm::vec2* >(m_Data));}void UniformValue::Apply(Shader* shader) const{ switch(m_Type) { case Vec2: shader->SetUniform(m_Name, ToVec2()); break; }}[/source]
I'm not entirely sure this is the best solution to my problem. Do you guys know any better? Especially if they allow me to pass local variables (Uniform(model) instead of Uniform(new glm::mat4(model))) and not have to use "new" in constructor.
I was thinking about using unions but I'm not sure they will work with glm::mat4 and other more complex objects (non-POD).
PS. Also solution should be pretty quick and not initialize unecessary things (like passing variable, copying it, then allocating some new one in the final step) - setting uniforms happens for all drawing commands every frame so it shouldn't be too unoptimized, because maybe its not much, but its done very often.
Edited by noizex, 24 September 2012 - 12:38 PM.







