From 890ee12459492bc4bdea36241bcd4c2a653c5f61 Mon Sep 17 00:00:00 2001 From: Shital Shah Date: Fri, 2 Mar 2018 21:33:47 +0530 Subject: [PATCH] Minor refactoring for PR https://github.com/Microsoft/AirSim/pull/850 --- .../Plugins/AirSim/Source/AirBlueprintLib.cpp | 45 ++++++++++ .../Plugins/AirSim/Source/AirBlueprintLib.h | 5 ++ .../Plugins/AirSim/Source/CameraDirector.cpp | 84 +++++++++---------- Unreal/Plugins/AirSim/Source/PIPCamera.cpp | 3 - .../Plugins/AirSim/Source/SimHUD/SimHUD.cpp | 3 + 5 files changed, 95 insertions(+), 45 deletions(-) diff --git a/Unreal/Plugins/AirSim/Source/AirBlueprintLib.cpp b/Unreal/Plugins/AirSim/Source/AirBlueprintLib.cpp index 1a12fecf45..2e0fb244b2 100644 --- a/Unreal/Plugins/AirSim/Source/AirBlueprintLib.cpp +++ b/Unreal/Plugins/AirSim/Source/AirBlueprintLib.cpp @@ -17,6 +17,7 @@ #include "Kismet/KismetStringLibrary.h" #include "MessageDialog.h" #include "Engine/LocalPlayer.h" +#include "Slate/SceneViewport.h" #include "Engine/Engine.h" /* @@ -28,6 +29,7 @@ parameters -> camel_case bool UAirBlueprintLib::log_messages_hidden = false; +uint32_t UAirBlueprintLib::FlushOnDrawCount = 0; msr::airlib::AirSimSettings::SegmentationSettings::MeshNamingMethodType UAirBlueprintLib::mesh_naming_method = msr::airlib::AirSimSettings::SegmentationSettings::MeshNamingMethodType::OwnerName; @@ -58,6 +60,49 @@ void UAirBlueprintLib::enableWorldRendering(AActor* context, bool enable) } } +void UAirBlueprintLib::enableViewportRendering(AActor* context, bool enable) +{ + // Enable/disable primary viewport rendering flag + auto* viewport = context->GetWorld()->GetGameViewport(); + if (!viewport) + return; + + if (!enable) { + // This disables rendering of the main viewport in the same way as the + // console command "show rendering" would do. + viewport->EngineShowFlags.SetRendering(false); + + // When getting an image through the API, the image is produced after the render + // thread has finished rendering the current and the subsequent frame. This means + // that the frame rate for obtaining images through the API is only half as high as + // it could be, since only every other image is actually captured. We work around + // this by telling the viewport to flush the rendering queue at the end of each + // drawn frame so that it executes our render request at that point already. + // Do this only if the main viewport is not being rendered anyway in case there are + // any adverse performance effects during main rendering. + //HACK: FViewPort doesn't expose this field so we are doing dirty work around by maintaining count by ourselves + if (FlushOnDrawCount == 0) + viewport->GetGameViewport()->IncrementFlushOnDraw(); + } + else { + viewport->EngineShowFlags.SetRendering(true); + + //HACK: FViewPort doesn't expose this field so we are doing dirty work around by maintaining count by ourselves + if (FlushOnDrawCount > 0) + viewport->GetGameViewport()->DecrementFlushOnDraw(); + } +} + +void UAirBlueprintLib::OnBeginPlay() +{ + FlushOnDrawCount = 0; +} + +void UAirBlueprintLib::OnEndPlay() +{ + //nothing to do for now +} + void UAirBlueprintLib::LogMessage(const FString &prefix, const FString &suffix, LogDebugLevel level, float persist_sec) { if (log_messages_hidden) diff --git a/Unreal/Plugins/AirSim/Source/AirBlueprintLib.h b/Unreal/Plugins/AirSim/Source/AirBlueprintLib.h index 88363806cc..070fd1991b 100644 --- a/Unreal/Plugins/AirSim/Source/AirBlueprintLib.h +++ b/Unreal/Plugins/AirSim/Source/AirBlueprintLib.h @@ -34,6 +34,8 @@ class UAirBlueprintLib : public UBlueprintFunctionLibrary GENERATED_BODY() public: + static void OnBeginPlay(); + static void OnEndPlay(); static void LogMessageString(const std::string &prefix, const std::string &suffix, LogDebugLevel level, float persist_sec = 60); UFUNCTION(BlueprintCallable, Category = "Utils") static void LogMessage(const FString &prefix, const FString &suffix, LogDebugLevel level, float persist_sec = 60); @@ -98,6 +100,7 @@ class UAirBlueprintLib : public UBlueprintFunctionLibrary } static void enableWorldRendering(AActor* context, bool enable); + static void enableViewportRendering(AActor* context, bool enable); private: template @@ -115,6 +118,8 @@ class UAirBlueprintLib : public UBlueprintFunctionLibrary private: static bool log_messages_hidden; + //FViewPort doesn't expose this field so we are doing dirty work around by maintaining count by ourselves + static uint32_t FlushOnDrawCount; static msr::airlib::AirSimSettings::SegmentationSettings::MeshNamingMethodType mesh_naming_method; }; diff --git a/Unreal/Plugins/AirSim/Source/CameraDirector.cpp b/Unreal/Plugins/AirSim/Source/CameraDirector.cpp index a56d76881c..756b87e1ef 100644 --- a/Unreal/Plugins/AirSim/Source/CameraDirector.cpp +++ b/Unreal/Plugins/AirSim/Source/CameraDirector.cpp @@ -1,6 +1,5 @@ #include "CameraDirector.h" #include "GameFramework/PlayerController.h" -#include "Runtime/Engine/Public/Slate/SceneViewport.h" #include "AirBlueprintLib.h" ACameraDirector::ACameraDirector() @@ -140,52 +139,53 @@ void ACameraDirector::attachSpringArm(bool attach) void ACameraDirector::setMode(ECameraDirectorMode mode) { - //if prev mode was spring arm but new mode isn't then detach spring arm - if (mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE && - mode != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE) - { - attachSpringArm(false); - } + { //first remove any settings done by previous mode + + //detach spring arm + if (mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE && + mode != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE) + { + attachSpringArm(false); + } - // Enable/disable primary viewport rendering flag - if (mode_ != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY && - mode == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY) - { - // This disables rendering of the main viewport in the same way as the - // console command "show rendering" would do. - GetWorld()->GetGameViewport()->EngineShowFlags.SetRendering(false); - - // When getting an image through the API, the image is produced after the render - // thread has finished rendering the current and the subsequent frame. This means - // that the frame rate for obtaining images through the API is only half as high as - // it could be, since only every other image is actually captured. We work around - // this by telling the viewport to flush the rendering queue at the end of each - // drawn frame so that it executes our render request at that point already. - // Do this only if the main viewport is not being rendered anyway in case there are - // any adverse performance effects during main rendering. - GetWorld()->GetGameViewport()->GetGameViewport()->IncrementFlushOnDraw(); - } - else if(mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY && - mode != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY) - { // Re-enable rendering - GetWorld()->GetGameViewport()->EngineShowFlags.SetRendering(true); - GetWorld()->GetGameViewport()->GetGameViewport()->DecrementFlushOnDraw(); + if (mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY && + mode != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY) + { + UAirBlueprintLib::enableViewportRendering(this, true); + } + + //Remove any existing key bindings for manual mode + if (mode != ECameraDirectorMode::CAMERA_DIRECTOR_MODE_MANUAL) { + if (external_camera_ != nullptr + && manual_pose_controller_->getActor() == external_camera_) { + + manual_pose_controller_->enableBindings(false); + } + //else someone else is bound to manual pose controller, leave it alone + } } + + { //perform any settings to enter in to this mode + + switch (mode) { + case ECameraDirectorMode::CAMERA_DIRECTOR_MODE_MANUAL: + //if new mode is manual mode then add key bindings + manual_pose_controller_->enableBindings(true); break; + case ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE: + //if we switched to spring arm mode then attach to spring arm (detachment was done earlier in method) + attachSpringArm(true); break; + case ECameraDirectorMode::CAMERA_DIRECTOR_MODE_NODISPLAY: + UAirBlueprintLib::enableViewportRendering(this, false); break; + default: + //other modes don't need special setup + break; + } - mode_ = mode; + } - //if new mode is manual mode then add key bindings - if (mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_MANUAL) - manual_pose_controller_->enableBindings(true); - //else remove any existing key bindings for manual mode - else if (external_camera_ != nullptr && manual_pose_controller_->getActor() == external_camera_) - manual_pose_controller_->enableBindings(false); - //else someone else is bound to manual pose controller, leave it alone - - //if we switched to spring arm mode then attach to spring arm (detachment was done earlier in method) - if (mode_ == ECameraDirectorMode::CAMERA_DIRECTOR_MODE_SPRINGARM_CHASE) - attachSpringArm(true); + //make switch official + mode_ = mode; } void ACameraDirector::setupInputBindings() diff --git a/Unreal/Plugins/AirSim/Source/PIPCamera.cpp b/Unreal/Plugins/AirSim/Source/PIPCamera.cpp index d5bdb92566..861344010f 100644 --- a/Unreal/Plugins/AirSim/Source/PIPCamera.cpp +++ b/Unreal/Plugins/AirSim/Source/PIPCamera.cpp @@ -135,9 +135,6 @@ void APIPCamera::setImageTypeSettings(int image_type, const APIPCamera::CaptureS setNoiseMaterial(image_type, camera_, camera_->PostProcessSettings, noise_setting); } - - - } void APIPCamera::updateCaptureComponentSetting(USceneCaptureComponent2D* capture, UTextureRenderTarget2D* render_target, diff --git a/Unreal/Plugins/AirSim/Source/SimHUD/SimHUD.cpp b/Unreal/Plugins/AirSim/Source/SimHUD/SimHUD.cpp index ccb89f3f91..fb57b4b523 100644 --- a/Unreal/Plugins/AirSim/Source/SimHUD/SimHUD.cpp +++ b/Unreal/Plugins/AirSim/Source/SimHUD/SimHUD.cpp @@ -21,6 +21,7 @@ void ASimHUD::BeginPlay() Super::BeginPlay(); try { + UAirBlueprintLib::OnBeginPlay(); initializeSettings(); setUnrealEngineSettings(); createSimMode(); @@ -52,6 +53,8 @@ void ASimHUD::EndPlay(const EEndPlayReason::Type EndPlayReason) simmode_ = nullptr; } + UAirBlueprintLib::OnEndPlay(); + Super::EndPlay(EndPlayReason); }