CanvasLayer messing with code. A bug?

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

Hi. I’m working on RPG project and currently developing a character sheet. I created a system of acquiring skill points (rewarding them by just pressing a button) and then spending them on different skills. When available points drop to zero, buttons that allow the increase get disabled. And everything works without any problem. However, when I put character sheet scene in a CanvasLayer on my main scene, after available points drop to zero buttons don’t get disabled and available points go below zero into negative.
If I put the scene outside of CanvasLayer on the main scene, everything works well and there’s no problem. So the problem only exists when my character sheet scene is a child of CanvasLayer.
Any idea what’s causing this? And is there some alternative to canvaslayer for organizing GUI?

Are You sure You adapted the reference to the buttons after changing scene child-parent hierarchy ?

Inces | 2021-12-13 12:03

:bust_in_silhouette: Reply From: bloqm

Without seeing our code, it sounds like you have a bad initialization or perhaps a bad signals/node communication. Do you get any warning?
Double check every reference to nodes (every usage of $../.., get_node(...) and onready var pointing to nodepaths…) and signal connections.

I organize my UI by making each instanced scene (for example a sub-menu) have a “parent interface” script that takes care of all its children, and reports back their signals – so when you instance said sub-menu you only have to interface with it, not its children.

Thanks for you time. So far I haven’t used any onready var. I did use $../.. but I checked it a couple of times while connecting and disconnecting signals. I think that these lines stop working when the scene is moved to canvaslayer:
This one for specific stat:

if dict_bstat["constitution"] == 10:
	$Stats_info/Con_cont/TextureButton2.disabled = true

And this one under delta for grouped stats:

 if new_level == true and available_points > 0:
	for button in get_tree().get_nodes_in_group("PlusButtons"):
		button.set_disabled(false)
else:
	for button in get_tree().get_nodes_in_group("PlusButtons"):
		button.set_disabled(true)

Like I said, it works in its own instance without any troubles and outside of CanvasLayer.

Happyman | 2021-12-13 15:59

Hard to say. CanvasLayer should have nothing to do with this. Try adding the CanvasLayer as a root of the standalone scene – if that breaks it, it may be an engine bug.

Some pointers:

  • I think a good practice is to initialize all the children with onready, this is usually cleaner and will trigger warnings if nodes get moved around.
  • Just so you know, you can use get_tree().call_group("PlusButtons", "set_disabled", false) instead of using for loops.
  • Also, it may be just the code preview, but in your second snippet the if and else are misaligned.

bloqm | 2021-12-14 14:38

It seems like it’s fixed now. There was another copy of the character scene in my player scene. After deleting it, everything works.
I guess it’s a path of a beginner :slight_smile:
Thanks once again.

Happyman | 2021-12-14 20:10