Whats the fastest way to “tint” or colourize an entire mesh? for example making a player flash white or red when hit.
Also on the iPhone, is it slower to use more lights even if its just vertex lighting, and if it isn’t slower, can I use more than 8, providing they dont all affect the same mesh?
Your best bet for a “flash” is probably adding a solid color to whatever you’ve already got going on in your shader, ideally just a texture. If that doesn’t get you predictable enough results, then you’ll have to blend the color in. That’s fastest to do with black (“multiply”), but black doesn’t constitute much of a “flash”. For other colors, I assume that screening (adding in the inverse of the texture to achieve white) is faster than the alternative, Lerp, but I’ve never tested the difference (screening requires two texture stages and I don’t know how that affects performance even when the overall calculations are fewer). If you need something other than white or black, and additive isn’t doing it for you, Lerp is what you need.
As for lights, I haven’t used them outside of testing shaders, but I can’t see how it wouldn’t slow things down to use more; why would you think it wouldn’t be slower?
Here’s a “screen” shader I use for explodey stuff:
Shader "Screen" {
Properties {
_MainTex ("Texture", 2D) = ""
}
// Equivalent to the "Screen" blend mode in Photoshop,
// with "_Flash" as a solid grayscale layer above the texture.
SubShader {
Pass {
SetTexture[_MainTex] {
ConstantColor (0,0,0, [_Flash])
Combine one - texture * constant alpha
}
SetTexture[_MainTex] {Combine texture + previous}
}
}
}
Thanks Jessy, I didn’t realise I could do that under opengl ES 1.1. I should point out that I need to change the colour of the mesh rather than just flash it, for example in some areas I might darken it to give it the illusion of being in shadow. I will try the above shader too
I’d recommend using vertex colors to paint your own vertex lighting, and then add in a bright color on top of that. Does that sound like what you want to do, or is a solid color good enough for you?
Solid colour seems perfect. In the old Blitz3D language I used they had a command like EntityColour(ent, r,g, b) And I figured if I could just “globally” change the mesh colour I could also re-use it, say greyscale parts could be any colour then!
But it would also need to play nice with existing vert lighting if possible… as we will always have at least one directional or something.
You’re introducing a lot of variables now. You’re obviously targeting older devices, so having a bunch of capability in a shader is not a good idea; it will come at the expense of performance. Let me know exactly what you need, and I’ll give you something to go on.
I’m not sure what you mean. Are you talking about this?
Why is that? If you don’t actually need it, not using lighting one of the most important things you can do to make the game run better. It could be better to settle on a lighting model and just work that into all your textures. Final Fantasy X used a fake GI approach, with blob shadows and lightmapping, for example.
I think I am over-complicating it. The exact effect I need is what I do on the iPhone under OpenGL ES, that is I change the RGB of the verts of my quads to draw images in different colours. But unlike that, I want the ordianary vertex lights to also light it as normal.
But I wanted to apply that to an entire mesh without the overhead of manually going in and tweaking all the vert colours. An inexpensive thing that I could change via script? Here is an image to explain better:
It’s just a mock up and the example colours are off but it should give you the basic idea… nothing fancy
It would also not have alpha channel information, it does not need that so it would disable glblend. I don’t know if unity does this already for speed. I would need to be able to tell one must to be a different colour via script though if possible
There’s no need to store the colors in the verts, if they’re all the same. That’s what the Material block and ConstantColor commands are for. However, if your objects can batch, that’s when you should consider storing the color data in the vertices. This won’t be worth doing if you have to change the colors a lot, though; it’s better to have more draw calls than to be updating lots of vertex colors.
Anyway, the greyscale nature of the textures makes this simple. The tinting you have going on there is just multiplication. Lighting is also multiplication. So you can combine the two, via the Material block:
I use Quad because it makes it easy to achieve the “flash” effect you talked about earlier. Use Double instead if that’s too bright, and if Double is too bright, just delete the last keyword in the shader.
Just use material.color. Very easy, and if you’re going to have lighting, this won’t have any further impact.
I don’t know anything about OpenGL. But I know ShaderLab, and “Blend Off” is the default. On the subject of alpha, though, if your texture is going to be nearly colorless, you may want to go all the way, and try putting it in the alpha channel of some other texture, to save room.