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

Setting new value of shared component disconnects sharing #179

Open
slimshader opened this issue Feb 24, 2023 · 3 comments
Open

Setting new value of shared component disconnects sharing #179

slimshader opened this issue Feb 24, 2023 · 3 comments
Labels
enhancement New feature or request

Comments

@slimshader
Copy link

Hi,

not sure if this a bug or I am missing something but component sharing does not work form me, I do:

var ep = w.CreateEntity();
ep.Set<EnemyPrefab>();
ep.Set(new Color(r, g, b));

at this point I see single Color component in World components

then

  var e = w.CreateEntity();
  e.SetSameAs<Color>(ep);

still seeing a singe Color component in the World.

ep.Set(new Color());

at this point there are 2 Color components in the World, the "prefab" using new one and and "instances" share the one at index 0 meaning I see no change of the color for the instances after changing the shared color of the "prefab".

(trying to emulate https://ajmmertens.medium.com/deconstructing-flecs-prefabs-d604b5ba0fcc with DefaultEcs)

@Doraku
Copy link
Owner

Doraku commented Feb 24, 2023

This is actually by design. A Set will overwrite whatever relationship was there (shared component with an entity or with a world component). The reason to do that is because when you Set a component on an entity, only this specific entity will notify the world that the value has changed. If the component was shared between multiple entities the other ones would not notify of a change which can be kinda counter-intuitive (it would be too complex to look for all entities using it). Also it would be strange for some Set to keep relationship while others (SetSameAs & SetSameAsWorld) would actually override it, so instead they all override it.

You can do the same as in this article like this: ep.Get<Color>() = new Color();, instead of a set, you retrieve the component reference and you modify it directly. Since all entity sharing this component actually use the same component reference, you have indeed changed the color of all the entities in a single call.

@slimshader
Copy link
Author

Isn't that contrary to what docs are saying:

referenceEntity.Set<int>(42);
entity.SetSameAs<int>(referenceEntity);

referenceEntity.Set<int>(1337);
// the value for entity will also be 1337
entity.Get<int>();

also, just below SetSameAs:

There are two ways to update a component value, either use the Set<T>(newValue) method or set/edit the value returned by Get<T>(). One major difference between the two is that Set<T>(newValue) will also notify internal queries that the component value has changed:

nowhere does it say that only one method is valid for shared components.

What you described is actually the functionality I was hoping for: changing the value in the source would cause WhenChanged event fire for every entity that shares the component. This way I could change the color value of the whole team.

@Doraku
Copy link
Owner

Doraku commented Feb 26, 2023

oh definitely, it was working like that but was changed afterward and I forgot to edit the readme I'll update it. I'll add some comment on the methods too to better reflect that.

Also you don't really "need" the change event, well it depends... if your system only ready the component value it doesn't need it and entity.Get<T>() = newValue; is enough, I am using just that in my game to change background objects. If you are using WhenChanged or the component is actually a key in a multi map, then yeah. I'll see if I can add that logic automatically in the NotifyChanged method.

@Doraku Doraku added the enhancement New feature or request label Feb 26, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants