Skip to main content
GameDev.net gamedev.net
🔒 Locked

Managing shaders/materials

Started by Werner291 Dec 26, 2013 at 12:19 PM 1 replies 3k views
Original Post
Werner291
Werner291

Hello, I'm trying to write a 3D engine, but I'm having some problems with the management of my shaders and materials.

Mostly, the problem is keeping the two seperate. Some things in my engine require texture splatting, others need to be reflective, others need to glow, yet others should look liquid, and then some more...

I was quite impressed by Ogre3D's material scripts, but I can't make heads or tails out of the enormous amount of source code.

My current approach is to try to automatically generate a shader program for every material, but this seems kinda wasteful. I might for example have two things in the game world that look exactly identical except for a different color.

Also, since the program generation is now locked away in the material, how to I implement things like tesselation and vertex manipulation?

This has been causing me headaches over the past couple days up to the point where I felt like just abandoning, but I'd at least like to understand this before I do.

Samith
Samith

My current approach is to try to automatically generate a shader program for every material, but this seems kinda wasteful. I might for example have two things in the game world that look exactly identical except for a different color.

That's because it is wasteful. The shader should never change if the only difference is some constant (in your case, the color). Color is stored in a constant buffer, which the shader will read. It would make more sense for your material to know what color to use, and then at runtime when you bind the material it will set that constant value for the shader to read. Basically any constants or textures are material properties, and they belong in the material. The shader doesn't need to be (and should not be) regenerated for every constant/texture change.

Now, regarding shader permutations: one simple technique that I employ is a standard 'ubershader' approach. One shader is written and it contains every feature I want, but each feature is inside a #if/#endif block. I can compile this shader multiple times with different sets of preprocessor defines to enable and disable various features. The material can specify which defines to set and compile the shader with those defines if necessary. You can cache which shaders you've already generated to avoid generating the shader with the same set of defines more than once.

You'll have to be more specific with your question about tessellation. I don't support tessellation in any engine I've written, but I think it should work within the ubershader framework I have. I don't think the way your generate shaders should really have any effect on what you can or can't support.

larspensjo
larspensjo

To manage shaders, I use the GLSW. It is simple to use, and still quite powerful. It is really just a text substitution engine, but it helps to organize and share large varieties of shaders.

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.