Shader "Skinning/SkinnedSurfaceShader" {
Properties {
_MainTex ("Texture", 2D) = "white" {}
_Color ("Main Color", Color) = (1,1,1,1)
_BumpMap ("Normalmap", 2D) = "bump" {}
_SkinQuality ("Skin Quality", Int) = 1
}
SubShader {
Tags { "RenderType" = "Opaque" }
CGPROGRAM
#pragma surface surf Lambert
#pragma vertex vert
struct Input {
float2 uv_MainTex;
float2 uv_BumpMap;
};
float4x4 _Bones[200];
int _SkinQuality;
float4 GetBoneVertex(int boneId, float4 vertex){
float4x4 bone = _Bones[boneId];
return mul (bone, vertex);
}
float3 Lerp(float3 v1, float3 v2, float t){
return v1 += (v2-v1)*t;
}
float4 Blend2Bones(int id1, int id2, float w2, float4 vertex){
float4 v1 = GetBoneVertex(id1,vertex);
float4 v2 = GetBoneVertex(id2,vertex);
vertex.xyz = Lerp(v1,v2,w2);
return vertex;
}
float4 BlendMultipleBones(float4 ids, float4 weights, float4 vertex, int q){
float4 v0 = GetBoneVertex((int)ids[0],vertex);
float3 result = v0.xyz;
for(int i=1; i < q; i++){
float4 v1 = GetBoneVertex((int)ids[i],vertex);
result = Lerp(result,v1,weights[i]);
v0 = v1;
}
vertex.xyz = result;
return vertex;
}
float4 Blend4Bones(int id1, int id2, int id3, int id4, float w2, float w3, float w4, float4 vertex){
float4 v1 = GetBoneVertex(id1,vertex);
float4 v2 = GetBoneVertex(id2,vertex);
float4 v3 = GetBoneVertex(id3,vertex);
float4 v4 = GetBoneVertex(id4,vertex);
float3 l1 = Lerp(v1,v2,w2);
float3 l2 = Lerp(l1,v3,w3);
vertex.xyz = Lerp(l2,v4,w4);
return vertex;
}
void vert (inout appdata_full v) {
float4 vertex = v.vertex;
if(_SkinQuality < 2){
vertex = GetBoneVertex((int)(v.color.r), vertex);
}else if(_SkinQuality < 3){
vertex = Blend2Bones((int)(v.color.r),(int)(v.color.g), v.texcoord3.y, vertex);
}else{
vertex = BlendMultipleBones(v.color,v.texcoord3,vertex, _SkinQuality);
}
v.vertex = mul (_World2Object, vertex);
}
fixed4 _Color;
sampler2D _MainTex;
sampler2D _BumpMap;
void surf (Input IN, inout SurfaceOutput o) {
fixed4 tex = tex2D(_MainTex, IN.uv_MainTex);
o.Albedo = tex.rgb * _Color.rgb;
o.Gloss = tex.a;
o.Alpha = tex.a * _Color.a;
o.Normal = UnpackNormal(tex2D(_BumpMap, IN.uv_BumpMap));
}
ENDCG
}
FallBack "Diffuse"
}