Don't Destroy on Load not Working

Sorry to bother you again so quickly after the darkened sprites fiasco, this was actually happening during that but I figured I could solve it my self afterwards. I don’t have a clue as to what’s wrong though. During the process of changing the theme and sprites, I must’ve changed something in the code, despite me not remembering touching it, and I can’t find out what it could be. So, the problem is as follows. The score text resets itself whenever the next level is loaded. I did a lot of tests using Debug.Log to find out what part of the Singleton Pattern is being ran, and every single time the script with the score text and pattern is being kept and marked as Don’t Destroy on Load. I did more tests, by making a serialzied field with a value of 13, and then setting the number to 20 on the first level. If Don’t Destroy was working, than that script should have been kept and the number should have stayed at 20 when the next level loaded in. But it was changed to 13, meaning that it had been deleted and replaced. I don’t get why it’s not working, it shows the script as being under Don’t Destroy On Load in the Hierarchy, but it’s getting destroyed anyways. I could really use some help in figuring this out, thanks again.

Can you please post your code and information about the involved game objects and I will try and help you solve it :slightly_smiling_face:

Thanks, Here’s all the other info. Let me know if there’s more or something specific you need.
GameStats is a game object made for keeping track of different parts of the game, such as how fast the game is playing, how many points are rewarded whenever a block is destroyed, and what the current score is.
Screenshot (75)
In this case, it’s telling the score text what to set the score too (More Score Text later) and running the Singleton Pattern. When GameStats is first awakened, it runs the pattern, and checks to see if there’s more than one of itself. If there is, then it marks itself as inactive, and destroys itself. Otherwise, it’ll make it so it doesn’t get destroyed when the next level does loads in.
(The selected code is what I’m trying to show you, and the code that was turned into notes was used to help find out what was being run as I mentioned in the first post)


The Score Text is a Text Mesh Pro UI text box that has a custom font and is a child under the Game Canvas, which is a perfectly default UI Canvas. Whenever a block is destroyed in the game, it runs the AddPoints method which is in GameStats, which adds the chosen point amount to the current score. then in void update, it takes the score text, which is selected in the GameStats Inspector, and changes the text to show the current score. All of this works fine.
Screenshot (78)
(the variable at the bottom of the next picture is also important to the topic)
Screenshot (77)
Screenshot (76)
I made the Game Canvas a child under GameStats so that way the score text is also put on Don’t Destroy On Load, and it does this according to the hierarchy.

But according to the testing I did, it destroys GameStats anyways, for who knows why. So when a new GameStats is loaded along with the next level, the Singleton Pattern sees it as being the only one, and doesn’t destroy it, and the game uses the new current score, which is now at zero.

Okay I read through several times and examined the photos very carefully and the only thing that really catches my attention is the method named DestroyObject in your singleton pattern, is that a method you wrote or a Unity method?

It’s a unity method. One I got from the lecture this was posted under. I know it says it’s obsolete, but I tried the other one it said and it still didn’t work. I figured it would be best to change it back to the one that was working before.

I did another test, and made another script with another singleton pattern, but this time it worked, and the game object wasn’t destroyed when the next scene loaded in. Which caused the new gameobject to be destroyed and replaced. This must mean that somewhere in the script with the first Singleton Pattern I put something that messed it up.

I could really use some help finding out what the problem here is. I don’t have the lightest idea what part of my code could possibly be causing it to not work. Maybe It could be some setting or something that’s only turned on for the game object it’s attached to. Whatever the reason, Don’t Destroy on load is only not working for this script, and I don’t know why. Here’s all the code for anyone that wants to help me crack this.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using TMPro;

public class GameStats : MonoBehaviour
{
//config params
[Range(0f, 10f)] [SerializeField] float timeRate = 1f;
[SerializeField] int pointsPerBlockReward = 10;
[SerializeField] TextMeshProUGUI scoreText;
[SerializeField] float speedIncreaseSize = 0.2f;
[SerializeField] float defaultTimeRate = 1f;
[SerializeField] bool autoPlay;

//state variables
[SerializeField] int currentScore = 0;

private void Awake()
{
    int gameStatusCount = FindObjectsOfType<GameStats>().Length;
    if (gameStatusCount > 1)
    {
        Debug.Log("GameStats destroyed");
        gameObject.SetActive(false);
        Destroy(gameObject);
    }
    else
    {
        DontDestroyOnLoad(gameObject);
        Debug.Log("GameStats kept");
    }
}

// Start is called before the first frame update
void Start()
{

}

// Update is called once per frame
void Update()
{
    Time.timeScale = timeRate;
    scoreText.text = currentScore.ToString();
}
public void AddPoints()
{
    currentScore += pointsPerBlockReward;
}

public void ResetScore()
{
    Destroy(gameObject);
}
public void IncreaseSpeed()
{
    timeRate += speedIncreaseSize;
}
public void ResetSpeed()
{
    timeRate = defaultTimeRate;
}
public bool IsAutoPlayEnabled()
{
    return autoPlay;
}

}

Hi William,

Please note, it’s better to copy/paste your code and apply the code fencing characters, rather than using screenshots. Screenshots are ideal for displaying specific details from within a game engine editor or even error messages, but for code, they tend to be less readable, especially on mobile devices which can require extensive zooming and scrolling.

You also prevent those that may offer to help you the ability to copy/paste part of your code back to you with suggestions and/or corrections, meaning that they would need to type a potentially lengthy response. You will often find that people are more likely to respond to your questions if you make it as easy as possible for them to do so.

And what problem do you have? This is a long thread. I’m not sure what you already fixed.


See also;

Ok, thanks. I think of doing it like that, I’ll be sure to check out that forum. And for my problem is the Singleton Pattern I have in this specific script isn’t working. After many tests, I’ve found out that the game object the script is attached to is being marked as Don’t Destroy On Load, but when the next scene is loaded it’s destroyed anyways. If I make a new script with just a singleton pattern in it, that one will work fine, leading me to think there must be something in the code of the broken one that’s messing it up. But I can’t figure out what it could be.

When does this method get called?

public void ResetScore()
{
    Destroy(gameObject);
}

Since the objects share the same name, you could log GetInstanceID() along with a meaningful message into your console. Do that in Awake and in ResetScore to see if your “singleton” got destroyed by the ResetScore method.

Wow. that was it. Apparently the method was also being called whenever the blocks were below zero, not just when the game was reset, and I have zero memory why. Thanks so much, I never would have thought it’d be something as simple as that. Now I’m worried that there was an important reason I had that called there, and it’s going to mess it up in some way :sweat_smile: Well, I guess I’ll deal with that when I encounter it.

In a normal Unity game, only two things destroy game objects: the Destroy method or Unity when a new scene gets loaded. For this reason, when a game object “magically” disappears from the Hierarchy, the first thing I usually do is looking for a Destroy method. Then add a bunch of Debug.Logs to the code to get more information on what is going on during runtime. The rest is about interpreting the information correctly.

Ok, thanks. I’ll defiantly try that when something similar happens in the future. After looking over where the method was called, I think what happened is I was trying to call the method called ResetSpeed, and when autofill popped up I pressed tab and didn’t realize it filled in ResetScore instead.

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.

Privacy & Terms