Component Is Shared Between Duplicated Blueprints and the Original?

So I created a class inheriting from Actor in C++ and made a Blueprint out of it. I also created a HealthComponent and attached it to my actor blueprint. Then I duplicated the blueprint. Now my problem is, values of properties that I modify in the HealthComponent are also applied to both the original and duplicate blueprint. Why is that? And what do I to fix it without having to re-create the blueprint to prevent shared values?

Hope I made sense. Thanks in advance!

the situation you might be encountering is a result of Archetype vs Instance
an Archetype is the well “Blueprint” which is the default, and any change made to it is propagated to every instance.

an Instance is a specific manifestation of that Archetype. which will “inherit” all the values of the Archetype and use those, unless it specifically changes those values.

to bring this to your example (presuming that the values are not marked as UPROPERTY(EditDefaultsOnly)) then any change made to the default UHealthComponent would be propagated to every instance of the UHealthComponent

to fix this you can modify the values of the UHealthComponent Instance on the specific Blueprints.

so for example if the PlayerCharacter should have a max health of 200 while Enemy_Grunt should have a max health of 10 then in the Blueprint for the PlayerCharacter you would modify the HealthComponent-Max Values there to be 200, and then in the Enemy_Grunt blueprint you would modify the HealthComponent->Max to be 10

this can also be done in C++ as well by giving say your AMyCharacter a TObjectPtr<UHealthComponent> HealthComp then do similar in like an AMyEnemyBase (this might just inherit from APawn and give it a similar TObjectPtr<UHealthComponent> HealthComp by putting them in the C++ base class you ensure that every instance shall have the component where by allowing the blueprint designers maybe forget could lead to problems.
often times for a bug a crash can be easier to work through then something being forgotten, or an incorrect value.

Hi, thanks for the reply.

By instance, did you mean the instance in the Outliner? My issue currently is still just in the Details of the default blueprint, not in the Scene yet.

It doesn’t seem to happen when I manually create the blueprint one by one from the Actor class I created. I can set values for the HealthComponent differently with no issues. It happens when say the first blueprint I inherited from the class, duplicate it in the content folder and edit their values. Then whichever blueprint I edit, the properties in the HealthComponent would be the same across all of all the duplicated blueprints and vice-versa with the original (the first blueprint).

technically both…

an Instance is anytime the object is instantiated, whether that be through holding it as a raw Pointer, or any of the pointer wrapper variants in the Engine that need to be assigned through likeCreateDefaultSubObject<T> or in the Blueprint Hierarchy through the [Add+] button.

personally I prefer to only ever use the CreateDefaultSubObject<T> in C++ if I can

while any value change in the C++ class itself, or the base blueprint is a Default Value, or part of the Archetype.

for copying a component directly (unless you are copying the pointer to an instance which is a different animal, and should be avoided unless absolutely intentional), if you are doing a shallow copy (just grabbing the data values, but leaving the pointers alone) then it should be independent, and will be at runtime anyways. if you are copying the pointer to the instance then any change made to any of those values will impact the instance because they are all technically the same instance.

for things like needed components that shall be composed in every instance they should be declared in the base class and inherited. Personally I prefer for C++ classes derived from UActorComponents and USceneComponents defined in C++ to declare the members in C++ as TObjectPtr<T> and then assign them in the constructor

for example if I have a UInventoryManager:UActorComponent on my Character/Pawn, and I know that say every Character/Pawn will have one. I will give the Character/Pawn
TObjectPtr<UInventoryManager> Inventory;
as a member and then in the constructor do
Inventory = CreateDefaultSubobject<UInventoryManager>(TEXT("Inventory"));
this way the Character/Pawn will “always” have the component

for things like USceneComponents that need setup in a blueprint (because they need like meshes) I would follow a similar pattern, but then not assign Meshes, or make a setup to attach a child Actor.

for Blueprints then I would create a BaseBlueprint, and in that give all of the Components that shall always be there. Then derive from that BaseBlueprint.