bool UDemoNetDriver::InitConnect( FNetworkNotify* InNotify, const FURL& ConnectURL, FString& Error ) { // handle default initialization if ( !InitBase( true, InNotify, ConnectURL, false, Error ) ) { return false; } // open the pre-recorded demo file FileAr = IFileManager::Get().CreateFileReader( *DemoFilename ); if ( !FileAr ) { Error = FString::Printf( TEXT( "Couldn't open demo file %s for reading" ), *DemoFilename ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); return false; } // Playback, local machine is a client, and the demo stream acts "as if" it's the server. ServerConnection = ConstructObject<UNetConnection>( UDemoNetConnection::StaticClass() ); ServerConnection->InitConnection( this, USOCK_Pending, ConnectURL, 1000000 ); #if 1 // Create fake control channel ServerConnection->CreateChannel( CHTYPE_Control, 1 ); #endif // use the same byte format regardless of platform so that the demos are cross platform // DEMO_FIXME: This is messing up for some reason, investigate //FileAr->SetByteSwapping( true ); int32 EngineVersion = 0; (*FileAr) << EngineVersion; (*FileAr) << PlaybackTotalFrames; UE_LOG( LogDemo, Log, TEXT( "Starting demo playback with demo. Filename: %s, Frames: %i, Version %i" ), *DemoFilename, PlaybackTotalFrames, EngineVersion ); #if 1 // Bypass UDemoPendingNetLevel FString LevelName; (*FileAr) << LevelName; FString LoadMapError; FURL DemoURL; DemoURL.Map = LevelName; FWorldContext * WorldContext = GEngine->GetWorldContextFromWorld( World ); if ( WorldContext == NULL ) { Error = FString::Printf( TEXT( "No world context" ), *DemoFilename ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); return false; } World->DemoNetDriver = NULL; SetWorld( NULL ); UDemoPendingNetGame * NewPendingNetGame = new UDemoPendingNetGame( FPostConstructInitializeProperties() ); NewPendingNetGame->DemoNetDriver = this; WorldContext->PendingNetGame = NewPendingNetGame; if ( !GEngine->LoadMap( *WorldContext, DemoURL, NewPendingNetGame, LoadMapError ) ) { Error = LoadMapError; UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: LoadMap failed: failed: %s" ), *Error ); return false; } SetWorld( WorldContext->World() ); WorldContext->World()->DemoNetDriver = this; WorldContext->PendingNetGame = NULL; #endif int32 NumStreamingLevels = 0; (*FileAr) << NumStreamingLevels; for ( int32 i = 0; i < NumStreamingLevels; ++i ) { ULevelStreamingKismet* StreamingLevel = static_cast<ULevelStreamingKismet*>(StaticConstructObject(ULevelStreamingKismet::StaticClass(), GetWorld(), NAME_None, RF_NoFlags, NULL ) ); StreamingLevel->bShouldBeLoaded = true; StreamingLevel->bShouldBeVisible = true; StreamingLevel->bShouldBlockOnLoad = false; StreamingLevel->bInitiallyLoaded = true; StreamingLevel->bInitiallyVisible = true; FString PackageName; FString PackageNameToLoad; (*FileAr) << PackageName; (*FileAr) << PackageNameToLoad; (*FileAr) << StreamingLevel->LevelTransform; StreamingLevel->PackageNameToLoad = FName( *PackageNameToLoad ); StreamingLevel->SetWorldAssetByPackageName( FName( *PackageName ) ); GetWorld()->StreamingLevels.Add( StreamingLevel ); UE_LOG( LogDemo, Log, TEXT( " Loading streamingLevel: %s, %s" ), *PackageName, *PackageNameToLoad ); } DemoDeltaTime = 0; return true; }
bool UDemoNetDriver::InitConnect( FNetworkNotify* InNotify, const FURL& ConnectURL, FString& Error ) { if ( GetWorld() == nullptr ) { UE_LOG( LogDemo, Error, TEXT( "GetWorld() == nullptr" ) ); return false; } if ( GetWorld()->GetGameInstance() == nullptr ) { UE_LOG( LogDemo, Error, TEXT( "GetWorld()->GetGameInstance() == nullptr" ) ); return false; } UGameInstance* GameInstance = GetWorld()->GetGameInstance(); // handle default initialization if ( !InitBase( true, InNotify, ConnectURL, false, Error ) ) { GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::Generic, FString( TEXT( "InitBase FAILED" ) ) ); return false; } ResetDemoState(); // open the pre-recorded demo file FileAr = IFileManager::Get().CreateFileReader( *DemoFilename ); if ( !FileAr ) { Error = FString::Printf( TEXT( "Couldn't open demo file %s for reading" ), *DemoFilename ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::DemoNotFound, FString( EDemoPlayFailure::ToString( EDemoPlayFailure::DemoNotFound ) ) ); return false; } // Playback, local machine is a client, and the demo stream acts "as if" it's the server. ServerConnection = ConstructObject<UNetConnection>( UDemoNetConnection::StaticClass() ); ServerConnection->InitConnection( this, USOCK_Pending, ConnectURL, 1000000 ); // use the same byte format regardless of platform so that the demos are cross platform // DEMO_FIXME: This is messing up for some reason, investigate //FileAr->SetByteSwapping( true ); FNetworkDemoHeader DemoHeader; (*FileAr) << DemoHeader; // Check magic value if ( DemoHeader.Magic != NETWORK_DEMO_MAGIC ) { Error = FString( TEXT( "Demo file is corrupt" ) ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::Corrupt, Error ); return false; } // Check version if ( DemoHeader.Version != NETWORK_DEMO_VERSION ) { Error = FString( TEXT( "Demo file version is incorrect" ) ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::InvalidVersion, Error ); return false; } // Create fake control channel ServerConnection->CreateChannel( CHTYPE_Control, 1 ); DemoTotalFrames = DemoHeader.NumFrames; DemoTotalTime = DemoHeader.TotalTime; UE_LOG( LogDemo, Log, TEXT( "Starting demo playback with demo. Filename: %s, Frames: %i, Version %i" ), *DemoFilename, DemoTotalFrames, DemoHeader.Version ); // Bypass UDemoPendingNetLevel FString LoadMapError; FURL DemoURL; DemoURL.Map = DemoHeader.LevelName; FWorldContext * WorldContext = GEngine->GetWorldContextFromWorld( GetWorld() ); if ( WorldContext == NULL ) { Error = FString::Printf( TEXT( "No world context" ), *DemoFilename ); UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: %s" ), *Error ); GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::Generic, FString( TEXT( "No world context" ) ) ); return false; } GetWorld()->DemoNetDriver = NULL; SetWorld( NULL ); auto NewPendingNetGame = NewObject<UDemoPendingNetGame>(); NewPendingNetGame->DemoNetDriver = this; WorldContext->PendingNetGame = NewPendingNetGame; if ( !GEngine->LoadMap( *WorldContext, DemoURL, NewPendingNetGame, LoadMapError ) ) { Error = LoadMapError; UE_LOG( LogDemo, Error, TEXT( "UDemoNetDriver::InitConnect: LoadMap failed: failed: %s" ), *Error ); GameInstance->HandleDemoPlaybackFailure( EDemoPlayFailure::Generic, FString( TEXT( "LoadMap failed" ) ) ); return false; } SetWorld( WorldContext->World() ); WorldContext->World()->DemoNetDriver = this; WorldContext->PendingNetGame = NULL; // Remember where we are const int32 OldPos = FileAr->Tell(); // Jump to meta data FileAr->Seek( DemoHeader.MetaDataOffset ); // Read meta data for ( int32 i = 0; i < DemoHeader.NumStreamingLevels; ++i ) { ULevelStreamingKismet* StreamingLevel = static_cast<ULevelStreamingKismet*>(StaticConstructObject(ULevelStreamingKismet::StaticClass(), GetWorld(), NAME_None, RF_NoFlags, NULL ) ); StreamingLevel->bShouldBeLoaded = true; StreamingLevel->bShouldBeVisible = true; StreamingLevel->bShouldBlockOnLoad = false; StreamingLevel->bInitiallyLoaded = true; StreamingLevel->bInitiallyVisible = true; FString PackageName; FString PackageNameToLoad; (*FileAr) << PackageName; (*FileAr) << PackageNameToLoad; (*FileAr) << StreamingLevel->LevelTransform; StreamingLevel->PackageNameToLoad = FName( *PackageNameToLoad ); StreamingLevel->SetWorldAssetByPackageName( FName( *PackageName ) ); GetWorld()->StreamingLevels.Add( StreamingLevel ); UE_LOG( LogDemo, Log, TEXT( " Loading streamingLevel: %s, %s" ), *PackageName, *PackageNameToLoad ); } // Jump back to start of stream FileAr->Seek( OldPos ); // Remember where the meta data is, this is where we must stop reading the demo stream EndOfStreamOffset = DemoHeader.MetaDataOffset; return true; }
void FPhysicsManipulationEdMode::Enter() { FWorldContext* PIEWorldContext = GEditor->GetPIEWorldContext(); check(PIEWorldContext && PIEWorldContext->World()); HandleComp->RegisterComponentWithWorld(PIEWorldContext->World()); }