【Unity3D】Particle粒子特效或3D物体显示在UGUI上的方案
目录
一、RawImage + Camera + RenderTexture方式
(1)扩展知识:实现射线检测RawImage内的3D物体
(2)扩展知识:实现粒子特效显示RawImage上
二、UI摄像机 + Canvas(Screen Space - Camera模式)方式
(1)尝试使用模板测试裁剪粒子特效(失败案例)
(2)传递Mask区域Rect数据进行裁剪粒子特效
一、RawImage + Camera + RenderTexture方式
(1)扩展知识:实现射线检测RawImage内的3D物体
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;public class SphereTest : MonoBehaviour
{//是否忽略UI检测public bool ignoreUICheck = false;//发送射线的摄像机public Camera rayCamera;public RectTransform canvasRectTrans;public Camera uiCamera;public RectTransform rawImageRectTrans;// Update is called once per framevoid Update(){if (Input.GetMouseButtonDown(0)){
#if (UNITY_ANDROID || UNITY_IOS) && !UNITY_EDITORif (!ignoreUICheck && EventSystem.current.IsPointerOverGameObject(Input.GetTouch(0).fingerId))
#elseif (!ignoreUICheck && EventSystem.current.IsPointerOverGameObject(-1))
#endif{Debug.Log("点击到UI物体:" + EventSystem.current.currentSelectedGameObject);}else{//ScreenPointToRay仅适用于主摄像机的射线(主摄像机即MainCamera 直接渲染到屏幕的)//针对RawImage内的3D物体进行射线检测,首先要使用渲染3D物体的摄像机(非主摄像机,它深度会被我们调到比主摄像机低,以及CullingMask剔除掉这层的物体)//其次是无法使用ScreenPointToRay检测到的,即使你将3D物体和摄像机都挪到主摄像机相同的位置朝向..//使用ViewportPointToRay转用视角发射射线, 获取RawImage视角坐标需要将屏幕点击坐标转RawImage所在Canvas的UI坐标,再转到RawImage空间的视角坐标//1.利用API(RectTransformUtility.ScreenPointToLocalPointInRectangle)将屏幕坐标点击位置转化为UGUI坐标Vector2 uiPos;if (RectTransformUtility.ScreenPointToLocalPointInRectangle(canvasRectTrans, Input.mousePosition, uiCamera, out uiPos)){//2.转RawImage空间的视角坐标,需知道uiPos相对该空间的位置,以及该空间的宽高//2.1获取RawImage物体的x,y,width,height (位于Canvas空间内的)float width = rawImageRectTrans.rect.width;float height = rawImageRectTrans.rect.height;float x = rawImageRectTrans.localPosition.x - (width * rawImageRectTrans.pivot.x);float y = rawImageRectTrans.localPosition.y - (height * rawImageRectTrans.pivot.y);//2.2根据上述参数求出uiPos位于RawImage空间的相对位置float uiPosXRelativeRawImage = (uiPos.x - x) / width;float uiPosYRelativeRawImage = (uiPos.y - y) / height;Vector2 relativeRawImagePos = new Vector2(uiPosXRelativeRawImage, uiPosYRelativeRawImage);Ray ray = rayCamera.ViewportPointToRay(relativeRawImagePos);RaycastHit raycastHit;if (Physics.Raycast(ray, out raycastHit, 1000)){if (raycastHit.collider.gameObject != null){Debug.Log("点击3D物体:" + raycastHit.collider.gameObject);}}Debug.DrawLine(ray.origin, raycastHit.point, Color.red, 1);}}}}
}
(2)扩展知识:实现粒子特效显示RawImage上
由于粒子特效的ColorMask默认是RGB,没有A(透明通道),而渲染粒子特效的摄像机Background的Alpha是0,就会导致没有A通道的是无法被摄像机渲染出来的(反正测试是这样)
因此我们需要修改粒子特效的Shader,去官网下载对应Unity版本的Shader源码找到对应的shader文件拷贝到我们工程内开始修改。
Unity官方下载_Unity新版_从Unity Hub下载安装 | Unity中国官网
修改如下2个地方,以保证粒子特效渲染于透明层级以及开放RGBA通道渲染
Tags {"Queue" = "Transparent"
}ColorMask RGBA
二、UI摄像机 + Canvas(Screen Space - Camera模式)方式
注意ClearFlags是清空所有位于它前面的摄像机缓存到ColorBuffer和DeepBuffer的,位于前面是指深度小于当前摄像机的。
此处是仅清空了深度(Deep Only),背景颜色保持用主摄像机。
选中Canvas,右击创建粒子特效,会帮你默认处理将粒子特效的Layer设置为UI
想让粒子特效显示的层级高于UI的Image则使用如下图控制,大于Canvas的Order即可。
正常显示出粒子特效,但发现没法被Mask组件裁剪,因为Mask裁剪原理是模板测试裁剪,而粒子特效Shader并没有模板测试,也尝试过将模板测试写到粒子特效Shader中,但是观察FrameDebugger发现其渲染是在Mask恢复了模板值为0之后进行的,所以这种依赖模板测试的方式裁剪行不通,具体如下图说明一切。
(1)尝试使用模板测试裁剪粒子特效(失败案例)
如果我将粒子特效的模板值改为0去比较,那肯定通过测试,全都会被渲染出来
(2)传递Mask区域Rect数据进行裁剪粒子特效
原理:传递Mask区域的左下角和右上角世界坐标到粒子Shader进行一个是否在(左下角,右上角)区域内判定,若不在则将透明度设置为0,达到裁剪目的。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;public class MyMask : MonoBehaviour
{public Camera uiCamera;public ParticleSystem particle;public RectTransform canvasRectTrans;private void Start(){var renderer = particle.GetComponent<ParticleSystemRenderer>();Material particleMat = renderer.material;//获取Mask裁剪区域四个点坐标RectTransform rectTransform = this.gameObject.GetComponent<RectTransform>();Vector3[] worldPosArray = new Vector3[4];rectTransform.GetWorldCorners(worldPosArray);Vector3 lbPos = worldPosArray[0];Vector3 rtPos = worldPosArray[2];//针对3D物体裁剪(粒子特效也是3D),需传递3D空间坐标(即世界坐标)particleMat.SetVector("_CustomClipRect", new Vector4(lbPos.x, lbPos.y, rtPos.x, rtPos.y));//注意 若针对UI裁剪,这必须传递UI空间系的坐标,如下注释内容...//lbPos = uiCamera.WorldToScreenPoint(lbPos);//rtPos = uiCamera.WorldToScreenPoint(rtPos);//Vector2 lbLocalPos = Vector2.zero;//Vector2 rtLocalPos = Vector2.zero;//RectTransformUtility.ScreenPointToLocalPointInRectangle(canvasRectTrans, lbPos, uiCamera, out lbLocalPos);//RectTransformUtility.ScreenPointToLocalPointInRectangle(canvasRectTrans, rtPos, uiCamera, out rtLocalPos);//particleMat.SetVector("_CustomClipRect", new Vector4(lbLocalPos.x, lbLocalPos.y, rtLocalPos.x, rtLocalPos.y));}
}
解释下为什么传递的是世界坐标系的Mask区域,因为Shader使用的是将vertex模型坐标转世界坐标后传递到frag,此时frag的worldPosition是精细化的粒子特效世界坐标,因此需要用同样是世界坐标的坐标进行计算。
若是UI裁剪,则必须传递的是Canvas空间下的坐标,否则无法正常裁剪,原因猜测就是UI是隶属于Canvas的,其Shader内的世界坐标也只是对应于Canvas空间下的世界坐标,而粒子特效是3D物体,不隶属Canvas这种特殊空间,所以正常传递世界坐标。
粒子特效Shader改动点如下:
Properties
{_CustomClipRect("CustomClipRect", vector) = (0,0,0,0)
}
Pass
{
Tags { Queue="Transparent" }Blend SrcAlpha OneMinusSrcAlpha CGPROGRAM#include "UnityUI.cginc"struct appdata_particles
{float4 vertex : POSITION;
};struct VertexOutput
{float4 worldPosition : TEXCOORD5;
};void vertParticleUnlit(appdata_particles v, out VertexOutput o)
{//o.worldPosition = v.vertex; //这行也是正常的,但稳妥起见还是转世界坐标o.worldPosition = mul(v.vertex, unity_ObjectToWorld);
}half4 fragParticleUnlit(VertexOutput IN) : SV_Target
{result.a *= UnityGet2DClipping(IN.worldPosition.xy, _CustomClipRect);
}ENDCG
}
Shader代码:(源码是针对Particles/Standard Unlit修改,注释了很多Pass...)
// Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)Shader "Custom/Standard Unlit"
{Properties{_MainTex("Albedo", 2D) = "white" {}_Color("Color", Color) = (1,1,1,1)_Cutoff("Alpha Cutoff", Range(0.0, 1.0)) = 0.5_BumpScale("Scale", Float) = 1.0_BumpMap("Normal Map", 2D) = "bump" {}_EmissionColor("Color", Color) = (0,0,0)_EmissionMap("Emission", 2D) = "white" {}_DistortionStrength("Strength", Float) = 1.0_DistortionBlend("Blend", Range(0.0, 1.0)) = 0.5_SoftParticlesNearFadeDistance("Soft Particles Near Fade", Float) = 0.0_SoftParticlesFarFadeDistance("Soft Particles Far Fade", Float) = 1.0_CameraNearFadeDistance("Camera Near Fade", Float) = 1.0_CameraFarFadeDistance("Camera Far Fade", Float) = 2.0_StencilComp("Stencil Comparison", Float) = 8_Stencil("Stencil ID", Float) = 0_StencilOp("Stencil Operation", Float) = 0_StencilWriteMask("Stencil Write Mask", Float) = 255_StencilReadMask("Stencil Read Mask", Float) = 255_ColorMask("Color Mask", Float) = 15_CustomClipRect("CustomClipRect", vector) = (0,0,0,0)// Hidden properties[HideInInspector] _Mode("__mode", Float) = 0.0[HideInInspector] _ColorMode("__colormode", Float) = 0.0[HideInInspector] _FlipbookMode("__flipbookmode", Float) = 0.0[HideInInspector] _LightingEnabled("__lightingenabled", Float) = 0.0[HideInInspector] _DistortionEnabled("__distortionenabled", Float) = 0.0[HideInInspector] _EmissionEnabled("__emissionenabled", Float) = 0.0[HideInInspector] _BlendOp("__blendop", Float) = 0.0[HideInInspector] _SrcBlend("__src", Float) = 1.0[HideInInspector] _DstBlend("__dst", Float) = 0.0[HideInInspector] _ZWrite("__zw", Float) = 1.0[HideInInspector] _Cull("__cull", Float) = 2.0[HideInInspector] _SoftParticlesEnabled("__softparticlesenabled", Float) = 0.0[HideInInspector] _CameraFadingEnabled("__camerafadingenabled", Float) = 0.0[HideInInspector] _SoftParticleFadeParams("__softparticlefadeparams", Vector) = (0,0,0,0)[HideInInspector] _CameraFadeParams("__camerafadeparams", Vector) = (0,0,0,0)[HideInInspector] _ColorAddSubDiff("__coloraddsubdiff", Vector) = (0,0,0,0)[HideInInspector] _DistortionStrengthScaled("__distortionstrengthscaled", Float) = 0.0}Category{SubShader{Tags {"Queue" = "Transparent""IgnoreProjector" = "True""RenderType" = "Transparent" "PreviewType" = "Plane" "PerformanceChecks" = "False" }BlendOp[_BlendOp]Blend[_SrcBlend][_DstBlend]ZWrite[_ZWrite]Lighting OffCull[_Cull] ColorMask [_ColorMask] Stencil{Ref[_Stencil]Comp[_StencilComp]Pass[_StencilOp]ReadMask[_StencilReadMask]WriteMask[_StencilWriteMask]}GrabPass{Tags { "LightMode" = "Always" }"_GrabTexture"}/* Pass{Name "ShadowCaster"Tags { "LightMode" = "ShadowCaster" }BlendOp AddBlend One ZeroZWrite OnCull OffCGPROGRAM#pragma target 2.5#pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON _ALPHAMODULATE_ON#pragma shader_feature_local _ _COLOROVERLAY_ON _COLORCOLOR_ON _COLORADDSUBDIFF_ON#pragma shader_feature_local _REQUIRE_UV2#pragma multi_compile_shadowcaster#pragma multi_compile_instancing#pragma instancing_options procedural:vertInstancingSetup#pragma vertex vertParticleShadowCaster#pragma fragment fragParticleShadowCaster#include "UnityStandardParticleShadow.cginc"ENDCG}*//* Pass{Name "SceneSelectionPass"Tags { "LightMode" = "SceneSelectionPass" }BlendOp AddBlend One ZeroZWrite OnCull OffCGPROGRAM#pragma target 2.5#pragma shader_feature_local _ALPHATEST_ON#pragma shader_feature_local _REQUIRE_UV2#pragma multi_compile_instancing#pragma instancing_options procedural:vertInstancingSetup#pragma vertex vertEditorPass#pragma fragment fragSceneHighlightPass#include "UnityStandardParticleEditor.cginc"ENDCG}*//* Pass{Name "ScenePickingPass"Tags{ "LightMode" = "Picking" }BlendOp AddBlend One ZeroZWrite OnCull OffCGPROGRAM#pragma target 2.5#pragma shader_feature_local _ALPHATEST_ON#pragma shader_feature_local _REQUIRE_UV2#pragma multi_compile_instancing#pragma instancing_options procedural:vertInstancingSetup#pragma vertex vertEditorPass#pragma fragment fragScenePickingPass#include "UnityStandardParticleEditor.cginc"ENDCG}*/Pass{Tags { "LightMode" = "ForwardBase" }Blend SrcAlpha OneMinusSrcAlpha CGPROGRAM#pragma multi_compile __ SOFTPARTICLES_ON#pragma multi_compile_fog#pragma target 2.5#pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON _ALPHAMODULATE_ON#pragma shader_feature_local _ _COLOROVERLAY_ON _COLORCOLOR_ON _COLORADDSUBDIFF_ON#pragma shader_feature_local _NORMALMAP#pragma shader_feature _EMISSION#pragma shader_feature_local _FADING_ON#pragma shader_feature_local _REQUIRE_UV2#pragma shader_feature_local EFFECT_BUMP#pragma vertex vertParticleUnlit#pragma fragment fragParticleUnlit#pragma multi_compile_instancing#pragma instancing_options procedural:vertInstancingSetup//#include "UnityStandardParticles.cginc"// Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)#ifndef UNITY_STANDARD_PARTICLES_INCLUDED
#define UNITY_STANDARD_PARTICLES_INCLUDED#if _REQUIRE_UV2
#define _FLIPBOOK_BLENDING 1
#endif#if EFFECT_BUMP
#define _DISTORTION_ON 1
#endif#include "UnityPBSLighting.cginc"
#include "UnityStandardParticleInstancing.cginc"
#include "UnityUI.cginc"// Particles surface shader has a lot of variants in it, but some of those do not affect
// code generation (i.e. don't have inpact on which Input/SurfaceOutput things are read or written into).
// Surface shader analysis done during import time skips "completely identical" shader variants, so to
// help this process we'll turn off some features that we know are not affecting the inputs/outputs.
//
// If you change the logic of what the below variants do, make sure to not regress code generation though,
// e.g. compare full "show generated code" output of the surface shader before & after the change.
#if defined(SHADER_TARGET_SURFACE_ANALYSIS)// All these only alter the color in various ways#undef _COLOROVERLAY_ON#undef _COLORCOLOR_ON#undef _COLORADDSUBDIFF_ON#undef _ALPHAMODULATE_ON#undef _ALPHATEST_ON// For inputs/outputs analysis SoftParticles and Fading are identical; so make sure to only keep one// of them ever defined.#if defined(SOFTPARTICLES_ON)#undef SOFTPARTICLES_ON#define _FADING_ON#endif
#endif// Vertex shader input
struct appdata_particles
{float4 vertex : POSITION;float3 normal : NORMAL;fixed4 color : COLOR;#if defined(_FLIPBOOK_BLENDING) && !defined(UNITY_PARTICLE_INSTANCING_ENABLED)float4 texcoords : TEXCOORD0;float texcoordBlend : TEXCOORD1;#elsefloat2 texcoords : TEXCOORD0;#endif#if defined(_NORMALMAP)float4 tangent : TANGENT;#endifUNITY_VERTEX_INPUT_INSTANCE_ID
};// Surface shader inputstruct Input{float4 color : COLOR;float2 texcoord;#if defined(_FLIPBOOK_BLENDING)float3 texcoord2AndBlend;#endif#if defined(SOFTPARTICLES_ON) || defined(_FADING_ON)float4 projectedPosition;#endif#if _DISTORTION_ONfloat4 grabPassPosition;#endif};// Non-surface shader v2f structurestruct VertexOutput{float4 vertex : SV_POSITION;float4 color : COLOR;UNITY_FOG_COORDS(0)float2 texcoord : TEXCOORD1;#if defined(_FLIPBOOK_BLENDING)float3 texcoord2AndBlend : TEXCOORD2;#endif#if defined(SOFTPARTICLES_ON) || defined(_FADING_ON)float4 projectedPosition : TEXCOORD3;#endif#if _DISTORTION_ONfloat4 grabPassPosition : TEXCOORD4;#endiffloat4 worldPosition : TEXCOORD5;UNITY_VERTEX_OUTPUT_STEREO};fixed4 readTexture(sampler2D tex, Input IN){fixed4 color = tex2D(tex, IN.texcoord);#ifdef _FLIPBOOK_BLENDINGfixed4 color2 = tex2D(tex, IN.texcoord2AndBlend.xy);color = lerp(color, color2, IN.texcoord2AndBlend.z);#endifreturn color;}fixed4 readTexture(sampler2D tex, VertexOutput IN){fixed4 color = tex2D(tex, IN.texcoord);#ifdef _FLIPBOOK_BLENDINGfixed4 color2 = tex2D(tex, IN.texcoord2AndBlend.xy);color = lerp(color, color2, IN.texcoord2AndBlend.z);#endifreturn color;}sampler2D _MainTex;float4 _MainTex_ST;half4 _Color;sampler2D _BumpMap;half _BumpScale;sampler2D _EmissionMap;half3 _EmissionColor;sampler2D _MetallicGlossMap;half _Metallic;half _Glossiness;UNITY_DECLARE_DEPTH_TEXTURE(_CameraDepthTexture);float4 _SoftParticleFadeParams;float4 _CameraFadeParams;half _Cutoff;#define SOFT_PARTICLE_NEAR_FADE _SoftParticleFadeParams.x#define SOFT_PARTICLE_INV_FADE_DISTANCE _SoftParticleFadeParams.y#define CAMERA_NEAR_FADE _CameraFadeParams.x#define CAMERA_INV_FADE_DISTANCE _CameraFadeParams.y#if _DISTORTION_ONsampler2D _GrabTexture;half _DistortionStrengthScaled;half _DistortionBlend;#endif#if defined (_COLORADDSUBDIFF_ON)half4 _ColorAddSubDiff;#endif#if defined(_COLORCOLOR_ON)half3 RGBtoHSV(half3 arg1){half4 K = half4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0);half4 P = lerp(half4(arg1.bg, K.wz), half4(arg1.gb, K.xy), step(arg1.b, arg1.g));half4 Q = lerp(half4(P.xyw, arg1.r), half4(arg1.r, P.yzx), step(P.x, arg1.r));half D = Q.x - min(Q.w, Q.y);half E = 1e-10;return half3(abs(Q.z + (Q.w - Q.y) / (6.0 * D + E)), D / (Q.x + E), Q.x);}half3 HSVtoRGB(half3 arg1){half4 K = half4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);half3 P = abs(frac(arg1.xxx + K.xyz) * 6.0 - K.www);return arg1.z * lerp(K.xxx, saturate(P - K.xxx), arg1.y);}#endif// Color function#if defined(UNITY_PARTICLE_INSTANCING_ENABLED)#define vertColor(c) \vertInstancingColor(c);#else#define vertColor(c)#endif// Flipbook vertex function#if defined(UNITY_PARTICLE_INSTANCING_ENABLED)#if defined(_FLIPBOOK_BLENDING)#define vertTexcoord(v, o) \vertInstancingUVs(v.texcoords.xy, o.texcoord, o.texcoord2AndBlend);#else#define vertTexcoord(v, o) \vertInstancingUVs(v.texcoords.xy, o.texcoord); \o.texcoord = TRANSFORM_TEX(o.texcoord, _MainTex);#endif#else#if defined(_FLIPBOOK_BLENDING)#define vertTexcoord(v, o) \o.texcoord = v.texcoords.xy; \o.texcoord2AndBlend.xy = v.texcoords.zw; \o.texcoord2AndBlend.z = v.texcoordBlend;#else#define vertTexcoord(v, o) \o.texcoord = TRANSFORM_TEX(v.texcoords.xy, _MainTex);#endif#endif// Fading vertex function#if defined(SOFTPARTICLES_ON) || defined(_FADING_ON)#define vertFading(o) \o.projectedPosition = ComputeScreenPos (clipPosition); \COMPUTE_EYEDEPTH(o.projectedPosition.z);#else#define vertFading(o)#endif// Distortion vertex function#if _DISTORTION_ON#define vertDistortion(o) \o.grabPassPosition = ComputeGrabScreenPos (clipPosition);#else#define vertDistortion(o)#endif// Color blending fragment function#if defined(_COLOROVERLAY_ON)#define fragColorMode(i) \albedo.rgb = lerp(1 - 2 * (1 - albedo.rgb) * (1 - i.color.rgb), 2 * albedo.rgb * i.color.rgb, step(albedo.rgb, 0.5)); \albedo.a *= i.color.a;#elif defined(_COLORCOLOR_ON)#define fragColorMode(i) \half3 aHSL = RGBtoHSV(albedo.rgb); \half3 bHSL = RGBtoHSV(i.color.rgb); \half3 rHSL = fixed3(bHSL.x, bHSL.y, aHSL.z); \albedo = fixed4(HSVtoRGB(rHSL), albedo.a * i.color.a);#elif defined(_COLORADDSUBDIFF_ON)#define fragColorMode(i) \albedo.rgb = albedo.rgb + i.color.rgb * _ColorAddSubDiff.x; \albedo.rgb = lerp(albedo.rgb, abs(albedo.rgb), _ColorAddSubDiff.y); \albedo.a *= i.color.a;#else#define fragColorMode(i) \albedo *= i.color;#endif// Pre-multiplied alpha helper#if defined(_ALPHAPREMULTIPLY_ON)#define ALBEDO_MUL albedo#else#define ALBEDO_MUL albedo.a#endif// Soft particles fragment function#if defined(SOFTPARTICLES_ON) && defined(_FADING_ON)#define fragSoftParticles(i) \float softParticlesFade = 1.0f; \if (SOFT_PARTICLE_NEAR_FADE > 0.0 || SOFT_PARTICLE_INV_FADE_DISTANCE > 0.0) \{ \float sceneZ = LinearEyeDepth (SAMPLE_DEPTH_TEXTURE_PROJ(_CameraDepthTexture, UNITY_PROJ_COORD(i.projectedPosition))); \softParticlesFade = saturate (SOFT_PARTICLE_INV_FADE_DISTANCE * ((sceneZ - SOFT_PARTICLE_NEAR_FADE) - i.projectedPosition.z)); \ALBEDO_MUL *= softParticlesFade; \}#else#define fragSoftParticles(i) \float softParticlesFade = 1.0f;#endif// Camera fading fragment function#if defined(_FADING_ON)#define fragCameraFading(i) \float cameraFade = saturate((i.projectedPosition.z - CAMERA_NEAR_FADE) * CAMERA_INV_FADE_DISTANCE); \ALBEDO_MUL *= cameraFade;#else#define fragCameraFading(i) \float cameraFade = 1.0f;#endif#if _DISTORTION_ON#define fragDistortion(i) \float4 grabPosUV = UNITY_PROJ_COORD(i.grabPassPosition); \grabPosUV.xy += normal.xy * _DistortionStrengthScaled * albedo.a; \half3 grabPass = tex2Dproj(_GrabTexture, grabPosUV).rgb; \albedo.rgb = lerp(grabPass, albedo.rgb, saturate(albedo.a - _DistortionBlend));#else#define fragDistortion(i)#endiffloat4 _CustomClipRect;void vert(inout appdata_particles v, out Input o){UNITY_INITIALIZE_OUTPUT(Input, o);float4 clipPosition = UnityObjectToClipPos(v.vertex);vertColor(v.color);vertTexcoord(v, o);vertFading(o);vertDistortion(o);}void surf(Input IN, inout SurfaceOutputStandard o){half4 albedo = readTexture(_MainTex, IN);albedo *= _Color;fragColorMode(IN);fragSoftParticles(IN);fragCameraFading(IN);#if defined(_METALLICGLOSSMAP)fixed2 metallicGloss = readTexture(_MetallicGlossMap, IN).ra * fixed2(1.0, _Glossiness);#elsefixed2 metallicGloss = fixed2(_Metallic, _Glossiness);#endif#if defined(_NORMALMAP)float3 normal = normalize(UnpackScaleNormal(readTexture(_BumpMap, IN), _BumpScale));#elsefloat3 normal = float3(0,0,1);#endif#if defined(_EMISSION)half3 emission = readTexture(_EmissionMap, IN).rgb * cameraFade * softParticlesFade;#elsehalf3 emission = 0;#endiffragDistortion(IN);o.Albedo = albedo.rgb;#if defined(_NORMALMAP)o.Normal = normal;#endifo.Emission = emission * _EmissionColor;o.Metallic = metallicGloss.r;o.Smoothness = metallicGloss.g;#if defined(_ALPHABLEND_ON) || defined(_ALPHAPREMULTIPLY_ON) || defined(_ALPHAOVERLAY_ON)o.Alpha = albedo.a;#elseo.Alpha = 1;#endif#if defined(_ALPHAMODULATE_ON)o.Albedo = lerp(half3(1.0, 1.0, 1.0), albedo.rgb, albedo.a);#endif#if defined(_ALPHATEST_ON)clip(albedo.a - _Cutoff + 0.0001);#endif}void vertParticleUnlit(appdata_particles v, out VertexOutput o){UNITY_SETUP_INSTANCE_ID(v);UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(o);o.worldPosition = v.vertex;float4 clipPosition = UnityObjectToClipPos(v.vertex);o.vertex = clipPosition;o.color = v.color; vertColor(o.color);vertTexcoord(v, o);vertFading(o);vertDistortion(o);UNITY_TRANSFER_FOG(o, o.vertex);}half4 fragParticleUnlit(VertexOutput IN) : SV_Target{half4 albedo = readTexture(_MainTex, IN);albedo *= _Color;fragColorMode(IN);fragSoftParticles(IN);fragCameraFading(IN);#if defined(_NORMALMAP)float3 normal = normalize(UnpackScaleNormal(readTexture(_BumpMap, IN), _BumpScale));#elsefloat3 normal = float3(0,0,1);#endif#if defined(_EMISSION)half3 emission = readTexture(_EmissionMap, IN).rgb;#elsehalf3 emission = 0;#endiffragDistortion(IN);half4 result = albedo;#if defined(_ALPHAMODULATE_ON)result.rgb = lerp(half3(1.0, 1.0, 1.0), albedo.rgb, albedo.a);#endifresult.rgb += emission * _EmissionColor * cameraFade * softParticlesFade;#if !defined(_ALPHABLEND_ON) && !defined(_ALPHAPREMULTIPLY_ON) && !defined(_ALPHAOVERLAY_ON)result.a = 1;#endifresult.a *= UnityGet2DClipping(IN.worldPosition.xy, _CustomClipRect);#if defined(_ALPHATEST_ON)clip(albedo.a - _Cutoff + 0.0001);#endifUNITY_APPLY_FOG_COLOR(IN.fogCoord, result, fixed4(0,0,0,0));return result;}#endif // UNITY_STANDARD_PARTICLES_INCLUDEDENDCG}}}Fallback "VertexLit"//CustomEditor "StandardParticlesShaderGUI"
}
测试针对UI(2D物体)的裁剪