• Unity3d 札记-Tanks Tutorial 知识点汇总---子弹爆炸效果的实现


    子弹爆炸  是一个范围性的爆炸,整个过程有四部分

    1.在该范围内的坦克都会受到冲击力(减血、位移)

    2.而且会播放一个爆炸的粒子效果

    3.播放音效

    4.子弹消失

    1UI模型搭建

    一个SHELL模型 + ShellExplosion爆炸粒子系统 

    其中Shell 中 应该有

              一个Collider用于触发物理碰撞           -----------胶囊型封装器 Capsule Collider

              一个RigidBody使其具有物理属性,比如受力       

              当然还有一个ShellExplosion粒子系统  

              及相应控制爆炸过程的 script 

    思考一下 ShellExplosion 爆炸的时候需要什么

                 1.物理特效 --------- PaticalSystem  ExplosionParticles

                 2.音效    ------------ AudioSource  ExplosionAudio

                 3.爆炸半径 ---------- float    ExplosionRadius

                 4.爆炸时间 ---------- float maxLifeTime

                 5.爆炸产生的冲击力  ------- float ExplosionForce  

                 6. 爆炸造成的最大伤害  -----  float maxDamage 

                 7.作用对象    --------LayerMask  TankMask

                

    再考虑一下 从外部引用还是内部定义获取            ,都是从外部引用           Public

     对UI进行相关的设置之后 (Collider的大小和位置, 添加各种组件 )

    直接PO代码

    using UnityEngine;
    
    public class ShellExplosion : MonoBehaviour
    {
        public LayerMask m_TankMask;
        public ParticleSystem m_ExplosionParticles;       
        public AudioSource m_ExplosionAudio;              
        public float m_MaxDamage = 100f;                  
        public float m_ExplosionForce = 1000f;            
        public float m_MaxLifeTime = 2f;                  
        public float m_ExplosionRadius = 5f;              
    
    
        private void Start()
        {
            Destroy(gameObject, m_MaxLifeTime);
        }
    
    
        private void OnTriggerEnter (Collider other)
        {
            // Collect all the colliders in a sphere from the shell's current position to a radius of the explosion radius.
            Collider[] colliders = Physics.OverlapSphere (transform.position, m_ExplosionRadius, m_TankMask);
    
            // Go through all the colliders...
            for (int i = 0; i < colliders.Length; i++)
            {
                // ... and find their rigidbody.
                Rigidbody targetRigidbody = colliders[i].GetComponent<Rigidbody> ();
    
                // If they don't have a rigidbody, go on to the next collider.
                if (!targetRigidbody)
                    continue;
    
                // Add an explosion force.
                targetRigidbody.AddExplosionForce (m_ExplosionForce, transform.position, m_ExplosionRadius);
    
                // Find the TankHealth script associated with the rigidbody.
                TankHealth targetHealth = targetRigidbody.GetComponent<TankHealth> ();
    
                // If there is no TankHealth script attached to the gameobject, go on to the next collider.
                if (!targetHealth)
                    continue;
    
                // Calculate the amount of damage the target should take based on it's distance from the shell.
                float damage = CalculateDamage (targetRigidbody.position);
    
                // Deal this damage to the tank.
                targetHealth.TakeDamage (damage);
            }
    
            // Unparent the particles from the shell.
            m_ExplosionParticles.transform.parent = null;
    
            // Play the particle system.
            m_ExplosionParticles.Play();
    
            // Play the explosion sound effect.
            m_ExplosionAudio.Play();
    
            // Once the particles have finished, destroy the gameobject they are on.
            Destroy (m_ExplosionParticles.gameObject, m_ExplosionParticles.duration);
    
            // Destroy the shell.
            Destroy (gameObject);
        }
    
    
        private float CalculateDamage (Vector3 targetPosition)
        {
            // Create a vector from the shell to the target.
            Vector3 explosionToTarget = targetPosition - transform.position;
    
            // Calculate the distance from the shell to the target.
            float explosionDistance = explosionToTarget.magnitude;
    
            // Calculate the proportion of the maximum distance (the explosionRadius) the target is away.
            float relativeDistance = (m_ExplosionRadius - explosionDistance) / m_ExplosionRadius;
    
            // Calculate damage as this proportion of the maximum possible damage.
            float damage = relativeDistance * m_MaxDamage;
    
            // Make sure that the minimum damage is always 0.
            damage = Mathf.Max (0f, damage);
    
            return damage;
        }
    }

    比较值得注意和学习的  

    Collider[] colliders = Physics.OverlapSphere (transform.position, m_ExplosionRadius, m_TankMask); //这个函数以某一位置,某一半径,以及相关的LayerMask作为区分 ,获取球形区域内物体的Collider 
     targetRigidbody.AddExplosionForce (m_ExplosionForce, transform.position, m_ExplosionRadius);//这个函数,则是RigidBody自带的,根据FORCE , POSITION , ExplosionRadius对自身施加爆炸冲击力
    
                // Find the TankHealth script associated with the rigidbody.
                TankHealth targetHealth = targetRigidbody.GetComponent<TankHealth> ();   //泛型获取一个 TankHealth对象 
    
                // If there is no TankHealth script attached to the gameobject, go on to the next collider.
                if (!targetHealth)
                    continue;
    
                // Calculate the amount of damage the target should take based on it's distance from the shell.
                float damage = CalculateDamage (targetRigidbody.position);
    
                // Deal this damage to the tank.
                targetHealth.TakeDamage (damage);
  • 相关阅读:
    我的大学学习之路
    拉勾上的一道题目
    python中文处理之encode/decode函数
    几个容易出错的css盒子模型细节
    洗牌算法shuffle
    判断正整数是否对称
    一种快速求fibonacci第n个数的算法
    利用正则表达式作为string.split seprator
    docker部分命令
    idea上传项目到GitHub
  • 原文地址:https://www.cnblogs.com/dongfangliu/p/5801758.html
Copyright © 2020-2023  润新知