/*
*Author: Lin Hengrui Ryan
*Date:21/06/2024
*Description: a sript to make enemy move
*/
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
using UnityEngine;
using UnityEngine.AI;
using UnityEngine.UI;
public class EnemyAi : MonoBehaviour
{
///
/// the navmesh agen to allow the enemy know where it can navigate
///
public NavMeshAgent agent;
///
/// to refrence the player to navigate the enemy to the player
///
public Transform player;
///
/// the physics layer of the ground so that the enemy knows where he can walk
///
public LayerMask groundMask;
///
/// the physic layer of the player to allow the enemy to checksphere
///
public LayerMask playerMask;
///
/// the health of the enemy
///
public int health = 100;
[Header("enemy stats")]
///
/// the point that the enemy will walk to when they are patroling
///
private Vector3 WalkPoint;
///
/// to bool to allow the walkpoint to be reset
///
private bool walkPointSet = false;
///
/// the maximum range that the enemy will walk while patroling
///
public float walkRange;
///
/// how far the player is from the enemy to start chasing the player
///
public float sightRange;
///
/// how far the player is from the enemy to allow the enemy to start shooting
///
public float attackRange;
///
/// a bool to call the chase function
///
private bool playerInSightRange;
///
/// a bool to call the shoot function
///
private bool playerInAttackRange;
///
/// a variable to allow the enemy to refrence the gun to call its functions
///
public GameObject gun;
///
/// to show the enemy health in the world space ui
///
private Slider healthbar;
///
/// to calibrate the enemy health on load
///
void Awake()
{
healthbar = GetComponentInChildren();
healthbar.maxValue = health;
}
///
/// to constantly check for the player in the sphere and do the nessasary action and to destroy the enemy dies after the heath reaches 0 or less
///
void Update()
{
//Check for sight and attack range
playerInSightRange = Physics.CheckSphere(transform.position, sightRange, playerMask);
playerInAttackRange = Physics.CheckSphere(transform.position, attackRange, playerMask);
if (!playerInSightRange && !playerInAttackRange)
Patrol();
if (playerInSightRange && !playerInAttackRange)
Chase();
if (playerInAttackRange && playerInSightRange)
Attack();
if (health <= 0)
{
Destroy(gameObject);
}
if (player == null)
{
player = GameObject.Find("PlayerCapsule").transform;
}
healthbar.value = health;
}
///
/// to set the enemy to go to a position specified
///
private void Patrol()
{
Debug.Log("Patroling");
if (!walkPointSet)
{
SeachWalkPoint();
}
else
{
agent.SetDestination(WalkPoint);
}
;
Vector3 distaceToWalk = transform.position - WalkPoint;
if (distaceToWalk.magnitude < 1f)
{
Invoke("changePoint", 4f);
}
}
///
/// to allow the walkpoint to change
///
public void changePoint()
{
walkPointSet = false;
}
///
/// seach for a new walk point to somewhere that is in the walk radius and is on the ground
///
private void SeachWalkPoint()
{
float randomZ = Random.Range(-walkRange, walkRange);
float randomX = Random.Range(-walkRange, walkRange);
WalkPoint = new Vector3(
transform.position.x + randomX,
transform.position.y,
transform.position.z + randomZ
);
if (Physics.Raycast(WalkPoint, -transform.up, 2f, groundMask))
{
walkPointSet = true;
}
}
///
/// to make the enemy chase the player if it is not in the shooting range
///
private void Chase()
{
Debug.Log("chasing");
agent.SetDestination(player.position);
}
///
/// to make the enemy attack the player
///
private void Attack()
{
Debug.Log("Attacking");
agent.SetDestination(transform.position);
transform.LookAt(player);
gun.GetComponent().Shoot();
}
///
/// to see the ranges in the scene view
///
private void OnDrawGizmosSelected()
{
Gizmos.color = Color.red;
Gizmos.DrawWireSphere(transform.position, attackRange);
Gizmos.color = Color.yellow;
Gizmos.DrawWireSphere(transform.position, sightRange);
}
}