- Home /
Why does this shader make my 2D sprites disappear if they are rotated 180 degrees? Also, pixel snap?
Shader "RGB -> Grey Texture/Alpha Blended" {
Properties{
_MainTex ("Sprite Texture", 2D) = ""
[MaterialToggle] PixelSnap ("Pixel snap", Float) = 1
}
Subshader {
Tags {"Queue"="Transparent"}
ZWrite Off
Blend SrcAlpha OneMinusSrcAlpha
Pass {
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
struct v2f {
float4 position : SV_POSITION;
float2 uv_mainTex : TEXCOORD;
};
uniform float4 _MainTex_ST;
v2f vert(float4 position : POSITION, float2 uv : TEXCOORD0) {
v2f o;
o.position = mul(UNITY_MATRIX_MVP, position);
o.uv_mainTex = uv * _MainTex_ST.xy + _MainTex_ST.zw;
return o;
}
uniform sampler2D _MainTex;
fixed4 frag(float2 uv_mainTex : TEXCOORD) : COLOR {
fixed4 mainTex = tex2D(_MainTex, uv_mainTex);
fixed4 fragColor;
fragColor.rgb = dot(mainTex.rgb, fixed3(.222, .707, .071));
fragColor.a = mainTex.a;
return fragColor;
}
ENDCG
}
}
}
I am not much into shaders, and my game has very limited use for them. One of the only uses I have, is to use shaders to "greyscale" my scenes, almost like the fullscreen effect in the pro license.
I have two questions about this shader, with one of them being a problem.
1) Any time I rotate my sprite gameobjects with this shader, to 180 degrees (horizontal flip), and the sprite vanishes. This is a problem because I flip some sprites horizontally using a 180 degree rotation. All my other shaders work fine, it is this exclusively.
2) How do I add PixelSnap to this shader? I have browsed a bit to try to do it myself, but I failed. Without digging in deeper and learning some shader code (which is honestly unnecessary as this shader is just a placeholder until I get a pro license) I'd like to enable Pixel Snap, if it is as simple as I think it will be.
Thank you :)
Answer by frogsbo · Aug 11, 2014 at 06:36 PM
you have to add Cull Off
to avoid backface culling of mesh, put it after zwrite off
Thanks. That was so simple, and looking over the shader compared to another with Pixel Snap, it just clicked and was easy to add pixel snap too.
Sometimes it's best to just step away and not program for a bit, come back, and bam 3 seconds later problem solved.
Answer by CarterG81 · Aug 12, 2014 at 03:13 AM
Greyscale effect shader for 2D Sprites + Pixel Snap + rotation enabled
Shader "RGB -> Grey Texture/Alpha Blended" {
Properties{
_MainTex ("Sprite Texture", 2D) = ""
[MaterialToggle] PixelSnap ("Pixel snap", Float) = 1
}
Subshader {
Tags {"Queue"="Transparent"}
ZWrite Off
Blend SrcAlpha OneMinusSrcAlpha
Cull Off
Lighting Off
Fog { Mode Off }
Pass {
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#pragma multi_compile DUMMY PIXELSNAP_ON
#pragma target 3.0
#include "UnityCG.cginc"
struct v2f {
float4 position : SV_POSITION;
float2 uv_mainTex : TEXCOORD;
};
uniform float4 _MainTex_ST;
v2f vert(float4 position : POSITION, float2 uv : TEXCOORD0) {
v2f o;
o.position = mul(UNITY_MATRIX_MVP, position);
o.uv_mainTex = uv * _MainTex_ST.xy + _MainTex_ST.zw;
#ifdef PIXELSNAP_ON
o.position = UnityPixelSnap (o.position);
#endif
return o;
}
uniform sampler2D _MainTex;
fixed4 frag(float2 uv_mainTex : TEXCOORD) : COLOR {
fixed4 mainTex = tex2D(_MainTex, uv_mainTex);
fixed4 fragColor;
fragColor.rgb = dot(mainTex.rgb, fixed3(.222, .707, .071));
fragColor.a = mainTex.a;
return fragColor;
}
ENDCG
}
}
}
To greyscale the entire scene, it's simple:
public Material greyscaleMAT;
List<Material> normalMATs = new List<Material>();
void GreyScaleSceneOn ()
{
object[] allObjects = FindObjectsOfTypeAll(typeof(GameObject)) ;
int index = 0;
foreach(object thisObject in allObjects)
if (((GameObject) thisObject).activeInHierarchy)
{
GameObject thisGO = (GameObject)thisObject;
if(thisGO.renderer && thisGO.tag != "NoGrey")
{
normalMATs.Add(thisGO.renderer.material);
thisGO.renderer.material = greyscaleMAT;
index++;
}
}
}
void GreyScaleSceneOff ()
{
object[] allObjects = FindObjectsOfTypeAll(typeof(GameObject)) ;
int index = 0;
foreach(object thisObject in allObjects)
if (((GameObject) thisObject).activeInHierarchy)
{
GameObject thisGO = (GameObject)thisObject;
if(thisGO.renderer && thisGO.tag != "NoGrey")
{
thisGO.renderer.material = normalMATs[index];
index++;
}
}
normalMATs.Clear ();
}
Answer by unity_oVsJgtACmNlH5w · May 01 at 09:08 AM
Anyone struggling with this today. I found that for me worked a simple solution seen below