I need help handling the leftover Player after returning Outside

Player is DontDestroyOnLoad
Player GameObject is only in the main scene (Outside)

I want to be Outside, enter my House, return Outside (Without having the leftover Player still there)

I am already able to enter my House and return Outside. My only problem at the moment is the leftover Player

The reason I am using DontDestroyOnLoad is that I am using 2 children of Player to hold item counts for the UI and I don’t want them destroyed.

I am using Sprites for the numbers in the UI and a bool in the Animator to hold the count

I can post more code but I don’t know what to post exactly. So here is where I’m at:

-What do I do to prevent the duplicate?

Here is my grab item storer(they’re tomatoes):

    void grabTomatos ()
    {
        animtomatoCount.SetFloat ("tomatoAmount", nowTomatos+4f);
    }

    void Start ()
    {
        nowTomatos = animtomatoCount.GetFloat ("tomatoAmount");
    }
 
    void Update ()
    {
        if (grabtomatosCheck == true && canPlant == true && Input.GetKeyUp (KeyCode.H) && canHarvest == true)
        {
            grabTomatos ();
        }
    }

Are you saying that there is a script that spawns your player outside that is running when the scene loads?
If that’s the case, then you should check if an instance already exists and do not load if so, I think? :slight_smile:

1 Like

This is my script from the House → Outside

public class enterOutside : MonoBehaviour
{
    public bool playeratDoor;

    // Use this for initialization
    void Start ()
    {
        playeratDoor = false;
    }
 
    // Update is called once per frame
    void FixedUpdate ()
    {
        if (playeratDoor == true)
        {
            SceneManager.LoadScene("Space");// <--- this is Outside
        }
    }
}

I guess I was thinking of it in 2-parts.

Player enters house (repoisiton Player & then make boolA = true)
Player leaves house (reposition Player & then make boolA = false again)

Excellent, that doesn’t really help me to know if you have something that spawns the player outside, though :wink: heh.

However, since you showed that code, I have a suggestion. If you have another piece of code that changes playeratDoor to true, I think you should put the LoadScene when & where that happens, rather than polling in FixedUpdate for a change. For 1 script/bool, it makes no difference, really, but it is a good habit to be in when you’re programming. =)

1 Like

I’m not spawning anything that I know of. If I can Instantiate the Player at a certain state(a.k.a. save the tomatocount), that would solve my problem.

tomatocount being a float in the Animator

*edit ill take a look
ty

I’m running a Distance script which tells whether the Player is at the door. Can it become a light performance issue down-the-road or something?

public class darylsoutsidedoorDist : MonoBehaviour
{

    public GameObject Player;
    public GameObject DarylsDoor;
    public float ddoorDist;
    public float ddoorRange = 1f;

    // Update is called once per frame
    void Update ()
    {
        ddoorDist = Vector3.Distance (Player.transform.position, DarylsDoor.transform.position);

        if (ddoorDist < ddoorRange)
        {
            DarylsDoor.GetComponent<enterDarylsHouse> ().playeratdDoor = true;

        }

        if (ddoorDist > ddoorRange)
        {
            DarylsDoor.GetComponent<enterDarylsHouse>().playeratdDoor = false;
        }
    }
}

Okay, is the player in the scene (Outside) when you run the game? This would be like “spawning” (by the engine, not you in code). If that’s the case, what you can do is check if the player has already been created (eg: anytime after the first load), and if it’s already there, destroy the new instance that’s loaded with the scene.

You responded while I was writing that. As for your distance check, that seems okay. Since you know ‘at the door’ is false to begin with, I would erase the part about setting it false. Then, I would just add changing the scene right there (in the distance check - you don’t even need the other script or variable).
Does that make sense?

1 Like

It does make sense. Less scripts to deal with is always good too lol. So, how would I go about checking if the player has already been created?(anytime after the first load) & destroying the new instance that’s loaded with the scene.

*The reason I’m asking here is because when I tried that earlier I was using GameObject.Find and it was finding both objects. I’m not sure how to cut-in before it spawns the extra Player

So sorry. YES Player is in the first scene (Outside)

Well, it’s relevant if the player is in the scene; if that’s not true, then ignore this…

You could have a static instance that’s set to (a script on the player). Assign that when you first load, and then if it’s not null, destroy the game object (that would be any other time the scene loads).
You could try just a bool, too, if you don’t really need the other (don’t want to complicate or confuse you).
Something like this:

static bool hasLoaded = false;

void Awake() {
 if(hasLoaded) {
      Destroy(gameObject);
      return;
    }
  hasLoaded = true;
  DontDestroyOnLoad(gameObject); // <- you already have something like this.
 }
1 Like

Totally worked. Thanks again. You Rule!

Great, glad to hear that. :slight_smile: You’re welcome. Enjoy your game!

Know how to GameObject.Find a child object?

tomatoCount = GameObject.Find (“DontDestroyOnLoad/Player/MainCamera/tomatoCount”);
and
tomatoCount = GameObject.Find (“Player/MainCamera/tomatoCount”);

doesn’t seem to work

I tend to avoid GameObject.Find whenever possible.

Is there some reason you cannot create a reference to this where it’s needed and drag n drop?

My game is about farming. I have gardening plots(100 of them). When I return Outside, some of their assignments are missing because they are not assigned at start.

Okay… Is TomatoCount also a script (name)? Is it on the DontDestroyOnLoad, too? – I think so from how you worded your example above.

So long as you set this up on 1 script on the player, you could use it to get any other script on the player (or player’s parent / child game objects).

You can add this in TomatoCount:

static TomatoCount instance;
public static TomatoCount Instance { get { return instance; }};

void Awake() {
    if(instance == null) instance = this;
  }

Then, when your other scripts need to get the reference, they can do something like this:

TomatoCount tomatoCount;
void Start() {
   tomatoCount = TomatoCount.Instance;
  }
1 Like

You could also use GameObject.FindObjectOfType (provided there is just 1 of these scripts), you’d get it that way. Whichever seems good for you.

1 Like

Can DontDestroyOnLoad only be used twice or something?

1st script

public class DoNotDestroy : MonoBehaviour
{
    public GameObject Player;
    public GameObject waterWellbtn;
    public GameObject garden1;


    void Start ()
    {
        DontDestroyOnLoad (Player);
        DontDestroyOnLoad (waterWellbtn);
        DontDestroyOnLoad (garden1); // <--- putting it here didnt work



    }

}

2nd script

public class DNDgarden1 : MonoBehaviour
{
    public GameObject garden1;


    void Awake ()
    {
        DontDestroyOnLoad (garden1);

    }

}

Yet my garden1 is still deleted…

There’s no limitation I’m aware of. Are you sure you’re not destroying it elsewhere?

1 Like