Devlog Update #205 - 04/28/2015Spent all of last night trying to write a transparent gradient shader, and learned a lot about Unity 5's Standard Surface Shader model in the process.
I wanted a tree that grew double gravity cubes.
This was my first go:
As you can see, it is absolutely hideous.
I thought a better style would be to have a gradient going from blue to red from bottom to top through the leaves.
I had a really hard time though trying to write a surface shader that did this.
You see, if I added the tag
"RenderType" = "Transparent"
or
"Queue" = "Transparent"
which seems to be what you're supposed to do if you want something transparent rendered, I get this:
Notice that there are no outlines in the red leaves (that's the shader I'm writing).
However, in the blue leaves, which uses the "Transparent" rendering mode of the Unity 5 standard surface shader, there are outlines.
If I use "RenderType" = "Opaque", I get this irregardless of what alpha value I set the output color to:
I was getting super confused and frustrated, because no matter what combination of RenderType or Queue tags with "Transparent" and "AlphaTest", the leaves were being rendered
after all the edges were drawn.
As it turns out, in the
Shaders 5.0 upgrade guide:
By default all opaque surface shaders output 1.0 (“white”) into alpha channel now. If you want to stop that, use “keepalpha” option on the #pragma surface line.
I needed to add keelalpha on the #pragma surface line.
I also found I needed this line for the shader to work:
Blend SrcAlpha OneMinusSrcAlpha
I don't fully understand why, but if I comment out the line the shader doesn't work.
Eventually, I was able to get it to work, but instead of gradient, I just saw black:
I switched to setting the gradient on screenspace, and that seemed to be working:
And then it hit me - I was using world space position, and all my objects were located in y < 0 ! That's why everything was black.
I zoomed out, and lo and behold:
The point at which black changed to red is y = 0.
I just moved everything up to y = 0, and it was working:
This was around 3 AM, so I wasn't really thinking straight, hence such a silly mistake.
Anyway, today I will add some code so that it can use the local position to set the gradient instead of relying on world space y = 0.