当前位置:   article > 正文

【Unity3D】广告牌特效_unity 广告牌

unity 广告牌

1 前言

        广告牌特效是指:空间中的一个 2D 对象始终(或尽可能)面向相机,使得用户能够尽可能看清楚该 2D 物体。广告牌特效一共有以下 3 种:

  • 正视广告牌:广告牌始终以正视图姿态面向相机,即广告牌的 x、y、z 轴正方向始终指向相机的 x、y、z 轴正方向;
  • 血条广告牌:游戏中的血条效果广告牌,广告牌可以绕世界坐标系的 y 轴旋转,使其尽可能面向相机,即广告牌的 x 轴正方向始终指向相机的 x 轴正方向,y 轴正方向始终指向 (0, 1, 0) 方向,z 轴正方向可以随相机位置和姿态变动;
  • 测距广告牌:测距时显示距离效果的广告牌,广告牌可以绕局部坐标系的 x 轴旋转,使其尽可能面向相机,即广告牌的 x 轴正方向固定不变,y、z 轴正方向可以随相机位置和姿态变动。

        本文完整资源见→Unity3D广告牌特效

2 正视广告牌

        正视广告牌是指:广告牌始终以正视图姿态面向相机,即广告牌的 x、y、z 轴正方向始终指向相机的 x、y、z 轴正方向。

        FrontView.shader

  1. Shader "MyShader/Billboard/FrontView" { // 正视广告牌
  2. Properties{
  3. _MainTex("Main Tex", 2D) = "white" {} // 材质纹理
  4. _Color("Color Tint", Color) = (1, 1, 1, 1) // 材质颜色
  5. }
  6. SubShader{
  7. // 批处理会合并所有相关的模型, 导致模型各自的模型空间丢失
  8. Tags {"Queue" = "Transparent" "IgnoreProjector" = "True" "RenderType" = "Transparent" "DisableBatching" = "True"}
  9. Pass {
  10. Tags { "LightMode" = "ForwardBase" }
  11. ZWrite Off
  12. Blend SrcAlpha OneMinusSrcAlpha
  13. Cull Off
  14. CGPROGRAM
  15. #pragma vertex vert
  16. #pragma fragment frag
  17. #include "Lighting.cginc"
  18. sampler2D _MainTex; // 材质纹理
  19. float4 _MainTex_ST; // 材质纹理的缩放和偏移
  20. fixed4 _Color; // 材质颜色
  21. struct a2v {
  22. float4 vertex : POSITION; // 模型空间顶点坐标
  23. half2 texcoord : TEXCOORD0; // 顶点纹理坐标
  24. };
  25. struct v2f {
  26. float4 pos : SV_POSITION; // 裁剪空间顶点坐标
  27. half2 uv : TEXCOORD0; // 顶点纹理坐标
  28. };
  29. v2f vert(a2v v) {
  30. v2f o;
  31. float3 center = mul(unity_ObjectToWorld, float4(0, 0, 0, 1)).xyz; // 世界坐标系中模型中心坐标
  32. float3 right = mul(unity_MatrixInvV, float4(1, 0, 0, 0)).xyz; // 世界坐标系中相机的right向量(广告牌的x轴)
  33. float3 up = mul(unity_MatrixInvV, float4(0, 1, 0, 0)).xyz; // 世界坐标系中相机的up向量(广告牌的y轴)
  34. float3 forward = mul(unity_MatrixInvV, float4(0, 0, 1, 0).xyz); // 世界坐标系中相机的forward向量(广告牌的z轴)
  35. float3 worldVec = mul(unity_ObjectToWorld, v.vertex).xyz - center; // 世界坐标系中模型中心指向顶点的向量
  36. float3 worldPos = center + worldVec.x * right + worldVec.y * up + worldVec.z * forward; // 世界坐标系中顶点坐标经过广告牌变换后的坐标
  37. o.pos = mul(unity_MatrixVP, float4(worldPos, 1)); // 裁剪坐标系中顶点坐标
  38. o.uv = TRANSFORM_TEX(v.texcoord, _MainTex); // 纹理uv坐标
  39. return o;
  40. }
  41. fixed4 frag(v2f i) : SV_Target {
  42. fixed4 color = tex2D(_MainTex, i.uv);
  43. color.rgb *= _Color.rgb;
  44. return color;
  45. }
  46. ENDCG
  47. }
  48. }
  49. FallBack "Transparent/VertexLit"
  50. }

        运行效果:

3 血条广告牌

        血条广告牌是指:游戏中的血条效果广告牌,广告牌可以绕世界坐标系的 y 轴旋转,使其尽可能面向相机,即广告牌的 x 轴正方向始终指向相机的 x 轴正方向,y 轴正方向始终指向 (0, 1, 0) 方向,z 轴正方向可以随相机位置和姿态变动。

        Lifebar.shader

  1. Shader "MyShader/Billboard/Lifebar" { // 血条广告牌
  2. Properties{
  3. _MainTex("Main Tex", 2D) = "white" {} // 材质纹理
  4. _Color("Color Tint", Color) = (1, 1, 1, 1) // 材质颜色
  5. }
  6. SubShader{
  7. // 批处理会合并所有相关的模型, 导致模型各自的模型空间丢失
  8. Tags {"Queue" = "Transparent" "IgnoreProjector" = "True" "RenderType" = "Transparent" "DisableBatching" = "True"}
  9. Pass {
  10. Tags { "LightMode" = "ForwardBase" }
  11. ZWrite Off
  12. Blend SrcAlpha OneMinusSrcAlpha
  13. Cull Off
  14. CGPROGRAM
  15. #pragma vertex vert
  16. #pragma fragment frag
  17. #include "Lighting.cginc"
  18. sampler2D _MainTex; // 材质纹理
  19. float4 _MainTex_ST; // 材质纹理的缩放和偏移
  20. fixed4 _Color; // 材质颜色
  21. struct a2v {
  22. float4 vertex : POSITION; // 模型空间顶点坐标
  23. half2 texcoord : TEXCOORD0; // 顶点纹理坐标
  24. };
  25. struct v2f {
  26. float4 pos : SV_POSITION; // 裁剪空间顶点坐标
  27. half2 uv : TEXCOORD0; // 顶点纹理坐标
  28. };
  29. v2f vert(a2v v) {
  30. v2f o;
  31. float3 center = mul(unity_ObjectToWorld, float4(0, 0, 0, 1)).xyz; // 世界坐标系中模型中心坐标
  32. float3 right = mul(unity_MatrixInvV, float4(1, 0, 0, 0)).xyz; // 世界坐标系中相机的right向量(广告牌的x轴)
  33. float3 up = float3(0, 1, 0); // 广告牌的y轴
  34. float3 forward = cross(right, up); // 广告牌的z轴
  35. float3 worldVec = mul(unity_ObjectToWorld, v.vertex).xyz - center; // 世界坐标系中模型中心指向顶点的向量
  36. float3 worldPos = center + worldVec.x * right + worldVec.y * up + worldVec.z * forward; // 世界坐标系中顶点坐标经过广告牌变换后的坐标
  37. o.pos = mul(unity_MatrixVP, float4(worldPos, 1)); // 裁剪坐标系中顶点坐标
  38. o.uv = TRANSFORM_TEX(v.texcoord, _MainTex); // 纹理uv坐标
  39. return o;
  40. }
  41. fixed4 frag(v2f i) : SV_Target {
  42. fixed4 color = tex2D(_MainTex, i.uv);
  43. color.rgb *= _Color.rgb;
  44. return color;
  45. }
  46. ENDCG
  47. }
  48. }
  49. FallBack "Transparent/VertexLit"
  50. }

        运行效果:

测距广告牌

        测距广告牌是指:测距时显示距离效果的广告牌,广告牌可以绕局部坐标系的 x 轴旋转,使其尽可能面向相机,即广告牌的 x 轴正方向固定不变,y、z 轴正方向可以随相机位置和姿态变动。

        MeasureDist.shader

  1. Shader "MyShader/Billboard/MeasureDist" { // 测距广告牌
  2. Properties{
  3. _MainTex("Main Tex", 2D) = "white" {} // 材质纹理
  4. _Color("Color Tint", Color) = (1, 1, 1, 1) // 材质颜色
  5. }
  6. SubShader{
  7. // 批处理会合并所有相关的模型, 导致模型各自的模型空间丢失
  8. Tags {"Queue" = "Transparent" "IgnoreProjector" = "True" "RenderType" = "Transparent" "DisableBatching" = "True"}
  9. Pass {
  10. Tags { "LightMode" = "ForwardBase" }
  11. ZWrite Off
  12. Blend SrcAlpha OneMinusSrcAlpha
  13. Cull Off
  14. CGPROGRAM
  15. #pragma vertex vert
  16. #pragma fragment frag
  17. #include "Lighting.cginc"
  18. sampler2D _MainTex; // 材质纹理
  19. float4 _MainTex_ST; // 材质纹理的缩放和偏移
  20. fixed4 _Color; // 材质颜色
  21. struct a2v {
  22. float4 vertex : POSITION; // 模型空间顶点坐标
  23. half2 texcoord : TEXCOORD0; // 顶点纹理坐标
  24. };
  25. struct v2f {
  26. float4 pos : SV_POSITION; // 裁剪空间顶点坐标
  27. half2 uv : TEXCOORD0; // 顶点纹理坐标
  28. };
  29. v2f vert(a2v v) {
  30. v2f o;
  31. float3 forwardDire = mul(unity_ObjectToWorld, float4(0, 0, 1, 0)).xyz; // 世界坐标系中模型的forward向量
  32. float3 center = mul(unity_ObjectToWorld, float4(0, 0, 0, 1)).xyz; // 世界坐标系中模型中心坐标
  33. float3 viewDire = normalize(center - _WorldSpaceCameraPos.xyz); // 观察向量, 相机指向顶点
  34. float3 right = normalize(mul(unity_ObjectToWorld, float4(1, 0, 0, 0)).xyz) * sign(dot(viewDire, forwardDire)); // 世界坐标系中模型的right向量(广告牌的x轴)
  35. float3 up = cross(viewDire, right); // 广告牌的y轴
  36. float3 forward = cross(right, up); // 广告牌的z轴
  37. float3 worldVec = mul(unity_ObjectToWorld, v.vertex).xyz - center; // 世界坐标系中模型中心指向顶点的向量
  38. float3 worldPos = center + worldVec.x * right + worldVec.y * up + worldVec.z * forward; // 世界坐标系中顶点坐标经过广告牌变换后的坐标
  39. o.pos = mul(unity_MatrixVP, float4(worldPos, 1)); // 裁剪坐标系中顶点坐标
  40. o.uv = TRANSFORM_TEX(v.texcoord, _MainTex); // 纹理uv坐标
  41. return o;
  42. }
  43. fixed4 frag(v2f i) : SV_Target {
  44. fixed4 color = tex2D(_MainTex, i.uv);
  45. color.rgb *= _Color.rgb;
  46. return color;
  47. }
  48. ENDCG
  49. }
  50. }
  51. FallBack "Transparent/VertexLit"
  52. }

        运行效果:

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/IT小白/article/detail/118035
推荐阅读
相关标签
  

闽ICP备14008679号