title: Vertex gradient shader rotation?
body: <p>I have a shader that allows me to create and rotate a 2 or 3 color gradient. My problem was that it was very heavy on the GPU, so I moved this part of the code from the fragment shader to the vertex shader:</p>
  
  <pre><code> fixed4 frag (v2f i) : SV_Target
              {   
                  //STARTS HERE
                  float2 uv =  - (i.screenPos.xy / i.screenPos.w - 0.5)*2;
  
                  fixed3 c;                        
                  #if _BG_COLOR_GRADIENT2
                      c = lerp(_BgColor1,_BgColor3,clampValue(rotateUV(uv.xy,_BgColorRotation*PI).y,_BgColorPosition));                                            
                  #elif _BG_COLOR_GRADIENT3
                      c = lerp3(_BgColor1,_BgColor2,_BgColor3,clampValue(rotateUV(uv.xy,_BgColorRotation*PI).y,_BgColorPosition),_BgColorPosition3);
                  #endif 
                  //ENDS HERE         
  
                  return fixed4(c, i.color.a);
              }
  </code></pre>
  
  <p>Now my shader looks like this:</p>
  
  <pre><code>Shader "Custom/Gradient"
  {
      Properties
      {
          [KeywordEnum(Gradient2, Gradient3)] _BG_COLOR ("Color Type", Float) = 1
          _Color("Color", Color) = (1, 1, 1, 1)
          _BgColor1 ("Start Color",Color) = (0.667,0.851,0.937,1)
          _BgColor2 ("Middle Color",Color) = (0.29, 0.8, 0.2,1)
          _BgColor3 ("End Color",Color) = (0.29, 0.8, 0.2,1)
          [GradientPositionSliderDrawer]
          _BgColorPosition ("Gradient Position",Vector) = (0,1,0)
          _BgColorRotation ("Gradient Rotation",Range(0,2)) = 0
          _BgColorPosition3 ("Middle Size",Range(0,1)) = 0
  
      }
  
      SubShader
      {
          Tags{ "Queue" = "Background" "IgnoreProjectors"="True" }
  
          Blend SrcAlpha OneMinusSrcAlpha
          AlphaTest Greater .01
          ColorMask RGB
          Cull Off Lighting Off ZWrite Off
          BindChannels {
          Bind "Color", color
          Bind "Vertex", vertex
          Bind "TexCoord", texcoord
      }
  
      Pass
      {
          CGPROGRAM
          #pragma vertex vert
          #pragma fragment frag
  
          #pragma shader_feature _BG_COLOR_GRADIENT2 _BG_COLOR_GRADIENT3
  
          #include "UnityCG.cginc"
          #include "GradientHelper.cginc"
  
          struct appdata
          {
             float4 vertex : POSITION;
             fixed4 color : COLOR;
          };
  
          struct v2f
          {                
              float4 pos : SV_POSITION;
              float4 screenPos : TEXCOORD4;
              fixed4 color : COLOR;
          };
  
          fixed4 _BgColor1;
          fixed4 _BgColor2;
          fixed4 _BgColor3;
          float _BgColorRotation;
          float2 _BgColorPosition;
          float _BgColorPosition3;
          float4 _Color;
  
          v2f vert (appdata v)
          {
              v2f o;
              o.pos = UnityObjectToClipPos(v.vertex);
              o.screenPos = ComputeScreenPos(o.pos);
  
              float2 uv =  - (o.screenPos.xy / o.screenPos.w - 0.5)*2;                         
  
              #if _BG_COLOR_GRADIENT2
                  o.color = lerp(_BgColor1,_BgColor3,clampValue(rotateUV(uv.xy,_BgColorRotation*PI).y,_BgColorPosition)) * v.color;                                            
              #elif _BG_COLOR_GRADIENT3
                  o.color = lerp3(_BgColor1,_BgColor2,_BgColor3,clampValue(rotateUV(uv.xy,_BgColorRotation*PI).y,_BgColorPosition),_BgColorPosition3) * v.color;
              #endif
  
              return o;
          }
  
          fixed4 frag (v2f i) : COLOR {
              return i.color;
          }
          ENDCG
          }
      }
      CustomEditor "Background.Editor.BackgroundGradientEditor"
  }
  </code></pre>
  
  <p>(Here is my shader helper):</p>
  
  <pre><code>#ifndef PI
  #define PI 3.141592653589793
  #endif
  #ifndef HALF_PI
  #define HALF_PI 1.5707963267948966
  #endif
  
  // Helper Funtions
  
  inline float clampValue(float input, float2 limit) 
  {
      float minValue = 1-limit.y;
      float maxValue = 1-limit.x;
      if(input&lt;=minValue){
          return 0;
      } else if(input&gt;=maxValue){
          return 1;
      } else {
          return (input - minValue )/(maxValue-minValue);
      }                       
  }
  
  inline float2 rotateUV(fixed2 uv, float rotation) 
  {
      float sinX = sin (rotation);
      float cosX = cos (rotation);
      float2x2 rotationMatrix = float2x2(cosX, -sinX, sinX, cosX);
      return mul ( uv, rotationMatrix )/2 + 0.5;
  }
  
  inline fixed4 lerp3(fixed4 a, fixed4 b, fixed4 c, float pos, float size){
  
      float ratio2 = 0.5+size*0.5;
      float ratio1 = 1-ratio2;
      if(pos&lt;ratio1)
          return lerp(a,b,pos/ratio1);
      else if(pos&gt;ratio2)
          return lerp(b,c,(pos-ratio2)/ratio1);               
      else
          return b;
  }    
  #endif
  </code></pre>
  
  <p>The performance is great now, but the rotation is totally messed up (most noticeable on the 3 color gradient) and I can't seem to figure it out why.</p>