How to move a node across a scene?

:information_source: Attention Topic was automatically imported from the old Question2Answer platform.
:bust_in_silhouette: Asked By redstonecreeper8

I have a player character that I want to be able to seamlessly transition between different scenes. The way I tried to do this was by using an autoload script. There was a variable “player” that stored the player node, and whenever the player passes a certain location, the autoload changes the scene and adds the player variable to the new scene root using add_child(). However, whenever this function runs the game instantly crashes with no error message. I can post a gif of what happens with my specific code if that helps. Thanks in advance! :slight_smile:
Edit: I have found out my problem is due to the player variable becoming “Deleted Object” when I change scenes. This is because the variable is pointing to a specific node in a specific scene. So what I want to know, is how can I “save” the player node as a scene that I can instance in the next scene? Thanks! :slight_smile:

:bust_in_silhouette: Reply From: Forsaken

So I assume, 2 things:

  • either you are loosing a reference to player instance
  • or you are deleting player with a scene, because it’s connected

The way I would do it, is to store a reference to a player somewhere in a singleton, or add it to the root tree temporarily and then, when a new scene is loaded, add it as a child. But the important thing here is that you need to call remove_child first like this:

player.get_parent().remove_child(player)
# or if the parent of player is current scene just remove_child(player)

# store player reference
Global.store_player(player)

# after a new scene is loaded
add_child(Global.get_player())
:bust_in_silhouette: Reply From: avencherus

When you aim to change the scene you have to remove the player from the existing scene first. If you call a scene change first it will free all its children. Usually everything is queued to be freed. At that point it doesn’t matter if you remove the player from the scene, it’s too late and has been queued to be freed.

Since it’s queue_free()'d you should be able to validly move it during the code, because it won’t go null until after your code is executed. Then the reference is lost in the next frame.

Some pseudo code of the process.

player = get_player()
player.get_parent().remove_child(player)  # Take player out first.

change_scene()

get_current_scene().add_child(player)
player.position = get_spawner().global_position