Skip to content

Commit

Permalink
Rewrote the thumbnail system. It saves only when the prefab is saved.…
Browse files Browse the repository at this point in the history
… Disabled custom realtime thumb renderere
  • Loading branch information
coderespawn committed Feb 4, 2020
1 parent b7f707e commit 53678b5
Show file tree
Hide file tree
Showing 12 changed files with 134 additions and 50 deletions.
1 change: 1 addition & 0 deletions Source/PrefabricatorEditor/PrefabricatorEditor.Build.cs
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ public PrefabricatorEditor(ReadOnlyTargetRules Target) : base(Target)
"Kismet",
"PlacementMode",
"EditorWidgets",
"RHI"
}
);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,13 +62,6 @@ class FPrefabricatorEditorModule : public IPrefabricatorEditorModule

// Override the prefabricator service with the editor version, so the runtime module can access it
FPrefabricatorService::Set(MakeShareable(new FPrefabricatorEditorService));

const UPrefabricatorSettings* PS = GetDefault<UPrefabricatorSettings>();
if (PS->bShowAssetThumbnails)
{
// Setup the thumbnail renderer for the prefab asset
UThumbnailManager::Get().RegisterCustomRenderer(UPrefabricatorAsset::StaticClass(), UPrefabricatorAssetThumbnailRenderer::StaticClass());
}
}

virtual void ShutdownModule() override {
Expand Down
36 changes: 1 addition & 35 deletions Source/PrefabricatorEditor/Private/UI/PrefabCustomization.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -146,22 +146,6 @@ void FPrefabActorCustomization::CustomizeDetails(IDetailLayoutBuilder& DetailBui
.Text(LOCTEXT("PrefabCollectionCommand_RecreateCollection", "Reload Prefab"))
.OnClicked(FOnClicked::CreateStatic(&FPrefabActorCustomization::HandleLoadFromAsset, &DetailBuilder))
];

}


const UPrefabricatorSettings* PS = GetDefault<UPrefabricatorSettings>();
if (!PS->bShowAssetThumbnails)
{
// Add an option to save the viewport image as a thumbnail for the asset
IDetailCategoryBuilder& Category = DetailBuilder.EditCategory("Prefab Collection Actions", FText::GetEmpty(), ECategoryPriority::Important);
Category.AddCustomRow(LOCTEXT("PrefabThumb_Filter", "thumbnail thumb"))
.WholeRowContent()
[
SNew(SButton)
.Text(LOCTEXT("PrefabThumbCommand_SaveThumbnail", "Update Thumbnail"))
.OnClicked(FOnClicked::CreateStatic(&FPrefabActorCustomization::UpdateThumbFromViewport, &DetailBuilder))
];
}
}

Expand Down Expand Up @@ -200,8 +184,7 @@ FReply FPrefabActorCustomization::HandleSaveToNewAsset(IDetailLayoutBuilder* Det
TArray<AActor*> Children;
PrefabActor->GetAttachedActors(Children);

if(Children.Num() > 0)
{
if(Children.Num() > 0) {
FPrefabTools::UnlinkAndDestroyPrefabActor(PrefabActor);
FPrefabTools::CreatePrefabFromActors(Children);
}
Expand Down Expand Up @@ -252,23 +235,6 @@ FReply FPrefabActorCustomization::UnlinkPrefab(IDetailLayoutBuilder* DetailBuild
return FReply::Handled();
}

FReply FPrefabActorCustomization::UpdateThumbFromViewport(IDetailLayoutBuilder* DetailBuilder)
{
if (GEditor) {
TArray<APrefabActor*> PrefabActors = GetDetailObject<APrefabActor>(DetailBuilder);
for (APrefabActor* PrefabActor : PrefabActors) {
if (PrefabActor) {
UPrefabricatorAsset* Asset = PrefabActor->GetPrefabAsset();
IContentBrowserSingleton& ContentBrowser = FModuleManager::LoadModuleChecked<FContentBrowserModule>("ContentBrowser").Get();
TArray<FAssetData> AssetList;
AssetList.Add(FAssetData(Asset));
ContentBrowser.CaptureThumbnailFromViewport(GEditor->GetActiveViewport(), AssetList);
}
}
}
return FReply::Handled();
}

///////////////////////////////// FPrefabRandomizerCustomization /////////////////////////////////

void FPrefabRandomizerCustomization::CustomizeDetails(IDetailLayoutBuilder& DetailBuilder)
Expand Down
112 changes: 112 additions & 0 deletions Source/PrefabricatorEditor/Private/Utils/PrefabEditorTools.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,15 @@
#include "EditorViewportClient.h"
#include "EngineUtils.h"
#include "Framework/Notifications/NotificationManager.h"
#include "ObjectTools.h"
#include "AssetData.h"
#include "Asset/PrefabricatorAsset.h"
#include "Kismet/KismetRenderingLibrary.h"
#include "Engine/TextureRenderTarget2D.h"
#include "Asset/Thumbnail/PrefabricatorAssetThumbnailScene.h"
#include "EngineModule.h"
#include "LegacyScreenPercentageDriver.h"
#include "Engine/Canvas.h"

void FPrefabEditorTools::ReloadPrefabsInLevel(UWorld* World, UPrefabricatorAsset* InAsset)
{
Expand Down Expand Up @@ -59,3 +68,106 @@ void FPrefabEditorTools::SwitchLevelViewportToRealtimeMode()
}
}

void FPrefabEditorTools::CapturePrefabAssetThumbnail(UPrefabricatorAsset* InAsset)
{
int32 ThumbSize = 512;

TArray<FColor> Bitmap;
{
FPrefabricatorAssetThumbnailScene ThumbnailScene;
UWorld* World = ThumbnailScene.GetWorld();
ThumbnailScene.SetPrefabAsset(InAsset);

UTextureRenderTarget2D* RTT = UKismetRenderingLibrary::CreateRenderTarget2D(World, ThumbSize, ThumbSize, RTF_RGBA32f);
FTextureRenderTargetResource* RTTResource = RTT->GameThread_GetRenderTargetResource();

FSceneViewFamilyContext ViewFamily(FSceneViewFamily::ConstructionValues(RTTResource, ThumbnailScene.GetScene(), FEngineShowFlags(ESFIM_Game))
.SetWorldTimes(FApp::GetCurrentTime() - GStartTime, FApp::GetDeltaTime(), FApp::GetCurrentTime() - GStartTime));

ViewFamily.EngineShowFlags.DisableAdvancedFeatures();
ViewFamily.EngineShowFlags.MotionBlur = 0;
ViewFamily.EngineShowFlags.LOD = 0;

ThumbnailScene.GetView(&ViewFamily, 0, 0, ThumbSize, ThumbSize);

ViewFamily.EngineShowFlags.ScreenPercentage = false;
ViewFamily.SetScreenPercentageInterface(new FLegacyScreenPercentageDriver(
ViewFamily, /* GlobalResolutionFraction = */ 1.0f, /* AllowPostProcessSettingsScreenPercentage = */ false));

FVector2D CanvasSize;
UCanvas* Canvas = nullptr;
FDrawToRenderTargetContext RenderContext;
UKismetRenderingLibrary::BeginDrawCanvasToRenderTarget(World, RTT, Canvas, CanvasSize, RenderContext);

GetRendererModule().BeginRenderingViewFamily(Canvas->Canvas, &ViewFamily);
Canvas->Canvas->Flush_GameThread(true);

ENQUEUE_RENDER_COMMAND(UpdateThumbnailRTCommand)(
[RTTResource](FRHICommandListImmediate& RHICmdList)
{
// Copy (resolve) the rendered thumbnail from the render target to its texture
RHICmdList.CopyToResolveTarget(
RTTResource->GetRenderTargetTexture(), // Source texture
RTTResource->TextureRHI, // Dest texture
FResolveParams() ); // Resolve parameters
});


RTTResource->ReadPixels(Bitmap);
check(Bitmap.Num() == ThumbSize * ThumbSize);

UKismetRenderingLibrary::EndDrawCanvasToRenderTarget(World, RenderContext);
UKismetRenderingLibrary::ReleaseRenderTarget2D(RTT);
}
/*
Bitmap.AddUninitialized(ThumbSize * ThumbSize);
for (int i = 0; i < Bitmap.Num(); i++) {
Bitmap[i] = FColor::Blue;
}
*/

//setup actual thumbnail
FObjectThumbnail TempThumbnail;
TempThumbnail.SetImageSize(ThumbSize, ThumbSize);
TArray<uint8>& ThumbnailByteArray = TempThumbnail.AccessImageData();

// Copy scaled image into destination thumb
int32 MemorySize = ThumbSize * ThumbSize * sizeof(FColor);
ThumbnailByteArray.AddUninitialized(MemorySize);
FMemory::Memcpy(&(ThumbnailByteArray[0]), &(Bitmap[0]), MemorySize);

FAssetToolsModule& AssetToolsModule = FModuleManager::LoadModuleChecked<FAssetToolsModule>("AssetTools");

//check if each asset should receive the new thumb nail
{
const FAssetData CurrentAsset = FAssetData(InAsset);

//assign the thumbnail and dirty
const FString ObjectFullName = CurrentAsset.GetFullName();
const FString PackageName = CurrentAsset.PackageName.ToString();

UPackage* AssetPackage = FindObject<UPackage>(NULL, *PackageName);
if (ensure(AssetPackage))
{
FObjectThumbnail* NewThumbnail = ThumbnailTools::CacheThumbnail(ObjectFullName, &TempThumbnail, AssetPackage);
if (ensure(NewThumbnail))
{
//we need to indicate that the package needs to be re-saved
AssetPackage->MarkPackageDirty();

// Let the content browser know that we've changed the thumbnail
NewThumbnail->MarkAsDirty();

// Signal that the asset was changed if it is loaded so thumbnail pools will update
if (CurrentAsset.IsAssetLoaded())
{
CurrentAsset.GetAsset()->PostEditChange();
}

//Set that thumbnail as a valid custom thumbnail so it'll be saved out
NewThumbnail->SetCreatedAfterCustomThumbsEnabled();
}
}
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -150,3 +150,9 @@ void FPrefabricatorEditorService::RunGC()
CollectGarbage(GARBAGE_COLLECTION_KEEPFLAGS);
}

void FPrefabricatorEditorService::CaptureThumb(UPrefabricatorAsset* PrefabAsset)
{
// Save the thumbnail
FPrefabEditorTools::CapturePrefabAssetThumbnail(PrefabAsset);
}

1 change: 0 additions & 1 deletion Source/PrefabricatorEditor/Public/UI/PrefabCustomization.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ class PREFABRICATOREDITOR_API FPrefabActorCustomization : public IDetailCustomiz
static FReply HandleLoadFromAsset(IDetailLayoutBuilder* DetailBuilder);
static FReply RandomizePrefabCollection(IDetailLayoutBuilder* DetailBuilder);
static FReply UnlinkPrefab(IDetailLayoutBuilder* DetailBuilder);
static FReply UpdateThumbFromViewport(IDetailLayoutBuilder* DetailBuilder);
};

class PREFABRICATOREDITOR_API FPrefabRandomizerCustomization : public IDetailCustomization {
Expand Down
2 changes: 2 additions & 0 deletions Source/PrefabricatorEditor/Public/Utils/PrefabEditorTools.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ class PREFABRICATOREDITOR_API FPrefabEditorTools {

static void SwitchLevelViewportToRealtimeMode();

static void CapturePrefabAssetThumbnail(UPrefabricatorAsset* InAsset);

template<typename T>
static T* CreateAssetOnContentBrowser(const FString& InAssetName, bool bSyncBrowserToAsset)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,5 +17,6 @@ class PREFABRICATOREDITOR_API FPrefabricatorEditorService : public IPrefabricato
virtual void BeginTransaction(const FText& Description) override;
virtual void EndTransaction() override;
virtual void RunGC() override;
virtual void CaptureThumb(UPrefabricatorAsset* PrefabAsset) override;
};

12 changes: 9 additions & 3 deletions Source/PrefabricatorRuntime/Private/Prefab/PrefabTools.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -134,18 +134,18 @@ namespace {
}

}
void FPrefabTools::CreatePrefabFromActors(const TArray<AActor*>& InActors)
APrefabActor* FPrefabTools::CreatePrefabFromActors(const TArray<AActor*>& InActors)
{
TArray<AActor*> Actors;
SanitizePrefabActorsForCreation(InActors, Actors);

if (Actors.Num() == 0) {
return;
return nullptr;
}

UPrefabricatorAsset* PrefabAsset = CreatePrefabAsset();
if (!PrefabAsset) {
return;
return nullptr;
}

TSharedPtr<IPrefabricatorService> Service = FPrefabricatorService::Get();
Expand Down Expand Up @@ -176,6 +176,7 @@ void FPrefabTools::CreatePrefabFromActors(const TArray<AActor*>& InActors)

SelectPrefabActor(PrefabActor);

return PrefabActor;
}

void FPrefabTools::AssignAssetUserData(AActor* InActor, const FGuid& InItemID, APrefabActor* Prefab)
Expand Down Expand Up @@ -254,6 +255,11 @@ void FPrefabTools::SaveStateToPrefabAsset(APrefabActor* PrefabActor)
PrefabAsset->LastUpdateID = FGuid::NewGuid();
PrefabActor->LastUpdateID = PrefabAsset->LastUpdateID;
PrefabAsset->Modify();

TSharedPtr<IPrefabricatorService> Service = FPrefabricatorService::Get();
if (Service.IsValid()) {
Service->CaptureThumb(PrefabAsset);
}
}

namespace {
Expand Down
2 changes: 1 addition & 1 deletion Source/PrefabricatorRuntime/Public/Prefab/PrefabTools.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ class PREFABRICATORRUNTIME_API FPrefabTools {
public:
static bool CanCreatePrefab();
static void CreatePrefab();
static void CreatePrefabFromActors(const TArray<AActor*>& Actors);
static APrefabActor* CreatePrefabFromActors(const TArray<AActor*>& Actors);
static void AssignAssetUserData(AActor* InActor, const FGuid& InItemID, APrefabActor* Prefab);

static void SaveStateToPrefabAsset(APrefabActor* PrefabActor);
Expand Down
3 changes: 0 additions & 3 deletions Source/PrefabricatorRuntime/Public/PrefabricatorSettings.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,6 @@ class PREFABRICATORRUNTIME_API UPrefabricatorSettings : public UDeveloperSetting
UPROPERTY(EditAnywhere, BlueprintReadOnly, config, Category = "Settings")
bool bAllowDynamicUpdate = true;

UPROPERTY(EditAnywhere, BlueprintReadOnly, config, Category = "Settings", meta = (ConfigRestartRequired = true))
bool bShowAssetThumbnails = true;

public:
UPrefabricatorSettings();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ class PREFABRICATORRUNTIME_API IPrefabricatorService {
virtual void BeginTransaction(const FText& Description) {}
virtual void EndTransaction() {}
virtual void RunGC() {}
virtual void CaptureThumb(UPrefabricatorAsset* PrefabAsset) {}
};

class PREFABRICATORRUNTIME_API FPrefabricatorRuntimeService : public IPrefabricatorService {
Expand Down

0 comments on commit 53678b5

Please sign in to comment.