Sorry again if this is the wrong section, or if this question has been answered elsewhere (I doubt it, though: I haven’t had luck finding any help online).
I’m having a shader problem on mobile devices (both Android and iOS). In our racing game, we have a reflection shader applied to the cars. This shader takes a cube map and rotates it horizontally and vertically about the car. The shader works fine in the editor and most of the time on mobile, but occasionally - seemingly at random - the cars will appear black instead. Solid black, too: the texture isn’t visible, and lighting doesn’t seem to affect it. It can’t be a hardware support issue as the shader works most of the time, and the issue seems to occur on several different devices (iPhone 4, iPad Mini, Galaxy Tab 10.1, and HTC One, to name a few).
I’ve tried dozens and dozens of tests, but nothing conclusive. All test cases consist of reloading the scene containing one or more meshes with the shader in question. If the issue occurs, it’s noticeable immediately upon scene load. The repro rate is erratic: sometimes it happens within the first 10 tests, and other times it doesn’t happen for 30+, so it’s difficult to tell if I’m getting close to a solution.
One forum thread suggested using Handheld.ClearShaderCache(), but that didn’t have any noticeable effect.
I don’t think it’s hitting the fallback shader, as Mobile/Diffuse has no color property and should render the texture white.
I’ve tried this shader and it works on its own. I tried adding the rotation and color behavior from my original shader to this one piece by piece, but there doesn’t seem to be a single piece of logic to blame.
I’ve attached screenshots of a test scene: one of intended behavior and another of the issue. I’ve also pasted the shader code below. If anyone has any insight into this issue, I would be tremendously appreciative.
Shader "CustomShaders/CubemapReflect" {
Properties {
_Color ("Main Color", Color) = (1,1,1,1)
_ColorTint ("Diffuse Tint Color", Color) = (1.0, 1.0, 1.0, 1.0)
_ReflectColor ("Reflection Color", Color) = (1.0, 1.0, 1.0, 1.0)
_MainTex ("Texture", 2D) = "white" {}
_Cube ("Cubemap", CUBE) = "" {}
_Angle ("Cubemap Rotation", float) = 0
_Shininess ("Shininess", Float) = 0.5
}
SubShader {
Tags { "RenderType"="Opaque" }
CGPROGRAM
#pragma surface surf Lambert finalcolor:mycolor
struct Input
{
float2 uv_MainTex;
float3 worldRefl;
float2 uv_SideTex;
float3 worldNormal;
};
fixed4 _ReflectColor;
fixed4 _Color;
fixed4 _ColorTint;
sampler2D _MainTex;
samplerCUBE _Cube;
uniform float _Angle;
uniform float _Shininess;
void mycolor (Input IN, SurfaceOutput o, inout fixed4 color)
{
color *= _ColorTint;
}
void surf (Input IN, inout SurfaceOutput o)
{
// Apply the main texture
o.Albedo = tex2D (_MainTex, IN.uv_MainTex).rgb * _Color;
// Calculate the rotated top world reflection vector
float3 topVec = IN.worldRefl;
half cosa = cos(_Angle);
half sina = sin(_Angle);
half y = IN.worldRefl.y;
half z = IN.worldRefl.z;
topVec.x = 1;
topVec.y = y * cosa - z * sina;
topVec.z = y * sina + z * cosa;
// Calculate the rotated side world reflection vector
float3 sideVec = IN.worldRefl;
half x = IN.worldRefl.x;
sideVec.x = x * cosa - z * sina;
sideVec.y = 1;
sideVec.z = x * sina + z * cosa;
// Calculate and clamp the ratio
half ratio = (0.8 - IN.worldNormal.y) / 0.4;
ratio = ratio > 1 ? 1 : ratio;
ratio = ratio < 0 ? 0 : ratio;
// Apply the top and side cubemaps
o.Emission = texCUBE(_Cube, topVec).rgb * _ReflectColor.rgb * (1 - ratio) * _Shininess;
o.Emission += texCUBE (_Cube, sideVec).rgb * _ReflectColor.rgb * ratio * _Shininess;
}
ENDCG
}
FallBack "Mobile/Diffuse"
}

