Hello,
I’m working my way through the platformer tutorial by GamesPlusJames, and reached the part with the flying enemy. I followed the tutorial without a hitch, and now have a script giving the flying enemy a perimeter around her, in which she follows the player whenever he’s inside the perimeter, and facing away from her (like the ghosts in Mario).
Unsatisfied with an idle enemy that you can just shoot while facing, I decided to add something into the code myself so that if the enemy has been damaged, she’ll follow the player regardless of his position, or where he’s facing.
I achieved this by accessing the separate script which manages the enemy’s health, and added the separate statement:
if(flyingHealth.enemyHealth < 3) { transform.position = Vector3.MoveTowards(transform.position, thePlayer.transform.position, moveSpeed * Time.deltaTime); //Move the flying enemy towards the player return; //Prevents the rest of the effects below from occuring while the statement is running }
And it seemed to work. If I shot the enemy, she would follow me, no matter how far away I was, and regardless of whether I was facing her or not.
Then, naturally, I made the enemy a prefab, so I could create more of her in other parts of the game. And then the code I added no longer works. She’ll still follow the player if I enter her perimeter and face away, but if I shoot her, she’ll just stay idle.
I even tried creating an OnTrigger2D event for if the enemy’s collider comes into contact with the player’s projectile, but it didn’t change anything. I personally can’t understand why turning the enemy into a prefab like this has suddenly caused it to ignore this segment of its script, so I’ve decided to ask for help on the matter.
Here’s the script in full below:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class FlyingEnemyAttack : MonoBehaviour
{
private PlayerController thePlayer; //Enables access to the Player Controller script
public float moveSpeed; //Flying enemy's movement speed
public float playerRange; //The distance from the flying enemy the player must enter before its pursuit
public LayerMask playerLayer; //Access the player's layer setting
public bool playerInRange; //Checks whether or not the player is within the flying enemy's pursuit perimeter
public bool facingAway; //Checks whether or not the player is facing away from the flying enemy
public bool followOnLookAway; //Makes the flying enemy pursue the player if he's not looking at her
private EnemyHealthManager flyingHealth; //Enables access to the Enemy Health Manager script
// Start is called before the first frame update
void Start()
{
thePlayer = FindObjectOfType<PlayerController>(); //Access the Player Controller script
flyingHealth = FindObjectOfType<EnemyHealthManager>(); //Access the Enemy Health Manager script
}
// Update is called once per frame
void Update()
{
playerInRange = Physics2D.OverlapCircle(transform.position, playerRange, playerLayer); //Sets the flying enemy's pursuit perimeter
if(flyingHealth.enemyHealth < 3)
{
transform.position = Vector3.MoveTowards(transform.position, thePlayer.transform.position, moveSpeed * Time.deltaTime); //Move the flying enemy towards the player
return; //Prevents the rest of the effects below from occuring while the statement is running
}
if (!followOnLookAway) //If the player is facing the flying enemy
{
if (playerInRange) //If the player enters the flying enemy's pursuit perimeter
{
transform.position = Vector3.MoveTowards(transform.position, thePlayer.transform.position, moveSpeed * Time.deltaTime); //Move the flying enemy towards the player
return; //Prevents the rest of the effects below from occuring while the statement is running
}
}
if((thePlayer.transform.position.x < transform.position.x && thePlayer.transform.localScale.x < 0) || //If the player is facing left while the flying enemy is on the right
(thePlayer.transform.position.x > transform.position.x && thePlayer.transform.localScale.x > 0)) //Or if the player is facing right while the flying enemy is on the left
{
facingAway = true; //Recognises that the player is facing away
}
else //If the player is facing towards the flying enemy
{
facingAway = false; //Recognises that the player is facing her
}
if (thePlayer.transform.position.x > transform.position.x && thePlayer.transform.localScale.x > 0) //If the player is facing right while the flying enemy is on the left
{
facingAway = true; //Recognises that the player is facing away
}
if (playerInRange && facingAway) //If the player enters the flying enemy's pursuit perimeter and facing away from her
{
transform.position = Vector3.MoveTowards(transform.position, thePlayer.transform.position, moveSpeed * Time.deltaTime); //Move the flying enemy towards the player
}
}
/*void OnTriggerEnter2D (Collider2D other)
{
if(other.name == "PlayerProjectile")
{
transform.position = Vector3.MoveTowards(transform.position, thePlayer.transform.position, moveSpeed * Time.deltaTime); //Move the flying enemy towards the player
}
}*/
void OnDrawGizmosSelected ()
{
Gizmos.DrawWireSphere(transform.position, playerRange); //Draw a circle to see the flying enemy's pursuit perimeter during development
}
}
Thanks in advance.
EDIT: I got the behaviour to finally work as I wanted to; the enemy is following the player now if I shoot them.
However, I now find that every flying enemy in the entire scene will follow the player like this if I reduce the health of just one. Is there a way I can separate their behaviour so that only the one I shoot will start following the player?