167 lines
7 KiB
C#
167 lines
7 KiB
C#
using System.Collections;
|
|
using System.Collections.Generic;
|
|
using UnityEngine;
|
|
using UnityEngine.AI;
|
|
|
|
public class TurretController : MonoBehaviour, IPooledObject{
|
|
|
|
[SerializeField] float speed = 1f;
|
|
[SerializeField] Animator anim = default;
|
|
[SerializeField] GameObject head = default;
|
|
[SerializeField] GameObject headObj = default;
|
|
|
|
[Space]
|
|
[SerializeField, Range(0, 3f)] float firstAttackDelay = 1f;
|
|
[SerializeField] int numberOfDisks = 10;
|
|
int currentDisk;
|
|
[SerializeField] float maxHeigth = 1f;
|
|
[SerializeField] float minHeigth = 0f;
|
|
[SerializeField] GameObject turretObject = default;
|
|
[SerializeField] Transform shootPos = default;
|
|
|
|
[Space]
|
|
[SerializeField, Range(0, 15)] float shootingDistance = 7f;
|
|
[SerializeField, Range(0, 5)] float aimingTime = 2f;
|
|
[SerializeField, Range(0, 1)] float attackDelay = .25f;
|
|
[SerializeField] LayerMask whatIsPlayer = default;
|
|
[SerializeField] LayerMask whatIsWall = default;
|
|
PlayerController player;
|
|
float rotationVelocity;
|
|
bool canAttack;
|
|
bool aiming;
|
|
bool prepareShooting;
|
|
bool playerDetected;
|
|
|
|
NavMeshAgent agent;
|
|
|
|
[HideInInspector] public EnemySpawner spawner;
|
|
[HideInInspector] public RoomTrigger room;
|
|
|
|
// Start is called before the first frame update
|
|
void Awake(){
|
|
agent = FindObjectOfType<NavMeshAgent>();
|
|
player = FindObjectOfType<PlayerController>();
|
|
agent.speed = speed;
|
|
}
|
|
|
|
public void OnObjectSpawn(){
|
|
currentDisk = numberOfDisks;
|
|
turretObject.transform.localPosition = new Vector3(minHeigth + (maxHeigth - minHeigth) / numberOfDisks * currentDisk, 0, 0);
|
|
playerDetected = aiming = prepareShooting = canAttack = false;
|
|
agent.Warp(transform.position);
|
|
agent.isStopped = true;
|
|
StartCoroutine(FirstAttackDelay());
|
|
}
|
|
|
|
IEnumerator FirstAttackDelay(){
|
|
yield return new WaitForSeconds(firstAttackDelay);
|
|
canAttack = true;
|
|
}
|
|
|
|
void Update(){
|
|
if(!playerDetected && Physics.CheckSphere(transform.position, shootingDistance, whatIsPlayer)){
|
|
agent.isStopped = false;
|
|
playerDetected = true;
|
|
}
|
|
|
|
Vector3 dire = (player.transform.position - (transform.position + Vector3.up * .3f)).normalized;
|
|
//Ray rayx = new Ray(transform.position + Vector3.up * .3f, dire * Vector3.Distance(transform.position + Vector3.up * .3f, player.transform.position));
|
|
//Debug.DrawRay(rayx.origin, rayx.direction * Vector3.Distance(transform.position + Vector3.up, player.transform.position));
|
|
|
|
if (Physics.CheckSphere(transform.position, shootingDistance, whatIsPlayer) && canAttack && currentDisk > 0){
|
|
Ray ray = new Ray(transform.position + Vector3.up * .3f, dire * Vector3.Distance(transform.position + Vector3.up * .3f, player.transform.position));
|
|
if (!Physics.Raycast(ray, Vector3.Distance(transform.position + Vector3.up * .3f, player.transform.position), whatIsWall)){
|
|
StartCoroutine(Shoot());
|
|
canAttack = false;
|
|
}
|
|
}
|
|
|
|
if (Physics.CheckSphere(transform.position + Vector3.up, shootingDistance, whatIsPlayer) && canAttack && currentDisk == 0){
|
|
Ray ray = new Ray(transform.position + Vector3.up * .3f, dire * Vector3.Distance(transform.position + Vector3.up * .3f, player.transform.position));
|
|
if (!Physics.Raycast(ray, Vector3.Distance(transform.position + Vector3.up * .3f, player.transform.position), whatIsWall)){
|
|
StartCoroutine(ShootHead());
|
|
canAttack = false;
|
|
}
|
|
}
|
|
|
|
if (aiming){
|
|
if (!prepareShooting){
|
|
agent.SetDestination(player.transform.position);
|
|
}else{
|
|
Vector3 pos = player.transform.position - transform.position;
|
|
float rotY = Mathf.Atan2(-pos.z, pos.x) * Mathf.Rad2Deg;
|
|
float angle = Mathf.SmoothDampAngle(transform.eulerAngles.y, rotY + 90, ref rotationVelocity, .1f);
|
|
transform.rotation = Quaternion.Euler(0f, angle, 0f);
|
|
}
|
|
}else if (playerDetected && !prepareShooting){
|
|
agent.SetDestination(player.transform.position);
|
|
}
|
|
}
|
|
|
|
IEnumerator ShootHead(){
|
|
aiming = true;
|
|
yield return new WaitForSeconds(aimingTime);
|
|
agent.isStopped = true;
|
|
prepareShooting = true;
|
|
yield return new WaitForSeconds(attackDelay);
|
|
agent.isStopped = false;
|
|
aiming = false;
|
|
prepareShooting = false;
|
|
anim.SetTrigger("Shoot");
|
|
currentDisk--;
|
|
//turretObject.transform.localPosition = new Vector3(minHeigth + (maxHeigth - minHeigth) / numberOfDisks * currentDisk, 0, 0);
|
|
headObj.SetActive(false);
|
|
//FrisbieController frisbie = ObjectPooler.instance.SpawnFromPool("Disk", shootPos.position, transform.rotation).GetComponent<FrisbieController>();
|
|
ObjectPooler.instance.SpawnFromPool("TurretHead", shootPos.position, transform.rotation);
|
|
canAttack = true;
|
|
gameObject.SetActive(false);
|
|
player.percentage += Utils.RAM_cleanseSmall;
|
|
room.Die(gameObject);
|
|
}
|
|
|
|
IEnumerator Shoot(){
|
|
aiming = true;
|
|
yield return new WaitForSeconds(aimingTime);
|
|
agent.isStopped = true;
|
|
prepareShooting = true;
|
|
yield return new WaitForSeconds(attackDelay);
|
|
agent.isStopped = false;
|
|
aiming = false;
|
|
prepareShooting = false;
|
|
anim.SetTrigger("Shoot");
|
|
currentDisk--;
|
|
turretObject.transform.localPosition = new Vector3(minHeigth + (maxHeigth - minHeigth) / numberOfDisks * currentDisk, 0, 0);
|
|
ObjectPooler.instance.SpawnFromPool("EnemyDisk", shootPos.position, transform.rotation);
|
|
//FrisbieController frisbie = Instantiate(bullet, transform.position + Vector3.up, transform.rotation).GetComponent<FrisbieController>();
|
|
canAttack = true;
|
|
}
|
|
|
|
void OnTriggerEnter(Collider col){
|
|
if (col.CompareTag("Disk")){
|
|
player.percentage += Utils.RAM_cleanseSmall;
|
|
gameObject.SetActive(false);
|
|
col.GetComponent<Rigidbody>().velocity = Vector3.zero;
|
|
room.Die(gameObject);
|
|
GameMaster.Instance.Pooler.SpawnFromPool("EnemyExplosion", transform.position);
|
|
if (Utils.spawnDisk())
|
|
GameMaster.Instance.Pooler.SpawnFromPool("DiskPickup", transform.position);
|
|
StopAllCoroutines();
|
|
}
|
|
}
|
|
void OnCollisionEnter(Collision col){
|
|
if (col.gameObject.CompareTag("Disk")){
|
|
player.percentage += Utils.RAM_cleanseSmall;
|
|
gameObject.SetActive(false);
|
|
col.gameObject.GetComponent<Rigidbody>().velocity = Vector3.zero;
|
|
room.Die(gameObject);
|
|
GameMaster.Instance.Pooler.SpawnFromPool("EnemyExplosion", transform.position);
|
|
if (Utils.spawnDisk())
|
|
GameMaster.Instance.Pooler.SpawnFromPool("DiskPickup", transform.position);
|
|
StopAllCoroutines();
|
|
}
|
|
}
|
|
|
|
void OnDrawGizmosSelected(){
|
|
Gizmos.DrawWireSphere(transform.position, shootingDistance);
|
|
}
|
|
}
|