// always keep Controllers that belong to players if (bIsClient) { for (FLocalPlayerIterator It(GEngine, CurrentWorld); It; ++It) { if (It->PlayerController != nullptr) { KeepAnnotation.Set(It->PlayerController); } } } else { for(FConstControllerIterator Iterator = CurrentWorld->GetControllerIterator(); Iterator; ++Iterator) { AController* Player = Iterator->Get(); if (Player->PlayerState || Cast<APlayerController>(Player) != nullptr) { KeepAnnotation.Set(Player); } } }
// ask players what else we should keep for (FLocalPlayerIterator It(GEngine, CurrentWorld); It; ++It) { if (It->PlayerController != nullptr) { It->PlayerController->GetSeamlessTravelActorList(!bSwitchedToDefaultMap, KeepActors); } } // mark all valid actors specified for (AActor* KeepActor : KeepActors) { if (KeepActor != nullptr) { KeepAnnotation.Set(KeepActor); } }
// Rename dynamic actors in the old world's PersistentLevel that we want to keep into the new world auto ProcessActor = [this, &KeepAnnotation, &ActuallyKeptActors, NetDriver](AActor* TheActor) -> bool { const FNetworkObjectInfo* NetworkObjectInfo = NetDriver ? NetDriver->GetNetworkObjectInfo(TheActor) : nullptr;
// Keep if it's in the current level AND it isn't specifically excluded AND it was either marked as should keep OR we don't own this actor if (bIsInCurrentLevel && !bForceExcludeActor && (bManuallyMarkedKeep || bKeepNonOwnedActor)) { ActuallyKeptActors.Add(TheActor); returntrue; } else { if (bManuallyMarkedKeep) { UE_LOG(LogWorld, Warning, TEXT("Actor '%s' was indicated to be kept but exists in level '%s', not the persistent level. Actor will not travel."), *TheActor->GetName(), *TheActor->GetLevel()->GetOutermost()->GetName()); }
// otherwise, set to be deleted KeepAnnotation.Clear(TheActor); // close any channels for this actor if (NetDriver != nullptr) { NetDriver->NotifyActorLevelUnloaded(TheActor); } returnfalse; } };