Unity3D粒子系统ParticleSystem

Posted little_fat_sheep

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Unity3D粒子系统ParticleSystem相关的知识,希望对你有一定的参考价值。

1 简介

        拖尾(TrailRenderer)线段渲染器(LineRenderer)、粒子系统(ParticleSystem)是 Unity3D 提供的三大特效,其中粒子系统的功能最为强大,特效也最炫酷,但操作也最复杂。粒子系统中,不断地有粒子生成和粒子消亡,一般而言,粒子消亡速率和生成速率保持一致(除预热阶段),使得粒子系统保持一个稳定状态。使用粒子系统,可以实现烟花、水泡、枪口火花、核弹爆炸等特效。

        在 Hierarchy 窗口右键,依次选择【Effects→Particle System】,可以创建一个粒子系统。

        粒子系统的使用非常灵活,主要有以下用法:

  • 控制发射器的形状(圆柱形、圆锥形、球形、圆形等)、发射周期、粒子数、粒子预热、发射延时等;
  • 控制粒子的形状、大小、颜色、材质、速度、旋转、生命周期等,并且在粒子的生命周期内可以修改这些属性;
  • 给粒子添加拖尾特效;
  • 控制多个粒子系统并行或串行发射粒子。

        粒子系统属性面板如下: 

  • Particle System:初始化模块
  • Emission:发射模块
  • Shape:发射器形状模块
  • Velocity over Lifetime:生命周期内速度变化模块
  • Limit Velocity over Lifetime:生命周期内速度约束模块
  • Inherit Velocity:继承父对象的速度,粒子速度会受到其父对象移动的影响
  • Force over Lifetime:生命周期内受力变化模块
  • Color over Lifetime:生命周期内颜色变化模块
  • Color by Speed:颜色受速度的影响模块
  • Size over Lifetime:生命周期内粒子大小变化模块
  • Size by Speed:粒子大小受速度影响模块
  • Rotation over Lifetime:生命周期内方向变化模块
  • Rotation by Speed:方向受速度影响模块
  • External Forces:粒子受外力影响模块
  • Noise:粒子受到随机噪声影响模块
  • Collision:碰撞模块
  • Triggers:触发器模块,如粒子雨,使粒子不会达到屋内
  • Sub Emitters:子发射器模块,多个粒子系统并行或串行发射粒子
  • Texture Sheet Animation:纹理层动画模块,可以控制将一张图片分割成多个部分,每次将其中的一个部分取出作为粒子贴图
  • Lights:光照模块
  • Trails:拖尾模块,可以给粒子添加拖尾效果
  • Custom Data:自定义模块,为粒子自定义数据
  • Renderer:渲染模块,可以设置渲染材质球、拖尾材质球等

2 Particle System(初始化模块)

  • Duration:粒子系统发射粒子的持续时间,当开启 Looping 后,Duration 失效;
  • Looping:是否循环发射粒子;
  • Prewarm:是否开启粒子预热,开启后,粒子个数从 0 逐渐增加到最大值;
  • Start Delay:发射粒子之前的延迟,当开启 Prewarm(预热)后不能使用此项;
  • Start Lifetime:粒子初始生命(存活时长),以秒为单位;
  • Start Speed:粒子初始速度
  • 3D Start SIze:粒子初始 3D 尺寸,开启后需要设置 X、Y、Z大小;
  • Start Size:粒子初始大小,3D Start SIze 开启后此选项消失;
  • 3D Start Rotation:粒子初始 3D 旋转,开启后,需要设置粒子在 X、Y、Z 轴上的旋转;
  • Start Rotation:粒子初始旋转角度,3D Start Rotation 开启后此选项消失;
  • Randomize Rotation:随机化旋转,取值 0~1,表示粒子反向(顺时针)旋转的概率;
  • Start Color:粒子初始颜色;
  • Gravity Modifier:粒子受到重力影响;
  • Simulation Space:粒子运动使用的坐标系(本地坐标系、世界坐标系);
  • Simulation Speed改变粒子系统中所有粒子的速度,取值表示倍数;
  • Delta Time:调整使用固定时间还是帧刷新粒子状态;
  • Scaling Mode:缩放粒子系统的状态;
  • Play On Awake:粒子系统启动后是否开启自动播放;
  • Emitter Velocity:粒子发射后的移动方式,采用 Rigidbody(刚体)还是 Transform(变换)
  • Max Particles:粒子系统中最大粒子个数;
  • Auto Random Seed:自动随机种子,粒子的部分状态随机生成,相同的随机数种子,每次产生的随机数一致;
  • Stop Action:当粒子系统发射完所有粒子后的操作,可以添加回调函数或在脚本中重写以下方法:
public void OnParticleSystemStopped()

        补充:属性右边的小三角形都可以展开,用户可以设置某属性取值方式,如下:

  • Constant:该属性取值是一个固定常量
  • Curve:该属性取值是一个变量,变量由曲线控制,用户可以自定义曲线;
  • Random Between Two Constant:该属性取值是 2 个常量中的随机数;
  • Random Between Two Curve:该属性取值是 2 个变量中的随机数,变量由 2 条曲线控制,用户可以自定义曲线

3 Emission(发射模块)

  • Rate over Time:发射频率按时间,每秒发射次数(未开启 Bursts 时,每次发射一个粒子);
  • Rate over Distance:发射频率按距离,移动粒子系统时,每米发射次数(未开启 Bursts 时,每次发射一个粒子);
  • Bursts:每次发射开启多少个循环(Cycles),每个循环发射多少个粒子(Count),每个循环的时间间隔是多少(Interval)

        设置 Bursts(爆炸)参数如下:

        显示效果如下:

4 Shape(发射器形状模块)

  • Shape:发射器形状,主要有:Sphere、Hemisphere、Cone、Donut、Box、Mesh、Mesh Renderer、Skinned Mesh Renderer、Circle、Edge;
Cone
Circle
Sphere

5 Renderer(渲染器模块)

  • Render Mode:渲染模式,主要有:Billboard(广告牌,粒子永远面朝相机)、Stretched Billboard(可拉伸广告牌)、Horizontal Billboard(水平广告牌,粒子面朝 Y 轴正方向)、Vertical Billboard(垂直广告牌,粒子面朝 X 轴正方向)、Mesh(网格);
  • Material:粒子材质;
  • Trail Material:拖尾特效材质,通常取 Default-Line。

6 Collision(碰撞模块)

  • Planes:碰撞平面;
  • Dampen:阻尼系数,取值 0~1,碰撞后速度减小;
  • Bounce:反弹系数,取值 0~1,碰撞后的反弹力度,取值为 0 时,粒子会贴着平面飞行;
  • Lifetime Loss:生命衰减系数,取值 0~1,每次碰撞生命都会衰减,取 0 时碰撞后粒子正常死亡,取 1 时碰撞后粒子立即死亡;
  • Visualization:可视化平面,网格(Grid)还是实体(Solid);
  • Scale Plane:缩放平面。

        点击 Planes 右边的加号,可以添加碰撞平面(此平面在运行时不可见),此时粒子系统游戏对象上自动添加了个子对象,如下:

         选中 Plane Transform 1 游戏对象,在 Inspector 窗口调整旋转角度,粒子系统显示效果如下:

7 Sub Emitters(子发射器模块)

  • Birth:子粒子系统与主粒子系统同时发射粒子(并行发射);
  • Collision:主粒子系统发生粒子碰撞时,触发子粒子系统发射粒子;
  • Death:主粒子系统粒子消亡时,触发子粒子系统发射粒子(串行发射)。

        设置主粒子系统每秒发射 1 个粒子(Rate over Time = 1,Emission 模块),再添加子粒子系统,如下:

         此时主粒子系统下面会自动添加一个子粒子系统,如下:

         选中 SubEmitter0,设置初始生命(Start Lifetime)为 1 秒,初始速度(StartSpeed)为 8 米 / 秒,查看 Emission 模块,发现自动添加了 Bursts,如下: 

        粒子系统显示效果如下:

8 Trails(拖尾模块)

        粒子系统中的拖尾与 TrailRenderer 组件类似。

  • Mode:拖尾模式,取值有:Particles(每个粒子拖尾独立绘制)、Ribbon(丝带,相邻粒子拖尾相连)
  • Lifetime:拖尾生命,拖尾长度由 0 增长到最长时的时长;
  • Color over Lifetime:拖尾生命周期内颜色变化;
  • Width over Trail:拖尾从头到尾宽度值;
  • Color over Trail:拖尾从头到尾颜色值。

        设置粒子系统每秒发射 1 个粒子(Rate over Time = 1,Emission 模块),初始生命(Start Lifetime)为 5 秒,初始速度(StartSpeed)为 25 米 / 秒,重力(Gravity Modifier)为 1,拖尾材质(Trail Material,Renderer 模块)为 Default-Line,拖尾(Trails)模块设置见属性面板,粒子系统显示效果如下:

Unity使用ParticleSystem粒子系统模拟药水在血管中流动(粒子碰撞)

一、前言

点关注不迷路,持续输出Unity干货文章。
嗨,大家好,我是新发。
之前我写了一篇Unity流体模拟的文章:《Unity流体模拟,支持粒子系统,支持流体碰撞交互(Obi Fluid插件使用教程)》
然后有同学私信我,问我能否做药剂打入血管的效果。
在这里插入图片描述
这个嘛,用ObiFluid可以做,不过我今天要尝试的,是用另一种方式:直接使用Unity的粒子系统来做。

二、最终效果

最终效果如下,效果虽然一般,不过制相对简单很多。
在这里插入图片描述
本文Demo工程已上传到CodeChina,感兴趣的同学可自行下载学习。
地址:https://codechina.csdn.net/linxinfa/UnityParticleFluidDemo
注:我使用的Unity版本:Unity 2020.1.14f1c1 (64-bit)
在这里插入图片描述

三、制作过程

1、导入血管模型

将血管模型导入工程中。
在这里插入图片描述

2、血管Shader

因为我们需要透过血管看到药水流动,所以血管需要半透明显示,我们这里创建一个shader,实现半透明效果。
在这里插入图片描述

shader代码如下:

Shader "linxinfa/CustomTransShader" {
	Properties {
		_Color ("Main Tint", Color) = (1,1,1,1)
		_MainTex ("Main Tex", 2D) = "white" {}
		_AlphaScale("Alpha Scale",Range(0,1)) = 1
	}
	SubShader {
		Tags{"Queue" = "AlphaTest" "IgnoreProjector" = "True" "RenderType" = "Transparent"}
 
		Pass
		{
			Tags{"LightMode" = "ForwardBase"}
 
			Cull Front
 
			ZWrite Off
			Blend SrcAlpha OneMinusSrcAlpha
 
 
			CGPROGRAM
			#pragma vertex vert
			#pragma fragment frag
			#include "Lighting.cginc"
			#include "UnityCG.cginc"
 
			fixed4 _Color;
			sampler2D _MainTex;
			float4 _MainTex_ST;
			fixed _AlphaScale;
 
			struct a2v
			{
				float4 vertex : POSITION;
				float3 normal : NORMAL;
				float4 texcoord : TEXCOORD0;
			};
 
			struct v2f
			{
				float4 pos : SV_POSITION;
				float3 worldNormal : TEXCOORD0;
				float3 worldPos : TEXCOORD1;
				float2 uv : TEXCOORD2;
			};
 
			v2f vert(a2v v)
			{
				v2f o;
				o.pos = UnityObjectToClipPos(v.vertex);
				o.worldNormal = UnityObjectToWorldNormal(v.normal);
				o.worldPos = mul(unity_ObjectToWorld,v.vertex).xyz;
 
				o.uv = TRANSFORM_TEX(v.texcoord,_MainTex);
 
				return o;
 
			}
 
			fixed4 frag(v2f i) : SV_TARGET0
			{
				fixed3 worldNormal = normalize(i.worldNormal);
				fixed3 worldLightDir = normalize(UnityWorldSpaceLightDir(i.worldPos));
 
				fixed4 texcolor = tex2D(_MainTex,i.uv);
 
				fixed3 albedo = texcolor.rgb * _Color.rgb;
				fixed3 ambient = UNITY_LIGHTMODEL_AMBIENT.xyz * albedo;
				fixed3 diffues = _LightColor0.rgb * albedo * max(0,dot(worldNormal,worldLightDir));
 
				return fixed4(ambient + diffues,texcolor.a * _AlphaScale);
			}
 
 
 
 
 
			ENDCG
		}
 
 
		Pass
		{
			Tags{"LightMode" = "ForwardBase"}
 
			Cull Back
 
			ZWrite Off
			Blend SrcAlpha OneMinusSrcAlpha
 
 
			CGPROGRAM
			#pragma vertex vert
			#pragma fragment frag
			#include "Lighting.cginc"
			#include "UnityCG.cginc"
 
			fixed4 _Color;
			sampler2D _MainTex;
			float4 _MainTex_ST;
			fixed _AlphaScale;
 
			struct a2v
			{
				float4 vertex : POSITION;
				float3 normal : NORMAL;
				float4 texcoord : TEXCOORD0;
			};
 
			struct v2f
			{
				float4 pos : SV_POSITION;
				float3 worldNormal : TEXCOORD0;
				float3 worldPos : TEXCOORD1;
				float2 uv : TEXCOORD2;
			};
 
			v2f vert(a2v v)
			{
				v2f o;
				o.pos = UnityObjectToClipPos(v.vertex);
				o.worldNormal = UnityObjectToWorldNormal(v.normal);
				o.worldPos = mul(unity_ObjectToWorld,v.vertex).xyz;
 
				o.uv = TRANSFORM_TEX(v.texcoord,_MainTex);
 
				return o;
 
			}
 
			fixed4 frag(v2f i) : SV_TARGET0
			{
				fixed3 worldNormal = normalize(i.worldNormal);
				fixed3 worldLightDir = normalize(UnityWorldSpaceLightDir(i.worldPos));
 
				fixed4 texcolor = tex2D(_MainTex,i.uv);
 
				fixed3 albedo = texcolor.rgb * _Color.rgb;
				fixed3 ambient = UNITY_LIGHTMODEL_AMBIENT.xyz * albedo;
				fixed3 diffues = _LightColor0.rgb * albedo * max(0,dot(worldNormal,worldLightDir));
 
				return fixed4(ambient + diffues,texcolor.a * _AlphaScale);
			}
 
			ENDCG
 
	}
	}
		FallBack "Transparent/VertexLit"
}

3、血管材质球

创建材质球,使用刚刚的CustomTransShader.shader
在这里插入图片描述
然后把材质球赋值给血管模型预设,这样,半透明的血管就做好了。
在这里插入图片描述

4、添加碰撞体

因为药水要在血管中流动,需要发生碰撞,所以血管需要添加碰撞体:MeshCollider
在这里插入图片描述

5、药水粒子

药水粒子其实就是普通的粒子。
在这里插入图片描述
最关键点就是开启粒子的Collision属性,这样粒子就可以与血管壁碰撞了。
在这里插入图片描述
其中一些参数:
Dampen:阻力
Bounce:弹力
Lifetime Loss:损失率
Min Kill Speed:最小死亡速度
Max Kill Speed: 最大死亡速度
Radius Scale: 半径缩放,可使粒子未撞到Collision便产生碰撞

四、测试效果

最终运行Unity,测试效果如下:
在这里插入图片描述

五、结束语

完毕。
喜欢Unity的同学,不要忘记点击关注,如果有什么Unity相关的技术难题,也欢迎留言或私信~

以上是关于Unity3D粒子系统ParticleSystem的主要内容,如果未能解决你的问题,请参考以下文章

Unity3D:粒子系统Particle System

Unity3D 粒子系统

[Unity2D/3D]Particle System粒子系统/以实现烟雾效果为例

Unity3d 粒子系统里,如果粒子做多了怎么统一修改参数

unity|火焰和烟效果(粒子系统)

Unity3D深入浅出 - 新版粒子系统 (Shuriken) - Tonge