- Home /
How to set up additive blending on a surface shader?
So, in a normal shader I have the line:
Blend SrcAlpha One
And that gives me additive blending of the sort I want. It works with transparency, and so on. However, when I use a surface shader this line does literally nothing. I take it that the CGPROGRAM section overrides the blend specifications and such above it. How do I do the equivalent thing in my surface shader?
I did try decal:add on the #pragma surface line, and that was additive blending in some respects, but it also destroyed the alpha blending so that's definitely not what I want.
I'm looking for an answer to this as well.
The "alpha" and "decal:add" tags override each other based on which comes last. "decal:add" does exactly the kind of additive color blending we're looking for (SrcAlpha One), but it doesn't care about alpha blending at all.
Why is there not a tag along the lines of "alpha:add"?
Answer by deram_scholzara · Jul 10, 2013 at 01:00 AM
Ah-ha! I figured it out...
So apparently when you do not use the "alpha", "decal:add", or "decal:blend" tags, the blending mode is defined by the old-style Blend settings.
So in short, don't use those tags, and, in your case, use "Blend SrcAlpha One" instead.
But this doesn't answer the question. This would require NOT using a surface shader, unless I misunderstand something?
Actually, it exactly answers the question. x4000 wanted to know how to set up a surface shader to use additive blending, and the way to do it is to use the "Blend SrcAlpha One" tag as with a non-CGPROGRA$$anonymous$$ shader, and leave out the "alpha", "decal:add", and "decal:blend" tags from the CGPROGRA$$anonymous$$. In the post, x4000 mentions that the "Blend" tag does nothing when writing a surface shader, and my explanation makes it do something - thereby allowing x4000 to do exactly what they want.
Are you wondering about something else that my answer doesn't fix?
Hm. I'm new to this, sorry. $$anonymous$$y understanding is this (and correct me where I'm wrong): if you're using a surface shader, then you don't include a Pass { } block. But if you want to use the old-style Blend settings you have to put them in a Pass.
To test, I have this shader that works already - it's an emissive shader that uses both texture alpha and alpha based on normal falloff.
Shader "Falloff/GhostFlat" {
Properties {
_Color ("$$anonymous$$ain Color", Color) = (1,1,1,1)
_$$anonymous$$ainTex ("Base (RGB) Trans (A)", 2D) = "white" {}
_RimPower ("Rim Exponent", Range(0.5,25.0)) = 3.0
_BaseAlpha ("Base Alpha", Range(0.0,1.0)) = 1.0
}
SubShader {
Tags {"Queue"="Transparent" "IgnoreProjector"="True" "RenderType"="Transparent"}
CGPROGRA$$anonymous$$
#pragma surface surf Lambert alpha
sampler2D _$$anonymous$$ainTex;
fixed4 _Color;
float _RimPower;
float _BaseAlpha;
struct Input {
float2 uv_$$anonymous$$ainTex;
float3 viewDir;
};
void surf (Input IN, inout SurfaceOutput o) {
fixed4 c = tex2D(_$$anonymous$$ainTex, IN.uv_$$anonymous$$ainTex) * _Color;
half rim = saturate(dot (normalize(IN.viewDir), o.Normal));
//o.Albedo = c.rgb; //No albedo, only emission
o.Emission = c.rgb;
o.Alpha = pow (rim, _RimPower) * _BaseAlpha * c.a;
}
ENDCG
}
FallBack "Self-Illu$$anonymous$$/Diffuse"
}
But if I wanted to make it additive as well, how would I do that? I tried taking the "alpha" out of the #pragma line, and adding this under the Tags {} block: Pass { Blend One One } but that caused a bunch of errors. So how can you combine these?
To the best of my knowledge, there is no such thing as "additive as well". There is only additive or not.
The Blend mode does not need to be in a Pass of its own, you can just put it under the SubShader block.
A surface shader basically creates its own Pass block, so when you put the Blend mode in a Pass block, it's a completely separate pass from the CGPROGRA$$anonymous$$ section, and therefore does not affect it. When you do not specify a blend pragma (using the alpha or decal options), it would appear that the shader defaults to whatever was specified in the subshader. As I understand it, this is how it works with fixed function Pass blocks as well - they default to the SubShader Blend mode, which is opaque (Zero One, I believe) when unspecified.
Answer by JBC · Jun 08, 2011 at 05:52 AM
Did you try adding "alpha" or "alphatest:_Cutoff" in the pragma line? Curious if that would help.
Your answer
Follow this Question
Related Questions
Multiply Shader with Alpha 0 Answers
Particle effects against light backgrounds 2 Answers
Iphone - Blend two textures + Additive blending 3 Answers
Simple texture blender shader not working properly 0 Answers
Additive Surface Shader in Unity 5 1 Answer