Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Local to Scene doesn't work when inside exported arrays #85614

Closed
nanodeath opened this issue Dec 1, 2023 · 3 comments · Fixed by #71578
Closed

Local to Scene doesn't work when inside exported arrays #85614

nanodeath opened this issue Dec 1, 2023 · 3 comments · Fixed by #71578
Labels

Comments

@nanodeath
Copy link
Contributor

Godot version

v4.2.stable.official [46dc277]

System information

Godot v4.2.stable - Windows 10.0.19045 - Vulkan (Mobile) - dedicated NVIDIA GeForce GTX 1050 Ti with Max-Q Design (NVIDIA; 31.0.15.4617) - Intel(R) Core(TM) i7-8750H CPU @ 2.20GHz (12 Threads)

Issue description

If I create a custom resource that has some runtime-mutable state (that is, the game modifies the resource during gameplay), and then store that resource in an Array used by multiple subscenes in my main scene, the mutable state ends up shared, even if Local to Scene is checked. If the resource is top-level instead of inside an Array, it works as expected (unshared).

Unexpected sharing of state between instances:

20231201071318.mp4

What I'm looking for:

  1. Is this a bug, or is this by design?
  2. If it's by design...should it be by design? I think we know this area's a bit confusing already Resource's Local to Scene is counter-intuitive and should be improved or removed godot-proposals#1848
  3. If it's not a bug and it's definitely by design, can we document this behavior somewhere? Local to Scene isn't even mentioned in the Resources tutorial, but some kind of best practice callout should probably be added here. Either "be careful when using Resources in Arrays" or "avoid mutable state inside Resources"?

Steps to reproduce

  1. Create a custom resource. It should have at least one field modified by the game at runtime, e.g. a checkbox to indicate whether the animation it represents has completed.
  2. Store this resource in an Array on a scene.
  3. Write a script and attach to the scene that uses the resource.
  4. Instantiate this scene multiple times and add it to the main scene.
  5. Observe that the mutated state is shared across all instances.

For the attached project, just run the main scene, then click on the first image, then the second image.

Minimal reproduction project

LocalToScene_GD.zip

I've attached a simple project where there's a stateful animation resource that's in an array shared by two instances. Because I've chosen Resource > Local to Scene for the AnimNames resource (and tried Make Unique on that resource for good measure), I expect the AnimNames resource to be fully independent between the two images. But it's actually shared.

What I expect the behavior to be when clicking on the images:

20231201071248.mp4

What actually happens when clicking on different instances. The jerking behavior is because it's unexpectedly playing the wrong animation.

20231201071318.mp4
@nanodeath
Copy link
Contributor Author

nanodeath commented Dec 1, 2023

# my_area.gd

# ...

func _ready():
	input_event.connect(clicked)
	animation_player.animation_finished.connect(anim_done)
+	anim_names = anim_names.duplicate()
+	anim_names.assign(anim_names.map(func(anim_name): return anim_name.duplicate()))

This change makes the Resources work as I would expect.

@RedMser
Copy link
Contributor

RedMser commented Dec 1, 2023

This is indeed a bug. Duplicate of #71243

@nanodeath
Copy link
Contributor Author

Does indeed seem like a dupe. Thanks @RedMser.

@nanodeath nanodeath closed this as not planned Won't fix, can't repro, duplicate, stale Dec 1, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants