Why is my script working only for one Enemy?

So I made an EnemyManager Script to save which enemies in my scene are dead, the script goes like this :

using UnityEngine;
using System.Collections;

public class EnemyManager : MonoBehaviour {
    public GameObject Enemy1;
    public GameObject Enemy2;
    public GameObject Enemy3;

    public int EnemyDead_1;
    public int EnemyDead_2;
    public int EnemyDead_3;

    public int CheckIfDead_1;
    public int CheckIfDead_2;
    public int CheckIfDead_3;
    void Start () {
   
    }
   

    void Update () {
        if(EnemyDead_3 == 1){
            Destroy(Enemy3);
        }
        if(EnemyDead_2 == 1){
            Destroy(Enemy2);
        }
    if(EnemyDead_1 == 1){
            Destroy(Enemy1);
        }
        if(Enemy3.GetComponent <Enemy>().isDead == true){
            CheckIfDead_3 = 1;
        }else{
            CheckIfDead_3 = 0;
        }
   
        if(Enemy2.GetComponent <Enemy>().isDead == true){
            CheckIfDead_2 = 1;
            Debug.Log("enemy1 is dead");
        }else{
            CheckIfDead_2 = 0;
        }
    if(Enemy1.GetComponent <Enemy>().isDead == true){
            CheckIfDead_1 = 1;
        }else{
            CheckIfDead_1 = 0;
        }

    }
    public void SaveEnemy(){
        PlayerPrefs.SetInt("Enemy_3_Dead",CheckIfDead_3);
        PlayerPrefs.SetInt("Enemy_2_Dead",CheckIfDead_2);
        PlayerPrefs.SetInt("Enemy_1_Dead",CheckIfDead_1);
   
    }
    public void LoadEnemy(){
        EnemyDead_3 = PlayerPrefs.GetInt("Enemy_3_Dead");
        EnemyDead_2 = PlayerPrefs.GetInt("Enemy_2_Dead");
        EnemyDead_1 = PlayerPrefs.GetInt("Enemy_1_Dead");
   
    }

So SaveEnemy gets called when i press the savegame button, and load enemy when i press the load game button.

Now my problem is that this scripts works in weird combinations:
-If I kill Enemy1 then I kill Enemy2 and then Enemy3 only Enemy1 gets saved.
-If I kill Enemy2 then Enemy1 then Enemy3 only enemy2 and enemy3 are saved…
-If I kill Enemy3 then Enemy2 then enemy3 all of them are saved.

It’s really pissing me off since I’ve had this bug for a week now and no one was able to help me and when I show people this code they think it’s good and are also confused why it works this way.I checked if I didn’t attach enemies or if I didn’t attach functions to the buttons, no, it’s all good, the problem is in the script.

Please help me, thanks in advance.

try something like this using a list of a class holding all the data pertaining to the enemy.
when written like this the list can be made in the inspector so you can assign game objects to it.

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
[System.Serializable]
public class enemyData
{
    public string enemyName;
    public GameObject EnemyObj;
    public int alive = 1;
}
public class saveHelp : MonoBehaviour
{
    public List<enemyData> enemyList = new List<enemyData>();

    // run this to dstroy the gamebjects linked to the enem dta with alive = 0;
    void checkEnemyStatus()
    {
        foreach(enemyData enemy in enemyList)
        {
            if (enemy.alive == 0)
            {
                Destroy (enemy.EnemyObj);
            }
        }
    }

    //run this for killing an enemy with that string name
    void killEnemy(string name)
    {
        foreach(enemyData enemy in enemyList)
        {
            if(enemy.enemyName == name)
            {
                enemy.alive = 0;
            }
        }
    }
    void saveEnemyStatus()
    {
        foreach(enemyData enemy in enemyList)
        {
            PlayerPrefs.SetInt(enemy.enemyName,enemy.alive);
        }
    }
    void loadEnemyStatus()
    {
        foreach(enemyData enemy in enemyList)
        {
            enemy.alive = PlayerPrefs.GetInt(enemy.enemyName);
        }
    }

}

thanks for the code it really looks like it will work but I run into a problem. So i used ur code and made this:

    enemyData enm;
    void Start(){
   
        enm = GetComponent<enemyData>();
    }
    void Update(){
        checkEnemyStatus();
        if(enm.EnemyObj.GetComponent<Enemy>().isDead == true){
            killEnemy(enm.EnemyObj.GetComponent<enemyData>().name); 
            Debug.Log("imdead");
        }
        if(Save.isSaving == true){
            saveEnemyStatus();
            Save.isSaving = false;
        }
        if(Load.isLoading == true){
            loadEnemyStatus();
            Load.isLoading = false;
        }

Now I attached the gameobjects and did everything in the inspector…I have an enemyscript isdead is true whenever the enemy is dead so now on this line if(enm.EnemyObj.GetComponent().isDead == true){ there is a problem because it never Debug.Logs the “imdead”… Any ideas?

either it isnt getting the component in the if statement or .isdead is false.
try using the enemy data class to control all states of the enemy and the gameobject is just a visual representation of the enemy data.

put a enemyData reference on the enemy game object script.

public enemyData enemyData;
    string name = "put its name matching the name in the enemy list";
    void Start()
    {
        for(int i = 0; i < enemyList.Count; i++)
        {
            if(enemyList[i].enemyName == name)
            {
                enemyData = enemyList[i];
            }
        }
    }

on game start up it will link itself to the enemyList class
your enemy gameobject now is linked to its enemyList class counterpart. now all it needs to do is check if it is dead in its class in the enemy list.

in my experience when saving data its much easier to do it all in class lists and just use the game objects as “puppets” of the background data.

I think you are over complicating it by constantly trying to get component scripts for each enemy.

so now that both are linked to each other (list and gameobject) the gameobject can change the class in the list to dead from some stimuli in the game and the list can check all the game objects to see if they are alive or dead when saving and loading.

I know that’s a bit off topic, but your EnemyManager script is not flexible.

I would suggest you making a single script for each enemy, with private variables like health bar. When health bar is 0 then enemy can be destroyed or saved.
And so you can have as many enemies as you want without having to write variables for each of them.

But if you really want to solve this issue then try adding else if:

void Update () {
        if(EnemyDead_3 == 1){
            Destroy(Enemy3);
        }
        elseif(EnemyDead_2 == 1){
            Destroy(Enemy2);
        }
    else if(EnemyDead_1 == 1){
            Destroy(Enemy1);
        }
        if(Enemy3.GetComponent <Enemy>().isDead == true){
            CheckIfDead_3 = 1;
        }else{
            CheckIfDead_3 = 0;
        }

        if(Enemy2.GetComponent <Enemy>().isDead == true){
            CheckIfDead_2 = 1;
            Debug.Log("enemy1 is dead");
        }else{
            CheckIfDead_2 = 0;
        }
    if(Enemy1.GetComponent <Enemy>().isDead == true){
            CheckIfDead_1 = 1;
        }else{
            CheckIfDead_1 = 0;
        }
    }

This may possibly be the case of why it behaves like that.

probably a good idea to look up the “OnDestroy” function and the “observer” design pattern, much cleaner, more robust, far more flexible

@elmar1028 My problem is not that the gameobjects are not destroyed but CheckIfDead never changes :smile: , @Craig8726 it gives me an error “The name 'enemyList does not exist in the current context”… I have little to no experience with using lists so sorry if I’m being too stupid… I added the code in my “Enemy” class… if that’s where I should put it?

or should I put it in Savehelp?

When you declare CheckIfDead variables they’re empty (null). Maybe that’s the issue…

I dont think so because checkifdead works only for some enemies in specific combos if i kill enemy1 firrst and then kill everyone else and save, when i load checifdead is saved only for enemy 1, when i kill enemy3 first and then kill the others everything saves fine… It’s crazy… But the script Craig8726 looks very good so I’m gonna try to make that one work, just waiting for him to reply ^^

have you created the list and the enemy class?

you need a reference to the script the list is on and it needs to be public. its just like accessing other variables like ints and bools from other scripts

it doesnt really matter where the list is stored but i like to have an empty gameobject tagged to store stuff like that so it can be easily found by other scripts at run time.

heres an example of finding a script attached to another object that is tagged.

ItemDatabase itemDatabase;

    void Start()
    {
        itemDatabase =  GameObject.FindGameObjectWithTag ("ItemDatabase").GetComponent<ItemDatabase> ();
    }