123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215 |
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- [RequireComponent(typeof(Collider))]
- public class ArUcoDrone : MonoBehaviour
- {
-
-
-
- [Tooltip("How close other drones have to be for this drone to start firing. Must also be directly in front of the drone.")]
- public float shootRangeMeters = 0.25f;
-
-
-
- [Tooltip("Time between each shot when firing.")]
- public float shootCooldownSeconds = 0.33f;
-
-
-
- [Tooltip("How much damage this drone can take before dying.")]
- public float maxHealth = 10;
-
-
-
- private float currentHealth;
-
-
-
- private float shootTimer = 0f;
-
-
-
- private bool canShoot
- {
- get
- {
- return shootTimer <= 0f;
- }
- }
-
-
-
- [Tooltip("Prefab of the projectile object the drone shoots. Should have an ArUcoDroneLaser component on it.")]
- public GameObject projectilePrefab;
-
-
-
- [Tooltip("Transform where laser shots are spawned, and from where the drone's laser range is tested.")]
- public Transform shootAnchorObject;
-
-
-
- [Tooltip("Object spawned when the drone dies.")]
- public GameObject explosionPrefab;
- private Collider col;
-
-
-
- [Tooltip("Sound played every time the drone fires a laser. Requires an AudioSource attached to this GameObject.")]
- public AudioClip laserShootSound;
- private AudioSource audioSource;
-
-
-
- [Tooltip("If true, will use the ZED's depth to check if there's a real-world object between this drone and its target.")]
- public bool checkRealWorldObstaclesBeforeShooting = false;
-
- void Start ()
- {
- col = GetComponent<Collider>();
- currentHealth = maxHealth;
- audioSource = GetComponent<AudioSource>();
- }
- private void OnEnable()
- {
- shootTimer = 0f;
- }
-
- void Update ()
- {
- if(canShoot == true && IsAimingAtTarget() == true)
- {
- StartCoroutine(Shoot());
- }
- }
-
-
-
-
-
- private bool IsAimingAtTarget()
- {
-
- Ray ray = new Ray(shootAnchorObject.position, shootAnchorObject.rotation * Vector3.forward);
- RaycastHit[] hits = Physics.RaycastAll(ray, shootRangeMeters);
- bool foundvirtualtarget = false;
- float nearestdist = Mathf.Infinity;
- foreach(RaycastHit hit in hits)
- {
- ArUcoDrone otherdrone = hit.transform.GetComponent<ArUcoDrone>();
- if(otherdrone != null && otherdrone != this)
- {
- foundvirtualtarget = true;
- if (hit.distance < nearestdist) nearestdist = hit.distance;
- }
- }
- if (!foundvirtualtarget) return false;
- if (checkRealWorldObstaclesBeforeShooting)
- {
-
- Vector3 collisionpoint;
- foreach (ZEDManager manager in ZEDManager.GetInstances())
- {
- bool hitreal = ZEDSupportFunctions.HitTestOnRay(manager.zedCamera, manager.GetLeftCamera(), shootAnchorObject.transform.position, shootAnchorObject.transform.rotation,
- nearestdist, 0.01f, out collisionpoint, false, 0.1f);
- if (hitreal) return false;
- }
- return true;
- }
- else return true;
- }
-
-
-
- private void SpawnProjectile()
- {
-
- if (!projectilePrefab) return;
- GameObject lasergo = Instantiate(projectilePrefab, shootAnchorObject.transform.position, shootAnchorObject.transform.rotation);
-
- lasergo.name = gameObject.name + "'s Laser";
- ArUcoDroneLaser laser = lasergo.GetComponentInChildren<ArUcoDroneLaser>();
- if(!laser)
- {
- Debug.LogError("projectilePrefab assigned to " + gameObject.name + " does not have an ArUcoDroneLaser component.");
- Destroy(lasergo);
- return;
- }
- laser.spawningDrone = this;
- if(audioSource && laserShootSound)
- {
- audioSource.PlayOneShot(laserShootSound);
- }
- }
-
-
-
-
- private IEnumerator Shoot()
- {
- SpawnProjectile();
- while(shootTimer < shootCooldownSeconds)
- {
- shootTimer += Time.deltaTime;
- yield return null;
- }
- shootTimer = 0f;
- }
-
-
-
-
- public void TakeDamage(float damage)
- {
- currentHealth -= damage;
-
- if (currentHealth <= 0)
- {
- Die();
- }
- }
-
-
-
- public void Die()
- {
- print(gameObject.name + " destroyed.");
- if(explosionPrefab)
- {
- Instantiate(explosionPrefab, transform.position, transform.rotation);
- }
- Destroy(gameObject);
- }
- }
|