作业要求
使用粒子流编程控制制作一些效果, 如“粒子光环”
参考资料
https://blog.youkuaiyun.com/simba_scorpio/article/details/51251126
实验过程
1. 添加粒子系统
创建空对象ParticleHalo,再它下面建立新的空子对象Clockwise_outer。
ParticleHalo下面可以有很多不同的粒子系统,这些粒子系统有不同的参数,之后再设定。


2. 粒子系统脚本
需要定义每个粒子不同的位置、运动角度、运动速度等参数,并通过调整这些参数来模拟每个粒子的运动,从而获得“粒子光环”的效果。
2.1 粒子结构体
表示每个粒子的半径、角度和时间。
public class CirclePosition
{
public float radius = 0f, angle = 0f, time = 0f;
public CirclePosition(float radius, float angle, float time)
{
this.radius = radius; // 半径
this.angle = angle; // 角度
this.time = time; // 时间
}
}
2.2 私有变量
需要控制的粒子系统和粒子数组,以及每个粒子的CirclePosition。
private ParticleSystem particleSys; // 粒子系统
private ParticleSystem.Particle[] particleArr; // 粒子数组
private CirclePosition[] circle; // 极坐标数组
为了达到光环的效果,还需要控制所有粒子的整体效果,包括数量、最大半径、最小半径、旋转方向、速度、游离范围:
public int count = 10000; // 粒子数量
public float size = 0.03f; // 粒子大小
public float minRadius = 5.0f; // 最小半径
public float maxRadius = 12.0f; // 最大半径
public bool clockwise = true; // 顺时针|逆时针
public float speed = 2f; // 速度
public float pingPong = 0.02f; // 游离范围
2.3 Start()
初始化粒子数组,并将所有的粒子随机分布在圆圈轨道上
void Start ()
{ // 初始化粒子数组
particleArr = new ParticleSystem.Particle[count];
circle = new CirclePosition[count];
// 初始化粒子系统
particleSys = this.GetComponent<ParticleSystem>();
particleSys.startSpeed = 0; // 粒子位置由程序控制
particleSys.startSize = size; // 设置粒子大小
particleSys.loop = false;
particleSys.maxParticles = count; // 设置最大粒子量
particleSys.Emit(count); // 发射粒子
particleSys.GetParticles(particleArr);
RandomlySpread(); // 初始化各粒子位置
}
void RandomlySpread()
{
for (int i = 0; i < count; ++i)
{ // 随机每个粒子距离中心的半径,同时希望粒子集中在平均半径附近
float midRadius = (maxRadius + minRadius) / 2;
float minRate = Random.Range(1.0f, midRadius / minRadius);
float maxRate = Random.Range(midRadius / maxRadius, 1.0f);
float radius = Random.Range(minRadius * minRate, maxRadius * maxRate);
// 随机每个粒子的角度
float angle = Random.Range(0.0f, 360.0f);
float theta = angle / 180 * Mathf.PI;
// 随机每个粒子的游离起始时间
float time = Random.Range(0.0f, 360.0f);
circle[i] = new CirclePosition(radius, angle, time);
particleArr[i].position = new Vector3(circle[i].radius * Mathf.Cos(theta), 0f, circle[i].radius * Mathf.Sin(theta));
}
particleSys.SetParticles(particleArr, particleArr.Length);
}
2.4 Update()
逐渐改变粒子的角度以让粒子旋转起来,同时为了有粒子闪动的效果:
- 让粒子运动角度的变化量不一样。
- 让粒子的运动半径不固定,使其能在半径方向上游离,此时用到time来随机。
void Update () {
for (int i = 0; i < count; i++) {
if (clockwise) // 顺时针旋转
circle[i].angle -= (i % tier + 1) * (speed / circle[i].radius / tier);
else // 逆时针旋转
circle[i].angle += (i % tier + 1) * (speed / circle[i].radius / tier);
// 保证angle在0~360度
circle[i].angle = (360.0f + circle[i].angle) % 360.0f;
float theta = circle[i].angle / 180 * Mathf.PI;
particleArr[i].position = new Vector3(circle[i].radius * Mathf.Cos(theta), 0f, circle[i].radius * Mathf.Sin(theta));
particleArr[i].color = colorGradient.Evaluate(circle[i].angle / 360.0f);
circle[i].time += Time.deltaTime;
circle[i].radius += Mathf.PingPong(circle[i].time / minRadius / maxRadius, pingPong) - pingPong / 2.0f;
}
particleSys.SetParticles(particleArr, particleArr.Length);
}
3. 增加旋转不同的粒子系统

给不同的粒子系统设置不同的参数,使粒子的变化更随机一点

本文详细介绍如何使用粒子流编程控制在Unity中实现粒子光环效果。通过定义粒子结构体、控制粒子系统参数,以及在Start()和Update()方法中初始化和更新粒子位置,实现了动态光环效果。文章还介绍了如何通过调整参数使光环效果更加多样化。
861

被折叠的 条评论
为什么被折叠?



