Ownership
Ownership Modes
EFusionObjectOwnerFlags has five values, each one a different rule for who can own the object and what happens to it when the owner disconnects. Pick the mode at design time on the UFusionActorComponent — it is the most consequential property on the component.
| Mode | Per-value behavior (from the enum comments in FusionActorComponent.h) |
|---|---|
Transaction |
Used for most objects. Take-and-release transaction semantics: the current owner releases via SetWantsOwner(false), then another client can claim via SetWantsOwner(true). |
PlayerAttached |
Same transaction semantics as Transaction, with one extra rule: if a player is the current owner when they leave the room, the object is destroyed. |
Dynamic |
Allows dynamic overriding of ownership on every client. Suited to objects that quickly change ownership (e.g. physics objects). |
MasterClient |
Object is always owned by whoever is the current Master Client. If a new Master Client is elected, ownership automatically switches. |
GameGlobal |
Object lifetime and ownership must be handled explicitly by application code. |
The default mapping: PlayerAttached for player avatars and per-player inventory, Transaction for shared pickups the player explicitly picks up and drops, Dynamic for physics objects and projectiles that change ownership frequently, MasterClient for singletons and room-wide systems, GameGlobal only when the project needs to manage lifetime itself.
Setting and Changing Ownership
The Ownership UPROPERTY on UFusionActorComponent is read once, when the actor is attached as a Fusion source. Set it in the C++ constructor or the BP defaults — it is not designed to flip at runtime.
C++
AInteractablePickup::AInteractablePickup()
{
FusionActorComponent = CreateDefaultSubobject<UFusionActorComponent>(TEXT("Fusion"));
FusionActorComponent->Ownership = EFusionObjectOwnerFlags::Transaction;
}
Changing the Ownership UPROPERTY after the actor is attached is not the normal transfer path and is not supported as a runtime API. Runtime ownership transfers go through SetWantsOwner instead — covered below.
Auto Dynamic Ownership Range
AutoDynamicOwnershipRange (in centimetres) on UFusionActorComponent is an optional helper that automates SetWantsOwner calls based on distance. It is a separate feature from the Dynamic ownership mode — the two often pair, but neither requires the other.
When the value is non-zero, the component enables its tick (SetComponentTickEnabled(AutoDynamicOwnershipRange > 0) in BeginPlay). Each tick, the component measures the distance from the actor to the local player pawn (UGameplayStatics::GetPlayerPawn(this, 0)) and calls SetWantsOwner(GetOwner(), WantsOwner) with WantsOwner = distance < AutoDynamicOwnershipRange. Source: FusionActorComponent.cpp L94 + L117-125.
C++
FusionActorComponent->Ownership = EFusionObjectOwnerFlags::Dynamic;
FusionActorComponent->AutoDynamicOwnershipRange = 500.0; // cm
The pairing with Dynamic is conventional but not required — the helper simply calls SetWantsOwner on whatever ownership mode the actor uses, and the mode itself decides what (if anything) happens. A value of 0 disables the helper entirely, leaving ownership transfer under explicit gameplay control via direct SetWantsOwner calls.
Requesting Ownership
UFusionOnlineSubsystem::SetWantsOwner(Actor, bWantsOwner) is the runtime entry point. Call it with bWantsOwner = true to claim ownership of an actor, or false to release. The call is BP-callable and resolves through the ownership-mode rules — a Transaction actor responds to the claim, a PlayerAttached actor does not.
C++
OnlineSubsystem->SetWantsOwner(Actor, true); // claim
OnlineSubsystem->SetWantsOwner(Actor, false); // release
The BP-pure inspectors on UFusionOnlineSubsystem answer the runtime "who owns this and can I write to it?" question: HasOwner(Actor), GetOwner(Actor), GetResolvedOwner(Actor), IsOwner(Actor), and CanModify(Actor). Use IsOwner and CanModify as the predicates for gating writes to replicated state.
Owner Disconnect Behavior
PlayerAttached objects are destroyed when the owning player leaves the room. This is per the enum comment in FusionActorComponent.h: "Same as transaction but if a player is currently the owner of the object when he leaves, the object is destroyed." Player avatars, player-attached inventory, and any other PlayerAttached actors do not survive a disconnect. If a value must persist across a rejoin, store it on APlayerState (which itself uses PlayerAttached ownership but is governed by Unreal's InactivePlayerArray flow — see Game Classes) or on a MasterClient-owned actor.
MasterClient objects auto-transfer to the new Master Client on master change, without application code. The next section covers the auto-promotion path in detail.
Transaction and Dynamic modes do not have explicit on-disconnect behavior documented in the enum comments; behavior in those cases is the responsibility of the application using transaction semantics on top of SetWantsOwner. GameGlobal lifetime is entirely application-controlled.
Master Client Mode and Auto-Promotion
EFusionObjectOwnerFlags::MasterClient ownership binds the object's owner to whichever player is the current Master Client. The resolved owner is recomputed on every master change, so IsOwner(Actor) and IsMasterClient() always agree for these actors.
When the current Master Client leaves the room, Photon promotes a new master automatically. Every MasterClient-owned object re-targets the new master in the same tick, and the OnOwnerChanged event fires on each affected UFusionActorComponent. No application code is required.
Do not pair SetWantsOwner with MasterClient-owned objects. The ownership rule for MasterClient is "whoever is master right now", not "whoever asked" — claim requests do not change the resolved owner. If the project needs ownership that any client can request and release, use Transaction or Dynamic instead.
Ownership and HasAuthority
The plugin does not override AActor::HasAuthority(). The predicate returns whatever stock UE would return based on ENetMode and ROLE_Authority. On a Fusion-owned actor ROLE_Authority is local on the owning peer, so HasAuthority() ends up reading true on the owner and false on remotes — but this is incidental behavior, not a contract Fusion makes.
Prefer UFusionOnlineSubsystem::IsOwner(Actor) and CanModify(Actor) over HasAuthority() for gating writes to Fusion-replicated state. They query the resolved Fusion owner directly and survive future changes to how UE roles are computed. The list of stock-UE replication mechanisms Fusion does and does not honor lives in Compatibility with Built-in Netcode.
Ownership-Change Events
OnOwnerChanged is a BlueprintAssignable multicast on UFusionActorComponent. It fires whenever the resolved owner of the actor changes, including the local-to-remote and remote-to-local transitions. The new owner's player id is passed as an event parameter, so handlers can update HUDs, ownership indicators, or AI possession.
OnOwnerWasGiven is the narrower companion event. It fires only when the local client has just become the owner — the right hook for "I just took authority, start driving this actor". Use it for spinning up input handling, AI behaviour, or any per-tick logic that only the owner should run.
C++
void AMyActor::BeginPlay()
{
Super::BeginPlay();
FusionActorComponent->OnOwnerChanged.AddDynamic(this, &AMyActor::HandleOwnerChanged);
FusionActorComponent->OnOwnerWasGiven.AddDynamic(this, &AMyActor::HandleBecameOwner);
}
Back to top