Enemy Script Help

I made an enemy that follows me and I wanted to spawn multiple instances of it in a round-like fashion. I made it into a prefab and made a script that duplicates the prefab. My problem is that the “prefab” enemies (the duplicates) don’t deal damage to the player.

I also noticed that I cannot set the values of the prefab in the inspector tab.

Here is the script that controls my enemy. It is very messy but it works.

using UnityEngine;
using System.Collections;
using UnityEngine.UI;

public class EnemyAI : MonoBehaviour
{
    public Transform target;
    public float moveSpeed;
    public int rotationSpeed;
    public float maxdistance = 0.3f;
    private int attackcooldown;
    public Slider HealthSlider;
    public int enemydamage = 3;
    public int enemyhealth;
    public UnityStandardAssets.Characters.FirstPerson.FirstPersonController Controller;

    private int PlayerPoints;

    private Transform myTransform;

    //If the enemy dies...
    void enemydeath ()
    {
        Destroy(gameObject);
        GetComponent<PointManager>().points = GetComponent<PointManager>().points + 50;
        PlayerPoints = GetComponent<PointManager>().points;
        GetComponent<PointManager>().ScoreText.text = "" + PlayerPoints;
    }


    void Awake()
    {
        myTransform = transform;
        attackcooldown = 0;
    }


    void Start()
    {
        GameObject go = GameObject.FindGameObjectWithTag("Player");

        target = go.transform;

        maxdistance = 1.3f;
    }


    IEnumerator Wait()
    {
        yield return new WaitForSeconds(0.4f);
        attackcooldown = 0;
       
    }


    void Update()
    {
        Debug.DrawLine(target.position, myTransform.position, Color.red);


        myTransform.rotation = Quaternion.Slerp(myTransform.rotation, Quaternion.LookRotation(target.position - myTransform.position), rotationSpeed * Time.deltaTime);

        if (Vector3.Distance(target.position, myTransform.position) > maxdistance)
        {
            //Move towards target
            myTransform.position += myTransform.forward * moveSpeed * Time.deltaTime;
        }
        if (Vector3.Distance(target.position, myTransform.position) < maxdistance && attackcooldown == 0)
        {
            attackcooldown = 1;
            Debug.Log("enemy hit you!");
            Controller.GetComponent<PlayerVitals>().healthSlider.value = Controller.GetComponent<PlayerVitals>().healthSlider.value - enemydamage;
            StartCoroutine (Wait());
        }
        if (enemyhealth <= 0)
        {
            enemydeath();
        }
    }
}

also, I get a “Object reference not set to an instance of an object” error on line 72 if anyone knows how to fix that.

If it helps, here is an image of the inspector. I cannot set the values for “Target”, “Health Slider”, and “controller”.

3139519--238135--Capture.PNG

You can’t set values of prefabs and have them point to stuff in the scene as it doesn’t hold that sort of reference.

You’re not doing damage because of your error. Chances are, controller is null. This should show in the inspector on enemies that spawn. You’ll need to assign something to it or you’ll need playerVitals to be a singleton.

Or, you have a manager script with static methods that can be called to deal damage to the player, update health bar, etc, which is generally a better idea than having each enemy try to manage that stuff.

So I need another script to store values instead of each enemy storing its own?
Sorry if I’m slow to understand, I am fairly new at this.

You don’t have to do it that way, I just suggest it.

Think of it this way. You have all this stuff in your scene (player, health bar, other stuff). Your manager contains references to these things. All this is in your scene.

Now, your enemy spawns, you have a few choices. Initialize a reference to all the stuff in the scene, or, simply have your enemies get values from the manager (or call methods on the manager). Thus, if my enemy deals damage, it should tell my manager to deal damage, my manager can handle dealing the damage, updating health bars, and also checking if the player died.

You can also get values off your manager if you absolutely need to. Instead of each enemy spawning and trying to find everything, your manager maintains your reference and you just get the value off of it.

Also, consider another scenario. Let’s say you have 20 enemies on the scene and your player drops a decoy. Now you want your enemies to go towards the decoy and not your player. Do you want to change that on all 20 enemies? Or even check for the decoy to exist when you spawn new enemies? Probably not. You simply change the target in your manager and all enemies go towards the decoy. Then when the decoy is destroyed or timer runs out, you switch it back to the player and they start moving towards the player again.

Just a general idea of how a manager script can make a difference.