Looking for a Pattern / Good Practice to set variables in scenes that are inside scenes, in a global scene

Godot Version

4.2

Question

Ok, I’m having this doubt since I started doing Godot from Unity, and I still don’t have a proper pattern that makes me satisfied. And that is: accessing variables of scenes that are inside scenes, in ta parent scene xD… I’m going to put some examples:

  • You have a scene that is a cowboy and it holds a weapon. The weapon is a scene that has many variables, one is bullets for example. The cowboy has a weapon. Now let’s say I have a scene that is a bar, and I put two cowboys there. One has a weapon with 3 bullets, and the other one has a weapon with 2 bullets.

  • You have a scene called “DamageReceiver” that manages everything related to being able to get hit and eventually die (or break) signaling up when the health is lower or equal to 0. The Damage Receiver has the hitbox, and is holding the health variable, so I can put that scene anywhere and that thing will have health, react to hits and eventually die or break. So you put this DamageReceiver into the enemy scene, and add some enemies into the world with different healths.

  • You have a scene for an enemy. Then, you have the head scene, the body scene and the tentacles scene. the “Enemy” scene holds these 3 scenes: head, body and tentacles. Let’s say tentacles have a variable called “amount” that draws this amount of tentacles. I want to put different enemies in my map (with different tentacles for example)

How do I solve this? It comes to my head 2 ways of solving these 3 cases:

  • “Editable children” so you can set those variables in the main scene (the bar, the world, the map). This doesn’t look like something that I should all the time, it exposes everything just for a variable and doesn’t look like the best approach.
  • Set a variable in the root node and send it down to the scene that uses it. This doesn’t scale, everytime I make a new weapon I have to add a variable to the cowboy? not much sense to me.

So is there a pattern to solve this? I Really hope I explained properly. Thanks!

2 Likes

An instanced scene is a Node, and that Node is the same as the root of that instanced scene.
If that root Node has a script that @exports a variable, that variable is editable from the instanced scene in the tree view.
So say you have you Gun scene, you @export the bullets variable in it, then when you instance it in the editor, click on it on the tree view or the editor view and the properties view will show a bullets field that you can edit. That field will only affect that specific instance of the scene. If you click on the claquette icon it will open the “model” scene and you will see the bullets remains unset there.
This way you can configure different instances of scenes that act in a similar way, but depend on which specific copy it is.

1 Like

Yeah. but my question is: The gun is inside the cowboy, and it’s the cowboy the one I instantiate in the editor.

oh, yeah, then you do need to have a bullets var in the cowboy and foward that to the gun on init
there are ways to make components that modify parents in a way to make this automatic, but it is a lot more complicated and may not be worthwile as it would require the use of the @tool annotation

Iam also interested in bestpractices for this.

My current solution would be:

  1. export variable on cowboy, let cowboy instance a gun node on init with variable set.
  2. A configuration-node that exports all your variables that specify for example your level as data as exported variables. Get this node on init in all your dynamic nodes and get the data from it to set the variables from within those nodes. Fallback to defaults if no level-configuration node found.

Yeah, everybody is answering this to me around, I guess this is the way. It’s just not super escalable to me… it couples things together. But if it’s the standard way… I will follow that.

instancing on init is not bad, although that’s almost the same as having it already and passing the variable down.

This looks a bit too overcomplicated maybe?

Thanks a lot for the responses!

I think the only problem you’re getting into with the scalability is that the godot editor just doesn’t work like that. It is possible to get this kind of composable interface, but if you want to see that in the editor panels, you’d have to use a @tool script. It feels like overkill, but if you insist, it is possible.