我正试图编写一个类似于Unity手册中的着色器,该着色器通过Clip()函数丢弃几乎水平的环中的像素来"切片"对象。
Shader "Example/Slices" {
Properties {
_MainTex ("Texture", 2D) = "white" {}
_BumpMap ("Bumpmap", 2D) = "bump" {}
}
SubShader {
Tags { "RenderType" = "Opaque" }
Cull Off
CGPROGRAM
#pragma surface surf Lambert
struct Input {
float2 uv_MainTex;
float2 uv_BumpMap;
float3 worldPos;
};
sampler2D _MainTex;
sampler2D _BumpMap;
void surf (Input IN, inout SurfaceOutput o) {
clip (frac((IN.worldPos.y+IN.worldPos.z*0.1) * 5) - 0.5);
o.Albedo = tex2D (_MainTex, IN.uv_MainTex).rgb;
o.Normal = UnpackNormal (tex2D (_BumpMap, IN.uv_BumpMap));
}
ENDCG
}
Fallback "Diffuse"
}
我希望能够以任意角度进行切片,而不仅仅是水平线。我通过实验发现(因为我是着色器编码的新手),worldPos Z上的乘数确实会改变切片的角度,所以我为它设置了一个属性变量:
clip (frac((IN.worldPos.y+IN.worldPos.z*_MYANGLEVARIABLE) * 5) - 0.5);
然而,这有两个问题。1) 最大值为1.0时,线会旋转45度,但超过此值后,线会开始"扭曲"并卷积成各种图案,而不是整齐的线。2)只有当面朝向正或负X轴时,这才有效。当面对Z时,线不会移动,当面对Y时,线会变大,但不会旋转。
将IN.worldPos.y
更改为IN.worldPos.x
可以达到您的预期效果-类似的情况,但在Z而不是X中按预期工作。
有什么想法吗1) 实现任意角度?2) 让他们不管朝向哪个方向都工作吗?
我使用worlPos是因为我总是希望线条相对于对象,而不是屏幕空间,但也许还有其他方法?我实际的着色器是一个片段,而不是一个表面着色器&我正在把worldPos从vert传给frag。
非常感谢
要获得任意角度,可以使用法向量定义平面,并使用点积进行剪裁。
Shader "Example/Slices" {
Properties {
_MainTex ("Texture", 2D) = "white" {}
_BumpMap ("Bumpmap", 2D) = "bump" {}
_PlaneNormal ("Plane Normal", Vector) = (0, 1, 0)
}
SubShader {
Tags { "RenderType" = "Opaque" }
Cull Off
CGPROGRAM
#pragma surface surf Lambert
struct Input {
float2 uv_MainTex;
float2 uv_BumpMap;
float3 worldPos;
};
sampler2D _MainTex;
sampler2D _BumpMap;
float3 _PlaneNormal;
void surf (Input IN, inout SurfaceOutput o) {
float d = dot(_PlaneNormal, IN.worldPos);
clip (frac(d) - 0.5);
o.Albedo = tex2D (_MainTex, IN.uv_MainTex).rgb;
o.Normal = UnpackNormal (tex2D (_BumpMap, IN.uv_BumpMap));
}
ENDCG
}
Fallback "Diffuse"
}
这里的法向量越长,切片就越频繁。
如果希望切片相对于对象,则需要使用除worldPos之外的一组坐标。这个答案可能会有所帮助:http://answers.unity3d.com/questions/561900/get-local-position-in-surface-shader.html