diff --git a/.circleci/config.yml b/.circleci/config.yml index 477b61c..0f4f323 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -4,13 +4,6 @@ workflows: version: 2.1 build: jobs: - # - functional-test-plugin: - # context: - # - unreal-engine-ci - # matrix: - # parameters: - # unreal-engine-version: ["5.3.0"] - # version: ["full"] - build-plugin: context: - unreal-engine-ci @@ -30,65 +23,6 @@ workflows: version: 2.1 jobs: - # functional-test-plugin: - # parameters: - # unreal-engine-version: - # type: string - # version: - # type: string - # docker: - # - image: ghcr.io/epicgames/unreal-engine:dev-slim-<< parameters.unreal-engine-version >> - # auth: - # username: $GHCR_USERNAME - # password: $GHCR_PASSWORD - # steps: - # - checkout - # - run: - # name: Run scripts for the license removing - # command: bash tools/remove_license.sh BlueprintToRSTDoc << parameters.version >> - # - run: - # name: Run scripts for the code removing - # command: bash tools/remove_code.sh BlueprintToRSTDoc << parameters.unreal-engine-version >> << parameters.version >> . - # - run: - # name: "Run scripts for the release" - # command: bash tools/replace_engine_version.sh BlueprintToRSTDoc << parameters.unreal-engine-version >> - # - run: - # name: "Copy plugin" - # command: | - # mkdir ${PWD}/tests/functional_test/FunctionalTest/Plugins - # cp -r BlueprintToRSTDoc ${PWD}/tests/functional_test/FunctionalTest/Plugins - # - run: - # name: "Build project" - # command: | - # /home/ue4/UnrealEngine/Engine/Build/BatchFiles/RunUAT.sh BuildCookRun \ - # -utf8output \ - # -platform=Linux \ - # -clientconfig=Shipping \ - # -serverconfig=Shipping \ - # -project=${PWD}/tests/functional_test/FunctionalTest/FunctionalTest.uproject \ - # -noP4 \ - # -nodebuginfo \ - # -allmaps \ - # -cook \ - # -build \ - # -stage \ - # -prereqs \ - # -pak \ - # -archive \ - # -archivedirectory=/tmp/Packaged - # - run: - # name: "Functional test against Plugin" - # command: | - # /home/ue4/UnrealEngine/Engine/Binaries/Linux/UnrealEditor \ - # ${PWD}/tests/functional_test/FunctionalTest/FunctionalTest.uproject \ - # -unattended \ - # -nopause \ - # -NullRHI \ - # -ExecCmds="Automation RunTests BlueprintToRSTDoc; Quit" \ - # -testexit="Automation Test Queue Empty" \ - # -log=RunTests.log \ - # -ReportOutputPath="/tmp/FunctionalTestsReport" - build-plugin: parameters: unreal-engine-version: diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml index 4b01764..6998399 100644 --- a/.github/workflows/lint.yaml +++ b/.github/workflows/lint.yaml @@ -47,22 +47,22 @@ jobs: run: | bash tests/lint/clang-format/run.sh samples/SampleProject - # functional-test-clang-format: - # name: functional-test-clang-format - # runs-on: ubuntu-latest - # container: - # image: ubuntu:20.04 - # steps: - # - name: Checkout repo - # uses: actions/checkout@v2 - - # - name: Install clang-format - # run: | - # apt update - # apt install -y clang-format - # - name: clang-format - # run: | - # bash tests/lint/clang-format/run.sh tests/functional_test/FunctionalTest + functional-test-clang-format: + name: functional-test-clang-format + runs-on: ubuntu-latest + container: + image: ubuntu:20.04 + steps: + - name: Checkout repo + uses: actions/checkout@v2 + + - name: Install clang-format + run: | + apt update + apt install -y clang-format + - name: clang-format + run: | + bash tests/lint/clang-format/run.sh tests/functional_test/FunctionalTest markdownlint: name: markdownlint diff --git a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/BlueprintToRSTDoc.Build.cs b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/BlueprintToRSTDoc.Build.cs index 87fe74b..46f656a 100644 --- a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/BlueprintToRSTDoc.Build.cs +++ b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/BlueprintToRSTDoc.Build.cs @@ -11,8 +11,8 @@ public BlueprintToRSTDoc(ReadOnlyTargetRules Target) : base(Target) PublicIncludePaths.AddRange(new string[]{}); PrivateIncludePaths.AddRange(new string[]{"BlueprintToRSTDoc/Public"}); PublicDependencyModuleNames.AddRange(new string[]{"Core"}); - PrivateDependencyModuleNames.AddRange( - new string[]{"Projects", "CoreUObject", "Engine", "Slate", "SlateCore", "BlueprintGraph", "ToolMenus", "Kismet", "DesktopPlatform", "InputCore"}); + PrivateDependencyModuleNames.AddRange(new string[]{"Projects", "CoreUObject", "Engine", "Slate", "SlateCore", + "BlueprintGraph", "ToolMenus", "Kismet", "DesktopPlatform", "InputCore"}); DynamicallyLoadedModuleNames.AddRange(new string[]{}); } } diff --git a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BPLibrary.cpp b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BPLibrary.cpp index c1baee6..e3d8402 100644 --- a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BPLibrary.cpp +++ b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BPLibrary.cpp @@ -1,20 +1,15 @@ #include "BPLibrary.h" #include "AssetRegistry/AssetRegistryModule.h" -#include "DesktopPlatformModule.h" +#include "Common.h" #include "EdGraphSchema_K2.h" #include "Engine/UserDefinedEnum.h" #include "Engine/UserDefinedStruct.h" #include "GenericPlatform/GenericPlatformFile.h" #include "HAL/FileManagerGeneric.h" -#include "IDesktopPlatform.h" +#include "Misc/EngineVersionComparison.h" #include "Settings.h" -#define ERROR_MESSAGE_BOX(Message) \ - FPlatformMisc::MessageBoxExt(EAppMsgType::Ok, \ - *FString::Format(TEXT("Error:\n\n{0}\n\n---\n\n{1} (Line:{2})"), {Message, *FString(__FILE__), __LINE__}), \ - TEXT("BlueprintToRSTDoc")); - void ConvertBPNameToCPPName(FString& Out, const FString& Type) { Out = Type; @@ -454,24 +449,7 @@ bool ParseProperty(FRSTDocProperty& Out, FProperty* Property, bool bIsBlueprint return true; } -bool OpenOutputDirectory(FString& OutDirectory) -{ - void* ParentWindowPtr = FSlateApplication::Get().GetActiveTopLevelWindow()->GetNativeWindow()->GetOSWindowHandle(); - IDesktopPlatform* DesktopPlatform = FDesktopPlatformModule::Get(); - if (!DesktopPlatform) - { - ERROR_MESSAGE_BOX(TEXT("Failed to get DesktopPlatform.\n")); - return false; - } - if (!DesktopPlatform->OpenDirectoryDialog(ParentWindowPtr, TEXT("Save RST Documents To"), TEXT(""), OutDirectory)) - { - return false; - } - - return true; -} - -bool GetBlueprintAssets(TArray& Blueprints, const UBlueprintToRSTDocSettings& Settings) +bool GetBlueprintAssets(TArray& Blueprints, const TArray& ExcludePaths, FString& ErrorMessage) { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked(FName("AssetRegistry")); IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); @@ -484,7 +462,7 @@ bool GetBlueprintAssets(TArray& Blueprints, const UBlueprintToRSTDoc if (!AssetRegistry.GetAssets(Filter, Blueprints)) { - ERROR_MESSAGE_BOX(TEXT("Failed to get assets of 'UBlueprint'.")); + ErrorMessage = TEXT("Failed to get assets of 'UBlueprint'."); return false; } @@ -493,7 +471,7 @@ bool GetBlueprintAssets(TArray& Blueprints, const UBlueprintToRSTDoc for (auto& BP : Blueprints) { bool bFound = false; - for (auto& Path : Settings.ExcludePaths) + for (auto& Path : ExcludePaths) { if (BP.PackagePath.ToString().Find(Path) != -1) { @@ -514,7 +492,7 @@ bool GetBlueprintAssets(TArray& Blueprints, const UBlueprintToRSTDoc return true; } -bool GetStructureAssets(TArray& ScriptStructs, const UBlueprintToRSTDocSettings& Settings) +bool GetStructureAssets(TArray& ScriptStructs, const TArray& ExcludePaths, FString& ErrorMessage) { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked(FName("AssetRegistry")); IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); @@ -527,7 +505,7 @@ bool GetStructureAssets(TArray& ScriptStructs, const UBlueprintToRST if (!AssetRegistry.GetAssets(Filter, ScriptStructs)) { - ERROR_MESSAGE_BOX(TEXT("Failed to get assets of 'UUserDefinedStruct'.")); + ErrorMessage = TEXT("Failed to get assets of 'UUserDefinedStruct'."); return false; } @@ -536,7 +514,7 @@ bool GetStructureAssets(TArray& ScriptStructs, const UBlueprintToRST for (auto& S : ScriptStructs) { bool bFound = false; - for (auto& Path : Settings.ExcludePaths) + for (auto& Path : ExcludePaths) { if (S.PackagePath.ToString().Find(Path) != -1) { @@ -557,7 +535,7 @@ bool GetStructureAssets(TArray& ScriptStructs, const UBlueprintToRST return true; } -bool GetEnumerationAssets(TArray& Enums, const UBlueprintToRSTDocSettings& Settings) +bool GetEnumerationAssets(TArray& Enums, const TArray& ExcludePaths, FString& ErrorMessage) { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked(FName("AssetRegistry")); IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); @@ -570,7 +548,7 @@ bool GetEnumerationAssets(TArray& Enums, const UBlueprintToRSTDocSet if (!AssetRegistry.GetAssets(Filter, Enums)) { - ERROR_MESSAGE_BOX(TEXT("Failed to get assets of 'UEnum'.")); + ErrorMessage = TEXT("Failed to get assets of 'UEnum'."); return false; } @@ -579,7 +557,7 @@ bool GetEnumerationAssets(TArray& Enums, const UBlueprintToRSTDocSet for (auto& E : Enums) { bool bFound = false; - for (auto& Path : Settings.ExcludePaths) + for (auto& Path : ExcludePaths) { if (E.PackagePath.ToString().Find(Path) != -1) { @@ -1053,7 +1031,7 @@ void CreateRSTEnumerationDoc(FString& Doc, RSTDocIndent& Indent, const FRSTDocEn Indent.Decrement(); } -bool CreateDirectoryRecursive(const FString& BaseDirectory, const FString& Directory) +bool CreateDirectoryRecursive(const FString& BaseDirectory, const FString& Directory, FString& ErrorMessage) { IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); @@ -1067,7 +1045,7 @@ bool CreateDirectoryRecursive(const FString& BaseDirectory, const FString& Direc FullPath += D; if (!PlatformFile.CreateDirectory(*FullPath)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create directory.\n{0}"), {FullPath})); + ErrorMessage = FString::Format(TEXT("Failed to create directory.\n{0}"), {FullPath}); return false; } } @@ -1075,7 +1053,8 @@ bool CreateDirectoryRecursive(const FString& BaseDirectory, const FString& Direc return true; } -bool WriteRSTBlueprintDocs(const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList) +bool WriteRSTBlueprintDocs( + const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList, FString& ErrorMessage) { IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); @@ -1085,13 +1064,13 @@ bool WriteRSTBlueprintDocs(const TArray& Data, const FString& ClassDirectory = FString::Format(TEXT("{0}/Blueprint"), {OutputDirectory}); if (!PlatformFile.CreateDirectory(*ClassDirectory)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create directory.\n{0}"), {ClassDirectory})); + ErrorMessage = FString::Format(TEXT("Failed to create directory.\n{0}"), {ClassDirectory}); return false; } for (auto& D : Data) { - if (!CreateDirectoryRecursive(ClassDirectory, D.Path.RightChop(1))) + if (!CreateDirectoryRecursive(ClassDirectory, D.Path.RightChop(1), ErrorMessage)) { return false; } @@ -1104,7 +1083,7 @@ bool WriteRSTBlueprintDocs(const TArray& Data, const FString& if (!FFileHelper::SaveStringToFile(Contents, *FilePath)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath})); + ErrorMessage = FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath}); return false; } @@ -1115,7 +1094,8 @@ bool WriteRSTBlueprintDocs(const TArray& Data, const FString& return true; } -bool WriteRSTStructureDocs(const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList) +bool WriteRSTStructureDocs( + const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList, FString& ErrorMessage) { IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); @@ -1125,13 +1105,13 @@ bool WriteRSTStructureDocs(const TArray& Data, const FString& StructDirectory = FString::Format(TEXT("{0}/Struct"), {OutputDirectory}); if (!PlatformFile.CreateDirectory(*StructDirectory)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create directory.\n{0}"), {StructDirectory})); + ErrorMessage = FString::Format(TEXT("Failed to create directory.\n{0}"), {StructDirectory}); return false; } for (auto& D : Data) { - if (!CreateDirectoryRecursive(StructDirectory, D.Path.RightChop(1))) + if (!CreateDirectoryRecursive(StructDirectory, D.Path.RightChop(1), ErrorMessage)) { return false; } @@ -1144,7 +1124,7 @@ bool WriteRSTStructureDocs(const TArray& Data, const FString& if (!FFileHelper::SaveStringToFile(Contents, *FilePath)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath})); + ErrorMessage = FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath}); return false; } @@ -1156,7 +1136,7 @@ bool WriteRSTStructureDocs(const TArray& Data, const FString& } bool WriteRSTEnumerationDocs( - const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList) + const TArray& Data, const FString& OutputDirectory, TArray& OutputDocsList, FString& ErrorMessage) { IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); @@ -1166,13 +1146,13 @@ bool WriteRSTEnumerationDocs( EnumDirectory = FString::Format(TEXT("{0}/Enum"), {OutputDirectory}); if (!PlatformFile.CreateDirectory(*EnumDirectory)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create directory.\n{0}"), {EnumDirectory})); + ErrorMessage = FString::Format(TEXT("Failed to create directory.\n{0}"), {EnumDirectory}); return false; } for (auto& D : Data) { - if (!CreateDirectoryRecursive(EnumDirectory, D.Path.RightChop(1))) + if (!CreateDirectoryRecursive(EnumDirectory, D.Path.RightChop(1), ErrorMessage)) { return false; } @@ -1185,7 +1165,7 @@ bool WriteRSTEnumerationDocs( if (!FFileHelper::SaveStringToFile(Contents, *FilePath)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath})); + ErrorMessage = FString::Format(TEXT("Failed to save file.\n{0}"), {FilePath}); return false; } @@ -1196,7 +1176,7 @@ bool WriteRSTEnumerationDocs( return true; } -void AskCleanupOrNot(const FString& Directory) +void AskCleanupOrNot(const FString& Directory, FString& ErrorMessage) { EAppReturnType::Type ReturnType = FPlatformMisc::MessageBoxExt(EAppMsgType::YesNo, *FString::Format(TEXT("Delete incompleted output files.\n{0}"), {Directory}), TEXT("BlueprintToRSTDoc")); @@ -1205,58 +1185,59 @@ void AskCleanupOrNot(const FString& Directory) { if (!FFileManagerGeneric::Get().DeleteDirectory(*Directory, true, true)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to delete directory.\n{0}"), {Directory})); + ErrorMessage = FString::Format(TEXT("Failed to delete directory.\n{0}"), {Directory}); } } } bool WriteRSTDocs(const TArray& BlueprintData, const TArray& StructData, - const TArray& EnumData, const FString& OutputDirectory, TArray& OutputDocsList) + const TArray& EnumData, const FString& OutputDirectory, TArray& OutputDocsList, + FString& ErrorMessage) { FString RSTOutputDirectory = FString::Format(TEXT("{0}/rst"), {OutputDirectory}); IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); if (PlatformFile.DirectoryExists(*RSTOutputDirectory)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Directory is already exist.\n{0}"), {RSTOutputDirectory})); + ErrorMessage = FString::Format(TEXT("Directory is already exist.\n{0}"), {RSTOutputDirectory}); return false; } if (!PlatformFile.CreateDirectory(*RSTOutputDirectory)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create directory.\n{0}"), {RSTOutputDirectory})); + ErrorMessage = FString::Format(TEXT("Failed to create directory.\n{0}"), {RSTOutputDirectory}); return false; } - if (!WriteRSTBlueprintDocs(BlueprintData, RSTOutputDirectory, OutputDocsList)) + if (!WriteRSTBlueprintDocs(BlueprintData, RSTOutputDirectory, OutputDocsList, ErrorMessage)) { - AskCleanupOrNot(RSTOutputDirectory); + AskCleanupOrNot(RSTOutputDirectory, ErrorMessage); return false; } - if (!WriteRSTStructureDocs(StructData, RSTOutputDirectory, OutputDocsList)) + if (!WriteRSTStructureDocs(StructData, RSTOutputDirectory, OutputDocsList, ErrorMessage)) { - AskCleanupOrNot(RSTOutputDirectory); + AskCleanupOrNot(RSTOutputDirectory, ErrorMessage); return false; } - if (!WriteRSTEnumerationDocs(EnumData, RSTOutputDirectory, OutputDocsList)) + if (!WriteRSTEnumerationDocs(EnumData, RSTOutputDirectory, OutputDocsList, ErrorMessage)) { - AskCleanupOrNot(RSTOutputDirectory); + AskCleanupOrNot(RSTOutputDirectory, ErrorMessage); return false; } return true; } -bool OutputDocsListFile( - const FString& OutputDirectory, const TArray& OutputDocsList, const UBlueprintToRSTDocSettings& Settings) +bool OutputDocsListFile(const FString& OutputDirectory, const TArray& OutputDocsList, bool bOutputDocsListFullPath, + const FString& OutputDocsListFileName, FString& ErrorMessage) { FString RSTOutputDirectory = FString::Format(TEXT("{0}/rst"), {OutputDirectory}); TArray DocsList; for (auto& Doc : OutputDocsList) { - if (Settings.bOutputDocsListFullPath) + if (bOutputDocsListFullPath) { DocsList.Add(Doc); } @@ -1268,84 +1249,78 @@ bool OutputDocsListFile( } else { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("{0} does not include {1}."), {RSTOutputDirectory, Doc})); - AskCleanupOrNot(RSTOutputDirectory); + ErrorMessage = FString::Format(TEXT("{0} does not include {1}."), {RSTOutputDirectory, Doc}); + AskCleanupOrNot(RSTOutputDirectory, ErrorMessage); return false; } } } - FString FilePath = FString::Format(TEXT("{0}/{1}"), {RSTOutputDirectory, Settings.OutputDocsListFileName}); + FString FilePath = FString::Format(TEXT("{0}/{1}"), {RSTOutputDirectory, OutputDocsListFileName}); FString Contents = FString::Join(DocsList, TEXT("\n")); if (!FFileHelper::SaveStringToFile(Contents, *FilePath)) { - ERROR_MESSAGE_BOX(*FString::Format(TEXT("Failed to create file.\n{0}"), {FilePath})); - AskCleanupOrNot(RSTOutputDirectory); + ErrorMessage = FString::Format(TEXT("Failed to create file.\n{0}"), {FilePath}); + AskCleanupOrNot(RSTOutputDirectory, ErrorMessage); return false; } return true; } -void UBlueprintToRSTDocBPLibrary::GenerateRSTDoc() +void UBlueprintToRSTDocBPLibrary::GenerateRSTDoc(const FString& OutputDirectory, const TArray& ExcludePaths, + bool& bSuccess, FString& ErrorMessage, bool bOutputBlueprint, bool bOutputStructure, bool bOutputEnumeration, + bool bOutputDocsList, const FString& OutputDocsListFileName, bool bOutputDocsListFullPath) { - UBlueprintToRSTDocSettings* Settings = GetMutableDefault(); - - FString OutputDirectory = Settings->OutputDirectory; - if (Settings->bAlwaysAskOutputDirectory) - { - if (!OpenOutputDirectory(OutputDirectory)) - { - return; - } - } - TArray DocBlueprints; - if (Settings->bOutputBlueprint) + if (bOutputBlueprint) { TArray Blueprints; - if (!GetBlueprintAssets(Blueprints, *Settings)) + if (!GetBlueprintAssets(Blueprints, ExcludePaths, ErrorMessage)) { + bSuccess = false; return; } ParseBlueprints(DocBlueprints, Blueprints); } TArray DocStructures; - if (Settings->bOutputStructure) + if (bOutputStructure) { TArray ScriptStructs; - if (!GetStructureAssets(ScriptStructs, *Settings)) + if (!GetStructureAssets(ScriptStructs, ExcludePaths, ErrorMessage)) { + bSuccess = false; return; } ParseStructures(DocStructures, ScriptStructs); } TArray DocEnumerations; - if (Settings->bOutputEnumeration) + if (bOutputEnumeration) { TArray Enums; - if (!GetEnumerationAssets(Enums, *Settings)) + if (!GetEnumerationAssets(Enums, ExcludePaths, ErrorMessage)) { + bSuccess = false; return; } ParseEnumerations(DocEnumerations, Enums); } TArray OutputDocsList; - if (!WriteRSTDocs(DocBlueprints, DocStructures, DocEnumerations, OutputDirectory, OutputDocsList)) + if (!WriteRSTDocs(DocBlueprints, DocStructures, DocEnumerations, OutputDirectory, OutputDocsList, ErrorMessage)) { + bSuccess = false; return; } - if (Settings->bOutputDocsList) + if (bOutputDocsList) { - if (!OutputDocsListFile(OutputDirectory, OutputDocsList, *Settings)) + if (!OutputDocsListFile(OutputDirectory, OutputDocsList, bOutputDocsListFullPath, OutputDocsListFileName, ErrorMessage)) { + bSuccess = false; return; } } - - FPlatformMisc::MessageBoxExt(EAppMsgType::Ok, TEXT("Generated documents successfully."), TEXT("BlueprintToRSTDoc")); } \ No newline at end of file diff --git a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BlueprintToRSTDoc.cpp b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BlueprintToRSTDoc.cpp index 0550123..91cdfc4 100644 --- a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BlueprintToRSTDoc.cpp +++ b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Private/BlueprintToRSTDoc.cpp @@ -4,7 +4,10 @@ #include "BPLibrary.h" #include "Commands.h" +#include "Common.h" +#include "DesktopPlatformModule.h" #include "Framework/MultiBox/MultiBoxBuilder.h" +#include "IDesktopPlatform.h" #include "ISettingsModule.h" #include "LevelEditor.h" #include "Misc/EngineVersionComparison.h" @@ -14,6 +17,23 @@ #define LOCTEXT_NAMESPACE "BlueprintToRSTDoc" +bool OpenOutputDirectory(FString& OutDirectory) +{ + void* ParentWindowPtr = FSlateApplication::Get().GetActiveTopLevelWindow()->GetNativeWindow()->GetOSWindowHandle(); + IDesktopPlatform* DesktopPlatform = FDesktopPlatformModule::Get(); + if (!DesktopPlatform) + { + ERROR_MESSAGE_BOX(TEXT("Failed to get DesktopPlatform.\n")); + return false; + } + if (!DesktopPlatform->OpenDirectoryDialog(ParentWindowPtr, TEXT("Save RST Documents To"), TEXT(""), OutDirectory)) + { + return false; + } + + return true; +} + void FBlueprintToRSTDocModule::StartupModule() { FBlueprintToRSTDocStyle::Initialize(); @@ -69,7 +89,31 @@ void FBlueprintToRSTDocModule::ShutdownModule() void FBlueprintToRSTDocModule::CommandExecuted() { - UBlueprintToRSTDocBPLibrary::GenerateRSTDoc(); + UBlueprintToRSTDocSettings* Settings = GetMutableDefault(); + + FString OutputDirectory = Settings->OutputDirectory; + if (Settings->bAlwaysAskOutputDirectory) + { + if (!OpenOutputDirectory(OutputDirectory)) + { + return; + } + } + + bool bSuccess; + FString ErrorMessage; + UBlueprintToRSTDocBPLibrary::GenerateRSTDoc(OutputDirectory, Settings->ExcludePaths, bSuccess, ErrorMessage, + Settings->bOutputBlueprint, Settings->bOutputStructure, Settings->bOutputEnumeration, Settings->bOutputDocsList, + Settings->OutputDocsListFileName, Settings->bOutputDocsListFullPath); + + if (!bSuccess) + { + ERROR_MESSAGE_BOX(ErrorMessage); + } + else + { + FPlatformMisc::MessageBoxExt(EAppMsgType::Ok, TEXT("Generated documents successfully."), TEXT("BlueprintToRSTDoc")); + } } void FBlueprintToRSTDocModule::AddToolBarExtension(FToolBarBuilder& Builder) diff --git a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/BPLibrary.h b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/BPLibrary.h index 39ca79b..7b5b8be 100644 --- a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/BPLibrary.h +++ b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/BPLibrary.h @@ -189,5 +189,7 @@ class BLUEPRINTTORSTDOC_API UBlueprintToRSTDocBPLibrary : public UBlueprintFunct public: UFUNCTION(BluePrintCallable, exec, category = "BlueprintToRSTDoc") - static void GenerateRSTDoc(); + static void GenerateRSTDoc(const FString& OutputDirectory, const TArray& ExcludePaths, bool& bSuccess, + FString& ErrorMessage, bool bOutputBlueprint = true, bool bOutputStructure = true, bool bOutputEnumeration = true, + bool bOutputDocsList = true, const FString& OutputDocsListFileName = "DocsList.txt", bool bOutputDocsListFullPath = false); }; \ No newline at end of file diff --git a/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/Common.h b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/Common.h new file mode 100644 index 0000000..989a494 --- /dev/null +++ b/BlueprintToRSTDoc/Source/BlueprintToRSTDoc/Public/Common.h @@ -0,0 +1,6 @@ +#pragma once + +#define ERROR_MESSAGE_BOX(Message) \ + FPlatformMisc::MessageBoxExt(EAppMsgType::Ok, \ + *FString::Format(TEXT("Error:\n\n{0}\n\n---\n\n{1} (Line:{2})"), {Message, *FString(__FILE__), __LINE__}), \ + TEXT("BlueprintToRSTDoc")); \ No newline at end of file diff --git a/samples/SampleProject/Source/SampleProject.Target.cs b/samples/SampleProject/Source/SampleProject.Target.cs index 1e393dd..f43d703 100644 --- a/samples/SampleProject/Source/SampleProject.Target.cs +++ b/samples/SampleProject/Source/SampleProject.Target.cs @@ -1,4 +1,11 @@ -// Copyright Epic Games, Inc. All Rights Reserved. +/*! + * SampleProject + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ using UnrealBuildTool; using System.Collections.Generic; diff --git a/samples/SampleProject/Source/SampleProject/SampleProject.Build.cs b/samples/SampleProject/Source/SampleProject/SampleProject.Build.cs index f7d9254..8706522 100644 --- a/samples/SampleProject/Source/SampleProject/SampleProject.Build.cs +++ b/samples/SampleProject/Source/SampleProject/SampleProject.Build.cs @@ -1,4 +1,11 @@ -// Copyright Epic Games, Inc. All Rights Reserved. +/*! + * SampleProject + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ using UnrealBuildTool; diff --git a/samples/SampleProject/Source/SampleProject/SampleProject.cpp b/samples/SampleProject/Source/SampleProject/SampleProject.cpp index 0238559..4804008 100644 --- a/samples/SampleProject/Source/SampleProject/SampleProject.cpp +++ b/samples/SampleProject/Source/SampleProject/SampleProject.cpp @@ -1,4 +1,11 @@ -// Copyright Epic Games, Inc. All Rights Reserved. +/*! + * SampleProject + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ #include "SampleProject.h" diff --git a/samples/SampleProject/Source/SampleProject/SampleProject.h b/samples/SampleProject/Source/SampleProject/SampleProject.h index ddbf2e2..1966188 100644 --- a/samples/SampleProject/Source/SampleProject/SampleProject.h +++ b/samples/SampleProject/Source/SampleProject/SampleProject.h @@ -1,4 +1,11 @@ -// Copyright Epic Games, Inc. All Rights Reserved. +/*! + * SampleProject + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ #pragma once diff --git a/samples/SampleProject/Source/SampleProjectEditor.Target.cs b/samples/SampleProject/Source/SampleProjectEditor.Target.cs index a391846..65343d9 100644 --- a/samples/SampleProject/Source/SampleProjectEditor.Target.cs +++ b/samples/SampleProject/Source/SampleProjectEditor.Target.cs @@ -1,4 +1,11 @@ -// Copyright Epic Games, Inc. All Rights Reserved. +/*! + * SampleProject + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ using UnrealBuildTool; using System.Collections.Generic; diff --git a/tests/functional_test/FunctionalTest/.gitignore b/tests/functional_test/FunctionalTest/.gitignore new file mode 100644 index 0000000..ea6f021 --- /dev/null +++ b/tests/functional_test/FunctionalTest/.gitignore @@ -0,0 +1,78 @@ +# Original: https://github.com/github/gitignore/blob/main/UnrealEngine.gitignore + +Plugins/BlueprintToRSTDoc + +# Visual Studio 2015 user specific files +.vs/ + +# Compiled Object files +*.slo +*.lo +*.o +*.obj + +# Precompiled Headers +*.gch +*.pch + +# Compiled Dynamic libraries +*.so +*.dylib +*.dll + +# Fortran module files +*.mod + +# Compiled Static libraries +*.lai +*.la +*.a +*.lib + +# Executables +*.exe +*.out +*.app +*.ipa + +# These project files can be generated by the engine +*.xcodeproj +*.xcworkspace +*.sln +*.suo +*.opensdf +*.sdf +*.VC.db +*.VC.opendb + +# Precompiled Assets +SourceArt/**/*.png +SourceArt/**/*.tga + +# Binary Files +Binaries/* +Plugins/*/Binaries/* + +# Builds +Build/* + +# Whitelist PakBlacklist-.txt files +!Build/*/ +Build/*/** +!Build/*/PakBlacklist*.txt + +# Don't ignore icon files in Build +!Build/**/*.ico + +# Built data for maps +*_BuiltData.uasset + +# Configuration files generated by the Editor +Saved/* + +# Compiled source files for the engine to use +Intermediate/* +Plugins/*/Intermediate/* + +# Cache files for the editor to use +DerivedDataCache/* \ No newline at end of file diff --git a/tests/functional_test/FunctionalTest/Config/DefaultEditor.ini b/tests/functional_test/FunctionalTest/Config/DefaultEditor.ini new file mode 100644 index 0000000..e69de29 diff --git a/tests/functional_test/FunctionalTest/Config/DefaultEngine.ini b/tests/functional_test/FunctionalTest/Config/DefaultEngine.ini new file mode 100644 index 0000000..346c6cc --- /dev/null +++ b/tests/functional_test/FunctionalTest/Config/DefaultEngine.ini @@ -0,0 +1,76 @@ + + +[/Script/EngineSettings.GameMapsSettings] +GameDefaultMap=/Game/Blank.Blank +EditorStartupMap=/Game/Blank.Blank + +[/Script/WindowsTargetPlatform.WindowsTargetSettings] +DefaultGraphicsRHI=DefaultGraphicsRHI_DX12 +-D3D12TargetedShaderFormats=PCD3D_SM5 ++D3D12TargetedShaderFormats=PCD3D_SM6 +-D3D11TargetedShaderFormats=PCD3D_SM5 ++D3D11TargetedShaderFormats=PCD3D_SM5 +Compiler=Default +AudioSampleRate=48000 +AudioCallbackBufferFrameSize=1024 +AudioNumBuffersToEnqueue=1 +AudioMaxChannels=0 +AudioNumSourceWorkers=4 +SpatializationPlugin= +SourceDataOverridePlugin= +ReverbPlugin= +OcclusionPlugin= +CompressionOverrides=(bOverrideCompressionTimes=False,DurationThreshold=5.000000,MaxNumRandomBranches=0,SoundCueQualityIndex=0) +CacheSizeKB=65536 +MaxChunkSizeOverrideKB=0 +bResampleForDevice=False +MaxSampleRate=48000.000000 +HighSampleRate=32000.000000 +MedSampleRate=24000.000000 +LowSampleRate=12000.000000 +MinSampleRate=8000.000000 +CompressionQualityModifier=1.000000 +AutoStreamingThreshold=0.000000 +SoundCueCookQualityIndex=-1 + +[/Script/HardwareTargeting.HardwareTargetingSettings] +TargetedHardwareClass=Desktop +AppliedTargetedHardwareClass=Desktop +DefaultGraphicsPerformance=Maximum +AppliedDefaultGraphicsPerformance=Maximum + +[/Script/Engine.RendererSettings] +r.GenerateMeshDistanceFields=True +r.DynamicGlobalIlluminationMethod=1 +r.ReflectionMethod=1 +r.Shadow.Virtual.Enable=1 +r.DefaultFeature.AutoExposure.ExtendDefaultLuminanceRange=True +r.DefaultFeature.LocalExposure.HighlightContrastScale=0.8 +r.DefaultFeature.LocalExposure.ShadowContrastScale=0.8 + +[/Script/WorldPartitionEditor.WorldPartitionEditorSettings] +CommandletClass=Class'/Script/UnrealEd.WorldPartitionConvertCommandlet' + +[/Script/Engine.UserInterfaceSettings] +bAuthorizeAutomaticWidgetVariableCreation=False +FontDPIPreset=Standard +FontDPI=72 + +[/Script/Engine.Engine] ++ActiveGameNameRedirects=(OldGameName="TP_Blank",NewGameName="/Script/FunctionalTest") ++ActiveGameNameRedirects=(OldGameName="/Script/TP_Blank",NewGameName="/Script/FunctionalTest") + +[/Script/AndroidFileServerEditor.AndroidFileServerRuntimeSettings] +bEnablePlugin=True +bAllowNetworkConnection=True +SecurityToken=67D7A6A846F80E71AF293FB7A28FE181 +bIncludeInShipping=False +bAllowExternalStartInShipping=False +bCompileAFSProject=False +bUseCompression=False +bLogFiles=False +bReportStats=False +ConnectionType=USBOnly +bUseManualIPAddress=False +ManualIPAddress= + diff --git a/tests/functional_test/FunctionalTest/Config/DefaultGame.ini b/tests/functional_test/FunctionalTest/Config/DefaultGame.ini new file mode 100644 index 0000000..8c9ccbf --- /dev/null +++ b/tests/functional_test/FunctionalTest/Config/DefaultGame.ini @@ -0,0 +1,3 @@ + +[/Script/EngineSettings.GeneralProjectSettings] +ProjectID=BBB5D5204BE05E43E38083ACA2DD0382 diff --git a/tests/functional_test/FunctionalTest/Config/DefaultInput.ini b/tests/functional_test/FunctionalTest/Config/DefaultInput.ini new file mode 100644 index 0000000..4cc3605 --- /dev/null +++ b/tests/functional_test/FunctionalTest/Config/DefaultInput.ini @@ -0,0 +1,85 @@ +[/Script/Engine.InputSettings] +-AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="Mouse2D",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) ++AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Mouse2D",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Left_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Left_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Left_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Right_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Right_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Vive_Right_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Left_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Left_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Left_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Right_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Right_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MixedReality_Right_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Left_Grip_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Left_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Right_Grip_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Right_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="OculusTouch_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Grip_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Grip_Force",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Left_Trackpad_Force",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Grip_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Grip_Force",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Trigger_Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Trackpad_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Trackpad_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="ValveIndex_Right_Trackpad_Force",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +bAltEnterTogglesFullscreen=True +bF11TogglesFullscreen=True +bUseMouseForTouch=False +bEnableMouseSmoothing=True +bEnableFOVScaling=True +bCaptureMouseOnLaunch=True +bEnableLegacyInputScales=True +bEnableMotionControls=True +bFilterInputByPlatformUser=False +bShouldFlushPressedKeysOnViewportFocusLost=True +bAlwaysShowTouchInterface=False +bShowConsoleOnFourFingerTap=True +bEnableGestureRecognizer=False +bUseAutocorrect=False +DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown +DefaultViewportMouseLockMode=LockOnCapture +FOVScale=0.011110 +DoubleClickTime=0.200000 +DefaultPlayerInputClass=/Script/EnhancedInput.EnhancedPlayerInput +DefaultInputComponentClass=/Script/EnhancedInput.EnhancedInputComponent +DefaultTouchInterface=/Engine/MobileResources/HUD/DefaultVirtualJoysticks.DefaultVirtualJoysticks +-ConsoleKeys=Tilde ++ConsoleKeys=Tilde ++ConsoleKeys=Caret + diff --git a/tests/functional_test/FunctionalTest/Content/Blank.umap b/tests/functional_test/FunctionalTest/Content/Blank.umap new file mode 100644 index 0000000..af05a58 Binary files /dev/null and b/tests/functional_test/FunctionalTest/Content/Blank.umap differ diff --git a/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestActor.uasset b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestActor.uasset new file mode 100644 index 0000000..751d65d Binary files /dev/null and b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestActor.uasset differ diff --git a/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestEnumeration.uasset b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestEnumeration.uasset new file mode 100644 index 0000000..5547bce Binary files /dev/null and b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestEnumeration.uasset differ diff --git a/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestStructure.uasset b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestStructure.uasset new file mode 100644 index 0000000..4194581 Binary files /dev/null and b/tests/functional_test/FunctionalTest/Content/FunctionalTest/TestStructure.uasset differ diff --git a/tests/functional_test/FunctionalTest/FunctionalTest.uproject b/tests/functional_test/FunctionalTest/FunctionalTest.uproject new file mode 100644 index 0000000..592c2c0 --- /dev/null +++ b/tests/functional_test/FunctionalTest/FunctionalTest.uproject @@ -0,0 +1,22 @@ +{ + "FileVersion": 3, + "EngineAssociation": "5.3", + "Category": "", + "Description": "", + "Modules": [ + { + "Name": "FunctionalTest", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "ModelingToolsEditorMode", + "Enabled": true, + "TargetAllowList": [ + "Editor" + ] + } + ] +} \ No newline at end of file diff --git a/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Blueprint/Game/FunctionalTest/TestActor.rst b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Blueprint/Game/FunctionalTest/TestActor.rst new file mode 100644 index 0000000..cd3e8ea --- /dev/null +++ b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Blueprint/Game/FunctionalTest/TestActor.rst @@ -0,0 +1,159 @@ +TestActor +========== + +Path: /Game/FunctionalTest/TestActor + +.. cpp:class:: TestActor : public Actor + + .. cpp:function:: void Construction_Script(exec then) + + Type: Construction script, the place to spawn components and do other setup. @note Name used in CreateBlueprint function + + Category: + + Access Modifier: Public + + Constant: False + + Flags: Required API, Event, Blueprint Event + + Construction script, the place to spawn components and do other setup. @note Name used in CreateBlueprint function + + :arg then: + :type then: exec + + .. cpp:function:: void Function_0(exec then, Vector Input_0, TestStructure Input_1) + + Type: Function 0 Description + + Category: Test + + Access Modifier: Public + + Constant: False + + Flags: Blueprint Callable, Blueprint Event, Blueprint Pure + + Function 0 Description + + :arg then: + :type then: exec + :arg Input_0: + :type Input_0: Vector + :arg Input_1: + :type Input_1: TestStructure + + .. cpp:function:: (exec, TestEnumeration, EDOFMode) Function_1(exec then) + + Type: Function 1 Description + + Category: Test + + Access Modifier: Public + + Constant: False + + Flags: Has Out Params, Blueprint Callable, Blueprint Event + + Function 1 Description + + :arg then: + :type then: exec + :returns execute: + :rtype execute: exec + :returns Output_0: (Default: NewEnumerator0) + :rtype Output_0: TestEnumeration + :returns Output_1: (Default: Default) + :rtype Output_1: EDOFMode + + .. cpp:function:: (exec, bool, string) Function_2(exec then, int Input_0, int Input_1) + + Type: Function 2 Description + + Category: + + Access Modifier: Public + + Constant: True + + Flags: Has Out Params, Blueprint Callable, Blueprint Event + + Function 2 Description + + :arg then: + :type then: exec + :arg Input_0: + :type Input_0: int + :arg Input_1: + :type Input_1: int + :returns execute: + :rtype execute: exec + :returns Output_0: (Default: false) + :rtype Output_0: bool + :returns Output_1: + :rtype Output_1: string + + .. cpp:function:: void Macro_0() + + Type: Macro 0 Description + + Category: + + Access Modifier: + + Constant: False + + Flags: + + Macro 0 Description + + .. cpp:member:: SceneComponent DefaultSceneRoot + + Category: Default + + Access Modifier: + Flags: Blueprint Visible, Zero Constructor, Instanced Reference, Non Transactional, No Destructor, Has Get Value Type Hash + Lifetime Condition: None + + + + .. cpp:member:: bool Variable_0 + + Category: Test + + Access Modifier: + Flags: Edit, Blueprint Visible, Zero Constructor, Disable Edit On Instance, Is Plain Old Data, No Destructor, Has Get Value Type Hash + Lifetime Condition: None + + Variable 0 Description + + .. cpp:member:: Vector Variable_1 + + Category: Test + + Access Modifier: + Flags: Edit, Blueprint Visible, Net, Zero Constructor, Is Plain Old Data, No Destructor, Has Get Value Type Hash + Lifetime Condition: Autonomous Only + + Variable 1 Description + + .. cpp:member:: TestStructure Variable_2 + + Category: Default + + Access Modifier: + Flags: Edit, Blueprint Visible, Disable Edit On Instance, Is Plain Old Data, No Destructor, Has Get Value Type Hash + Lifetime Condition: None + + Variable 2 Description + + .. cpp:member:: MulticastInlineDelegate Event_0 + + Category: Default + + Access Modifier: + Flags: Edit, Blueprint Visible, Zero Constructor, Disable Edit On Instance, Blueprint Assignable, Blueprint Callable + Lifetime Condition: None + + Event 0 Description + diff --git a/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/DocsList.txt b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/DocsList.txt new file mode 100644 index 0000000..71d77c0 --- /dev/null +++ b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/DocsList.txt @@ -0,0 +1,3 @@ +Blueprint/Game/FunctionalTest/TestActor.rst +Struct/Game/FunctionalTest/TestStructure.rst +Enum/Game/FunctionalTest/TestEnumeration.rst \ No newline at end of file diff --git a/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Enum/Game/FunctionalTest/TestEnumeration.rst b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Enum/Game/FunctionalTest/TestEnumeration.rst new file mode 100644 index 0000000..f8988e8 --- /dev/null +++ b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Enum/Game/FunctionalTest/TestEnumeration.rst @@ -0,0 +1,17 @@ +TestEnumeration +================ + +Path: /Game/FunctionalTest/TestEnumeration + +.. cpp:enum:: TestEnumeration + + Enumeration Description + + .. cpp:enumerator:: Item_0 = 0 + + tem 0 Description + + .. cpp:enumerator:: Item_1 = 1 + + Item 1 Description + diff --git a/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Struct/Game/FunctionalTest/TestStructure.rst b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Struct/Game/FunctionalTest/TestStructure.rst new file mode 100644 index 0000000..ff7b166 --- /dev/null +++ b/tests/functional_test/FunctionalTest/FunctionalTest/Expected/rst/Struct/Game/FunctionalTest/TestStructure.rst @@ -0,0 +1,29 @@ +TestStructure +============== + +Path: /Game/FunctionalTest/TestStructure + +.. cpp:class:: TestStructure + + Structure Description + + .. cpp:member:: int Variable_0 + + Category: + + Access Modifier: + Flags: Edit, Blueprint Visible, Zero Constructor, Is Plain Old Data, No Destructor, Has Get Value Type Hash + Lifetime Condition: None + + + + .. cpp:member:: Vector Variable_1 + + Category: + + Access Modifier: + Flags: Edit, Blueprint Visible, Zero Constructor, Is Plain Old Data, No Destructor, Has Get Value Type Hash + Lifetime Condition: None + + + diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTest.Target.cs b/tests/functional_test/FunctionalTest/Source/FunctionalTest.Target.cs new file mode 100644 index 0000000..de12945 --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTest.Target.cs @@ -0,0 +1,22 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +using UnrealBuildTool; +using System.Collections.Generic; + +public class FunctionalTestTarget : TargetRules +{ + public FunctionalTestTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Game; + DefaultBuildSettings = BuildSettingsVersion.V4; + IncludeOrderVersion = EngineIncludeOrderVersion.Unreal5_3; + ExtraModuleNames.Add("FunctionalTest"); + } +} diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.Build.cs b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.Build.cs new file mode 100644 index 0000000..db90016 --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.Build.cs @@ -0,0 +1,31 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +using UnrealBuildTool; + +public class FunctionalTest : ModuleRules +{ + public FunctionalTest(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicDependencyModuleNames.AddRange(new string[]{"Core", "CoreUObject", "Engine", "InputCore", "BlueprintToRSTDoc"}); + + PrivateDependencyModuleNames.AddRange(new string[]{}); + + // Uncomment if you are using Slate UI + // PrivateDependencyModuleNames.AddRange(new string[] { "Slate", "SlateCore" }); + + // Uncomment if you are using online features + // PrivateDependencyModuleNames.Add("OnlineSubsystem"); + + // To include OnlineSubsystemSteam, add it to the plugins section in your uproject file with the Enabled attribute set to + // true + } +} diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.cpp b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.cpp new file mode 100644 index 0000000..8fccf9c --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.cpp @@ -0,0 +1,14 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +#include "FunctionalTest.h" + +#include "Modules/ModuleManager.h" + +IMPLEMENT_PRIMARY_GAME_MODULE(FDefaultGameModuleImpl, FunctionalTest, "FunctionalTest"); diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.h b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.h new file mode 100644 index 0000000..a894edc --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTest.h @@ -0,0 +1,12 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +#pragma once + +#include "CoreMinimal.h" diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTestAutomationTest.cpp b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTestAutomationTest.cpp new file mode 100644 index 0000000..3e20bd0 --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTest/FunctionalTestAutomationTest.cpp @@ -0,0 +1,82 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +#include "BPLibrary.h" +#include "GenericPlatform/GenericPlatformFile.h" +#include "HAL/FileManagerGeneric.h" +#include "Kismet/KismetSystemLibrary.h" +#include "Misc/AutomationTest.h" + +IMPLEMENT_SIMPLE_AUTOMATION_TEST(FFuntionalTestSyncVersion, "BlueprintToRSTDoc.FunctionalTest.GenerateRSTDocument", + EAutomationTestFlags::EditorContext | EAutomationTestFlags::EngineFilter); + +bool FFuntionalTestSyncVersion::RunTest(const FString& Parameters) +{ + FString ProjectFilePath = FPaths::GetProjectFilePath(); + FString OutputDirectory = FString::Format(TEXT("{0}/_FunctionalTestOutput"), {FPaths::GetPath(ProjectFilePath)}); + + // Create an output directory. + IPlatformFile& PlatformFile = FPlatformFileManager::Get().GetPlatformFile(); + if (!PlatformFile.DirectoryExists(*OutputDirectory)) + { + PlatformFile.CreateDirectory(*OutputDirectory); + } + + // Generate RST documents. + bool bSuccess; + FString ErrorMessage; + UBlueprintToRSTDocBPLibrary::GenerateRSTDoc( + OutputDirectory, {"ChaosNiagara", "Engine", "DatasmithContent", "Niagara"}, bSuccess, ErrorMessage); + if (!bSuccess) + { + UE_LOG(LogTemp, Error, TEXT("%s"), *ErrorMessage); + return 1; + } + + IFileManager& FileManager = FFileManagerGeneric::Get(); + FString ExpectedFilesDirectory = FString::Format(TEXT("{0}/FunctionalTest/Expected"), {FPaths::GetPath(ProjectFilePath)}); + TArray ExpectedFiles; + FString ActualFilesDirectory = OutputDirectory; + TArray ActualFiles; + FileManager.FindFilesRecursive(ExpectedFiles, *ExpectedFilesDirectory, TEXT("*.*"), true, false, false); + FileManager.FindFilesRecursive(ActualFiles, *ActualFilesDirectory, TEXT("*.*"), true, false, false); + + if (ExpectedFiles.Num() != ActualFiles.Num()) + { + UE_LOG(LogTemp, Error, TEXT("Number of Files is not matched: %d (Expected) vs %d (Actual)"), ExpectedFiles.Num(), + ActualFiles.Num()); + return 1; + } + + TMap FilePairs; + for (auto E : ExpectedFiles) + { + FString FileName = E.Mid(ExpectedFilesDirectory.Len()); + int32 Index = ActualFiles.Find(ActualFilesDirectory + FileName); + if (Index == INDEX_NONE) + { + UE_LOG(LogTemp, Error, TEXT("Not Found: %s"), *FileName); + return 1; + } + + FString Expected; + FString Actual; + FFileHelper::LoadFileToString(Expected, *E); + FFileHelper::LoadFileToString(Actual, *ActualFiles[Index]); + if (Expected != Actual) + { + UE_LOG(LogTemp, Error, TEXT("File Content does not match (File: %s)"), *E); + return 1; + } + } + + PlatformFile.DeleteDirectoryRecursively(*OutputDirectory); + + return 0; +} diff --git a/tests/functional_test/FunctionalTest/Source/FunctionalTestEditor.Target.cs b/tests/functional_test/FunctionalTest/Source/FunctionalTestEditor.Target.cs new file mode 100644 index 0000000..c4c9253 --- /dev/null +++ b/tests/functional_test/FunctionalTest/Source/FunctionalTestEditor.Target.cs @@ -0,0 +1,22 @@ +/*! + * FunctionalTest + * + * Copyright (c) 2019-2023 nutti + * + * This software is released under the MIT License. + * https://opensource.org/licenses/MIT + */ + +using UnrealBuildTool; +using System.Collections.Generic; + +public class FunctionalTestEditorTarget : TargetRules +{ + public FunctionalTestEditorTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Editor; + DefaultBuildSettings = BuildSettingsVersion.V4; + IncludeOrderVersion = EngineIncludeOrderVersion.Unreal5_3; + ExtraModuleNames.Add("FunctionalTest"); + } +}