You cannot select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
	
	
		
			199 lines
		
	
	
		
			8.2 KiB
		
	
	
	
		
			C#
		
	
		
		
			
		
	
	
			199 lines
		
	
	
		
			8.2 KiB
		
	
	
	
		
			C#
		
	
| 
								 
											1 year ago
										 
									 | 
							
								using System.Collections;
							 | 
						||
| 
								 | 
							
								using System.Collections.Generic;
							 | 
						||
| 
								 | 
							
								using UnityEngine;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								namespace Autohand {
							 | 
						||
| 
								 | 
							
								    [RequireComponent(typeof(AutoGun))]
							 | 
						||
| 
								 | 
							
								    public class AutoGunEffects : MonoBehaviour {
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        [AutoSmallHeader("Visual Effects")]
							 | 
						||
| 
								 | 
							
								        public bool ignoreMe3;
							 | 
						||
| 
								 | 
							
								        [Tooltip("Whether or not racking the slide with a bullet already in the chamber ejects that bullet or not")]
							 | 
						||
| 
								 | 
							
								        public bool ejectUnfiredBullet = true;
							 | 
						||
| 
								 | 
							
								        [Tooltip("This is the unfired bullet prefab that will be instantiated and ejected if the 'ejectUnfiredBullet' value is true and the slide is racked while full")]
							 | 
						||
| 
								 | 
							
								        public GameObject bullet;
							 | 
						||
| 
								 | 
							
								        [Tooltip("This is the fired bullet shell prefab that will be instantiated and ejected if the when the gun is shot")]
							 | 
						||
| 
								 | 
							
								        public GameObject bulletShell;
							 | 
						||
| 
								 | 
							
								        [Tooltip("Particle effect that plays from the gun aim transform on shoot")]
							 | 
						||
| 
								 | 
							
								        public ParticleSystem shootParticle;
							 | 
						||
| 
								 | 
							
								        [Tooltip("The lifetime of the ejected bullets before they are added to the pool")]
							 | 
						||
| 
								 | 
							
								        public float ejectedBulletLifetime = 3f;
							 | 
						||
| 
								 | 
							
								        [Tooltip("The position and rotation where the bullets are instantiated")]
							 | 
						||
| 
								 | 
							
								        public Transform shellEjectionSpawnPoint;
							 | 
						||
| 
								 | 
							
								        [Tooltip("The forward direction of this point represents the direction the shells should be ejected")]
							 | 
						||
| 
								 | 
							
								        public Transform shellEjectionDirection;
							 | 
						||
| 
								 | 
							
								        [Tooltip("The amount of force to add to the ejected bullet")]
							 | 
						||
| 
								 | 
							
								        public float shellEjectionForce = 50;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        [AutoSmallHeader("Sound Effects")]
							 | 
						||
| 
								 | 
							
								        public bool ignoreMe4;
							 | 
						||
| 
								 | 
							
								        [Tooltip("This sound will play when a bullet is fired")]
							 | 
						||
| 
								 | 
							
								        public AudioSource shootSound;
							 | 
						||
| 
								 | 
							
								        [Tooltip("This sound will play when a the trigger is pressed and there is nothing to shoot")]
							 | 
						||
| 
								 | 
							
								        public AudioSource emptyShootSound;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        Dictionary<GameObject, float> bulletLifetimeTracker = new Dictionary<GameObject, float>();
							 | 
						||
| 
								 | 
							
								        Dictionary<GameObject, float> shellLifetimeTracker = new Dictionary<GameObject, float>();
							 | 
						||
| 
								 | 
							
								        List<GameObject> bulletPool = new List<GameObject>();
							 | 
						||
| 
								 | 
							
								        List<GameObject> bulletShellPool = new List<GameObject>();
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        List<ParticleSystem> activeParticlePool = new List<ParticleSystem>();
							 | 
						||
| 
								 | 
							
								        List<ParticleSystem> inactiveParticlePool = new List<ParticleSystem>();
							 | 
						||
| 
								 | 
							
								        AutoGun gun;
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        private void OnEnable(){
							 | 
						||
| 
								 | 
							
								            gun = GetComponent<AutoGun>();
							 | 
						||
| 
								 | 
							
								            gun.OnShoot.AddListener(OnShoot);
							 | 
						||
| 
								 | 
							
								            gun.OnEmptyShoot.AddListener(OnEmptyShoot);
							 | 
						||
| 
								 | 
							
								            gun.OnSlideEvent.AddListener(OnSlideLoaded);
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        private void OnDisable(){
							 | 
						||
| 
								 | 
							
								            gun.OnShoot.RemoveListener(OnShoot);
							 | 
						||
| 
								 | 
							
								            gun.OnEmptyShoot.RemoveListener(OnEmptyShoot);
							 | 
						||
| 
								 | 
							
								            gun.OnSlideEvent.RemoveListener(OnSlideLoaded);
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        private void FixedUpdate() {
							 | 
						||
| 
								 | 
							
								            CheckBulletLifetime();
							 | 
						||
| 
								 | 
							
								            CheckParticlPlaying();
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void CreateShootParticle() {
							 | 
						||
| 
								 | 
							
								            if(shootParticle != null) {
							 | 
						||
| 
								 | 
							
								                var newShootParticle = GameObject.Instantiate(shootParticle);
							 | 
						||
| 
								 | 
							
								                newShootParticle.transform.position = gun.shootForward.position;
							 | 
						||
| 
								 | 
							
								                newShootParticle.transform.forward = gun.shootForward.forward;
							 | 
						||
| 
								 | 
							
								                activeParticlePool.Add(newShootParticle);
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void OnShoot(AutoGun gun){
							 | 
						||
| 
								 | 
							
								            shootSound?.PlayOneShot(shootSound.clip);
							 | 
						||
| 
								 | 
							
								            CreateShootParticle();
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void OnEmptyShoot(AutoGun gun){
							 | 
						||
| 
								 | 
							
								            emptyShootSound?.PlayOneShot(emptyShootSound.clip);
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void OnSlideLoaded(AutoGun gun, SlideLoadType loadType) {
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								            if(loadType == SlideLoadType.ShotLoaded){
							 | 
						||
| 
								 | 
							
								                if(gun.slideJoint != null) {
							 | 
						||
| 
								 | 
							
								                    if(Mathf.Abs(gun.slideJoint.xMinLimit) >= gun.slideJoint.xMaxLimit &&
							 | 
						||
| 
								 | 
							
								                        Mathf.Abs(gun.slideJoint.yMinLimit) >= gun.slideJoint.yMaxLimit &&
							 | 
						||
| 
								 | 
							
								                        Mathf.Abs(gun.slideJoint.zMinLimit) >= gun.slideJoint.zMaxLimit)
							 | 
						||
| 
								 | 
							
								                        gun.slideJoint.SetJointMin();
							 | 
						||
| 
								 | 
							
								                    else
							 | 
						||
| 
								 | 
							
								                        gun.slideJoint.SetJointMax();
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								                EjectShell();
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								            else if(gun.IsSlideLoaded()) {
							 | 
						||
| 
								 | 
							
								                EjectBullet();
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        public void EjectBullet() {
							 | 
						||
| 
								 | 
							
								            if(bullet != null) {
							 | 
						||
| 
								 | 
							
								                GameObject newBullet;
							 | 
						||
| 
								 | 
							
								                if(bulletPool.Count > 0) {
							 | 
						||
| 
								 | 
							
								                    newBullet = bulletPool[0];
							 | 
						||
| 
								 | 
							
								                    bulletPool.RemoveAt(0);
							 | 
						||
| 
								 | 
							
								                    newBullet.transform.position = shellEjectionSpawnPoint.position;
							 | 
						||
| 
								 | 
							
								                    newBullet.transform.rotation = shellEjectionSpawnPoint.rotation;
							 | 
						||
| 
								 | 
							
								                    newBullet.SetActive(true);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								                else {
							 | 
						||
| 
								 | 
							
								                    newBullet = Instantiate(bullet, shellEjectionSpawnPoint.position, shellEjectionSpawnPoint.rotation);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								                if(newBullet.CanGetComponent<Rigidbody>(out var body)) {
							 | 
						||
| 
								 | 
							
								                    if(AutoHandPlayer.Instance.IsHolding(gun.grabbable))
							 | 
						||
| 
								 | 
							
								                        body.velocity = AutoHandPlayer.Instance.body.velocity;
							 | 
						||
| 
								 | 
							
								                    body.velocity += gun.grabbable.body.velocity;
							 | 
						||
| 
								 | 
							
								                    body.AddForce(shellEjectionDirection.forward * shellEjectionForce, ForceMode.Force);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								                bulletLifetimeTracker.Add(newBullet, ejectedBulletLifetime);
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        public void EjectShell() {
							 | 
						||
| 
								 | 
							
								            if(bulletShell != null) {
							 | 
						||
| 
								 | 
							
								                GameObject newShell;
							 | 
						||
| 
								 | 
							
								                if(bulletShellPool.Count > 0) {
							 | 
						||
| 
								 | 
							
								                    newShell = bulletShellPool[0];
							 | 
						||
| 
								 | 
							
								                    bulletShellPool.RemoveAt(0);
							 | 
						||
| 
								 | 
							
								                    newShell.transform.position = shellEjectionSpawnPoint.position;
							 | 
						||
| 
								 | 
							
								                    newShell.transform.rotation = shellEjectionSpawnPoint.rotation;
							 | 
						||
| 
								 | 
							
								                    newShell.SetActive(true);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								                else {
							 | 
						||
| 
								 | 
							
								                    newShell = Instantiate(bulletShell, shellEjectionSpawnPoint.position, shellEjectionSpawnPoint.rotation);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								                if(newShell.CanGetComponent<Rigidbody>(out var body)) {
							 | 
						||
| 
								 | 
							
								                    if(AutoHandPlayer.Instance.IsHolding(gun.grabbable))
							 | 
						||
| 
								 | 
							
								                        body.velocity = AutoHandPlayer.Instance.body.velocity;
							 | 
						||
| 
								 | 
							
								                    body.velocity += gun.grabbable.body.velocity;
							 | 
						||
| 
								 | 
							
								                    body.AddForce(shellEjectionDirection.forward * shellEjectionForce, ForceMode.Force);
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								                shellLifetimeTracker.Add(newShell, ejectedBulletLifetime);
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void CheckBulletLifetime() {
							 | 
						||
| 
								 | 
							
								            if(bulletLifetimeTracker.Count > 0) {
							 | 
						||
| 
								 | 
							
								                var bulletKeys = new GameObject[bulletLifetimeTracker.Count];
							 | 
						||
| 
								 | 
							
								                bulletLifetimeTracker.Keys.CopyTo(bulletKeys, 0);
							 | 
						||
| 
								 | 
							
								                foreach(var bullet in bulletKeys) {
							 | 
						||
| 
								 | 
							
								                    bulletLifetimeTracker[bullet] -= Time.deltaTime;
							 | 
						||
| 
								 | 
							
								                    if(bulletLifetimeTracker[bullet] <= 0) {
							 | 
						||
| 
								 | 
							
								                        bullet.SetActive(false);
							 | 
						||
| 
								 | 
							
								                        bulletPool.Add(bullet);
							 | 
						||
| 
								 | 
							
								                        bulletLifetimeTracker.Remove(bullet);
							 | 
						||
| 
								 | 
							
								                    }
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								            if(shellLifetimeTracker.Count > 0) {
							 | 
						||
| 
								 | 
							
								                var shellKeys = new GameObject[shellLifetimeTracker.Count];
							 | 
						||
| 
								 | 
							
								                shellLifetimeTracker.Keys.CopyTo(shellKeys, 0);
							 | 
						||
| 
								 | 
							
								                foreach(var shell in shellKeys) {
							 | 
						||
| 
								 | 
							
								                    shellLifetimeTracker[shell] -= Time.deltaTime;
							 | 
						||
| 
								 | 
							
								                    if(shellLifetimeTracker[shell] <= 0) {
							 | 
						||
| 
								 | 
							
								                        shell.SetActive(false);
							 | 
						||
| 
								 | 
							
								                        bulletShellPool.Add(shell);
							 | 
						||
| 
								 | 
							
								                        shellLifetimeTracker.Remove(shell);
							 | 
						||
| 
								 | 
							
								                    }
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								
							 | 
						||
| 
								 | 
							
								        void CheckParticlPlaying() {
							 | 
						||
| 
								 | 
							
								            if(inactiveParticlePool.Count > 0) {
							 | 
						||
| 
								 | 
							
								                var playingKeys = new ParticleSystem[activeParticlePool.Count];
							 | 
						||
| 
								 | 
							
								                activeParticlePool.CopyTo(playingKeys, 0);
							 | 
						||
| 
								 | 
							
								                foreach(var particle in playingKeys) {
							 | 
						||
| 
								 | 
							
								                    if(!particle.isPlaying)
							 | 
						||
| 
								 | 
							
								                        particle.gameObject.SetActive(false);
							 | 
						||
| 
								 | 
							
								                    inactiveParticlePool.Add(particle);
							 | 
						||
| 
								 | 
							
								                    activeParticlePool.Remove(particle);
							 | 
						||
| 
								 | 
							
								                }
							 | 
						||
| 
								 | 
							
								            }
							 | 
						||
| 
								 | 
							
								        }
							 | 
						||
| 
								 | 
							
								    }
							 | 
						||
| 
								 | 
							
								}
							 |