zoukankan      html  css  js  c++  java
  • unity游戏开发_对象池

    现在假设游戏中我们需要实现一个这样功能,按下鼠标左键,发射一颗子弹,3秒之后消失。在这个功能中,我们发射了上百上千发子弹,就需要实例化生成上百上千次。这时候,我们就需要使用对象池这个概念,每次实例化生成一个子弹对象后,三秒钟后不销毁(不执行destroy),而是将其将其隐藏(SetActive(false))并且放入对象池中。再次按下鼠标时,如果对象池不为空,就去对象池里将隐藏的对象显示出来。如果对象池里面没有可用对象时,再执行实例化子弹的方法。

    首先创建一个对象池脚本,此脚本是一个单例脚本(不需要挂在任何游戏对象上面)。

    using UnityEngine;
    using System.Collections;
    using System.Collections.Generic;
    public class GameObjectPool : MonoBehaviour {
    //集合里面的元素,相当于对象池里面的对象,这里的集合可看作为对象池。
        List<GameObject> pools = new List<GameObject> ();
    //首先创建一个单例
        private GameObjectPool(){}
        private static GameObjectPool instance;
        public static GameObjectPool GetInstance(){
                if(instance == null){
                //动态的生成一个名为“GameObjectPool”的对象并将单例脚本附加上去
                instance  = new GameObject("GameObjectPool").AddComponent<GameObjectPool>();
            }
            return instance;
        }
    //从对象池中取对象
        public GameObject MyInstantiate(GameObject name){
        //如果对象池中没有可以对象
            if(pools.Count == 0){
                //就实例化一个新的对象
                return Instantiate(name,Vector3.zero,Quaternion.identity) as GameObject;
            }else{
            //取出对象池里面的第一个元素
                GameObject obj = pools[0];
                //将对象设置为激活状态
                obj.SetActive(true);
                //将被取出的元素,从对象池中移除
                pools.Remove(obj);
                return obj;
    
            }
    
    }
    //向对象池里面存对象
        public void MyDisable(GameObject name){
        //将传进来的对象隐藏(处于非激活状态)
            name.SetActive(false);
            //添加到对象池中(添加到集合中)
            pools.Add(name);
        }
    }
    GameObjectPool

    2.创建一个名为Game Manager的脚本,来控制子弹的生成 
    这里写图片描述

    创建子弹的预设体

    using UnityEngine;
    using System.Collections;
    
    public class gameManager : MonoBehaviour {
    //创建子弹的预设体
        public GameObject mBulletPrefab;
    
        void Update () {
        //如果按下鼠标左键
            if(Input.GetMouseButtonDown(0)){
            //调用单例脚本里面的从对象池中取对象的方法
                GameObjectPool.GetInstance().MyInstantiate(mBulletPrefab);
            }
    
        }
    }
    gameManager
    using UnityEngine;
    using System.Collections;
    
    public class gameManager : MonoBehaviour {
    //创建子弹的预设体
        public GameObject mBulletPrefab;
    
        void Update () {
        //如果按下鼠标左键
            if(Input.GetMouseButtonDown(0)){
            //调用单例脚本里面的从对象池中取对象的方法
                GameObjectPool.GetInstance().MyInstantiate(mBulletPrefab);
            }
    
        }
    }
                            
    
    3.为子弹的预设体创建Bullet脚本
    
    using UnityEngine;
    using System.Collections;
    public class Bullet : MonoBehaviour {
    void OnEnable  () {
    //脚本可用的时候,重置子弹的位置。
    //如果不加这句代码,从对象池中取出的子弹就会从上一次消失的位置开始运动。而不是你设定的子弹生成位置
    transform.position = Vector3.zero;
    //开启协程方法
    StartCoroutine(DelayDisable(3f));
    }
    
    
    void Update () {
    //子弹生成,自动向前运动
    transform.Translate(Vector3.forward*Time.deltaTime*20);
    }
    void OnDisable(){
    Debug.Log("I'm over");
    }
    //子弹消失的方法
    IEnumerator DelayDisable(float time){
    //等待三秒
    yield return new WaitForSeconds(time);
    //调用单例中向对象池里面存对象的方法
    GameObjectPool.GetInstance().MyDisable(gameObject);
    为子弹的预设体创建Bullet脚本
    using UnityEngine;
    using System.Collections;
    public class Bullet : MonoBehaviour 
    {
        void OnEnable  () 
        {
            //脚本可用的时候,重置子弹的位置。
            //如果不加这句代码,从对象池中取出的子弹就会从上一次消失的位置开始运动。而不是你设定的子弹生成位置
            transform.position = Vector3.zero;
            //开启协程方法
            StartCoroutine(DelayDisable(3f));
        }
    
    
        void Update () 
        {
            //子弹生成,自动向前运动
            transform.Translate(Vector3.forward*Time.deltaTime*20);
        }
        void OnDisable()
        {
            Debug.Log("I'm over");
        }
        //子弹消失的方法
        IEnumerator DelayDisable(float time)
        {
            //等待三秒
            yield return new WaitForSeconds(time);
            //调用单例中向对象池里面存对象的方法
            GameObjectPool.GetInstance().MyDisable(gameObject);
        }
    
    }
    Bullet

    引用自http://blog.csdn.net/qq_25210959/article/details/51221021

  • 相关阅读:
    Dll版本管理
    线程池ThreadPool
    关于sitemesh和freemark在struts2中的一些问题总结
    Google 怎么搜索
    android 设计模式
    android webview
    ios 基础数据类型
    android 常用
    android Handler vs Timer
    网站
  • 原文地址:https://www.cnblogs.com/shirln/p/8464153.html
Copyright © 2011-2022 走看看