c# - 统一: Change Particle System to pooling

标签 c# unity3d particle-system

我正在尝试将我的粒子系统功能更改为池化而不是每次都实例化。我想重复使用这些粒子。这怎么可能?我不知道如何开始,虽然我看了统一教程,但不知何故仍然不清楚。可能是因为我在其他类中调用了粒子系统函数,这让我有些困惑。

public ParticleSystem[] Myeffects;


public void Particle(int particleNum, Vector3 Pos)
{
    if (Myeffects != null && Myeffects[particleNumber] != null )
    {
        if (Myeffects[particleNumber].isPlaying)
            Myeffects[particleNumber].Stop();

        ParticleSystem temp = Instantiate(Myeffects[particleNum], particlePos, new Quaternion()) as ParticleSystem;

        temp.Play();
    }
}
}

最佳答案

首先,选择您的粒子系统预制件/TNT,然后确保未选中Play On Awake。下面的池脚本是实现这一目标的专用技巧。它将创建指定的 ParticleSystem 数组,然后重新使用它们。请注意,ParticlePool 继承自 MonoBehaviour,因此请确保直接复制它。

using UnityEngine;
using System.Collections;
using System;

public class ParticlePool
{
    int particleAmount;
    ParticleSystem[] NormalParticle;
    ParticleSystem[] TNTParticle;

    public ParticlePool(ParticleSystem normalPartPrefab, ParticleSystem tntPartPrefab, int amount = 10)
    {
        particleAmount = amount;
        NormalParticle = new ParticleSystem[particleAmount];
        TNTParticle = new ParticleSystem[particleAmount];

        for (int i = 0; i < particleAmount; i++)
        {
            //Instantiate 10 NormalParticle
            NormalParticle[i] = GameObject.Instantiate(normalPartPrefab, new Vector3(0, 0, 0), new Quaternion()) as ParticleSystem;

            //Instantiate 10 TNTParticle
            TNTParticle[i] = GameObject.Instantiate(tntPartPrefab, new Vector3(0, 0, 0), new Quaternion()) as ParticleSystem;
        }
    }

    //Returns available GameObject
    public ParticleSystem getAvailabeParticle(int particleType)
    {
        ParticleSystem firstObject = null;

        //Normal crate
        if (particleType == 0)
        {
            //Get the first GameObject
            firstObject = NormalParticle[0];
            //Move everything Up by one
            shiftUp(0);
        }

        //TNT crate
        else if (particleType == 1)
        {
            //Get the first GameObject
            firstObject = TNTParticle[0];
            //Move everything Up by one
            shiftUp(1);
        }

        return firstObject;
    }

    //Returns How much GameObject in the Array
    public int getAmount()
    {
        return particleAmount;
    }

    //Moves the GameObject Up by 1 and moves the first one to the last one
    private void shiftUp(int particleType)
    {
        //Get first GameObject
        ParticleSystem firstObject;

        //Normal crate
        if (particleType == 0)
        {
            firstObject = NormalParticle[0];
            //Shift the GameObjects Up by 1
            Array.Copy(NormalParticle, 1, NormalParticle, 0, NormalParticle.Length - 1);

            //(First one is left out)Now Put first GameObject to the Last one
            NormalParticle[NormalParticle.Length - 1] = firstObject;
        }

        //TNT crate
        else if (particleType == 1)
        {
            firstObject = TNTParticle[0];
            //Shift the GameObjects Up by 1
            Array.Copy(TNTParticle, 1, TNTParticle, 0, TNTParticle.Length - 1);

            //(First one is left out)Now Put first GameObject to the Last one
            TNTParticle[TNTParticle.Length - 1] = firstObject;
        }
    }
}

然后,您的 ParticleHolder 脚本应使用以下代码更新。就是这样。没有更多的实例化。

public class ParticleHolder : MonoBehaviour
{

    public ParticleSystem[] effects;
    ParticlePool particlePool;

    void Start()
    {
        // 0 = Normal crate
        // 1 = TNT crate
        particlePool = new ParticlePool(effects[0], effects[1], 5);
    }

    public void playParticle(int particleType, Vector3 particlePos)
    {
        ParticleSystem particleToPlay = particlePool.getAvailabeParticle(particleType);

        if (particleToPlay != null)
        {
            if (particleToPlay.isPlaying)
                particleToPlay.Stop();

            particleToPlay.transform.position = particlePos;
            particleToPlay.Play();
        }

    }
}

关于c# - 统一: Change Particle System to pooling,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38280685/

相关文章:

c# - 如何等待(在异步方法中)包含 C# 方法调用的 linq 请求

c# - 在 C# 中,如何使用十六进制值创建 System.Drawing.Color 对象?

c# - 如何正确使用 CharacterController.Move() 来移动角色

unity3d - 我可以在 Unity 中使用 powershell 命令吗?

c++ - 我的粒子数组不工作(C++/粒子系统)

C# IDisposable 模式和抛出 ObjectDisposedException

c# - 自动重构访问修饰符

c# - 如何通过 Unity 使用 WebGL/C# 在新选项卡上打开链接?

swift - SceneKit:在 SCNView 上渲染 SpriteKit 粒子系统时应用程序崩溃,当所有代码似乎都是系统代码的一部分时如何调试

unity-game-engine - Unity - 发射非随机粒子