Files
UnrealEngineUWP/Engine/Source/Editor/EditorConfig/Public/JsonConfig.h
sebastian nordgren 1b2a1ceacb Added some includes to fix non-unity compile issues.
#jira UE-107391
#rb trivial

#ROBOMERGE-SOURCE: CL 15311900 in //UE5/Release-5.0-EarlyAccess/...
#ROBOMERGE-BOT: STARSHIP (Release-5.0-EarlyAccess -> Main) (v771-15082668)

[CL 15311992 by sebastian nordgren in ue5-main branch]
2021-02-04 05:47:39 -04:00

147 lines
5.3 KiB
C++

// Copyright Epic Games, Inc. All Rights Reserved.
#pragma once
#include "CoreMinimal.h"
#include "Async/Async.h"
#include "Concepts/EqualityComparable.h"
#include "Containers/StringView.h"
#include "Dom/JsonObject.h"
namespace UE
{
class EDITORCONFIG_API FJsonPath
{
public:
struct FPart
{
FString Name;
int32 Index = INDEX_NONE;
};
FJsonPath();
FJsonPath(const TCHAR* Path);
FJsonPath(FStringView Path);
FJsonPath(const FJsonPath& Other);
FJsonPath(FJsonPath&& Other);
bool IsValid() const { return Length() > 0; }
const int32 Length() const { return PathParts.Num(); }
void Append(FStringView Name);
void SetArrayIndex(int32 Index);
FJsonPath GetSubPath(int32 NumParts) const;
FString ToString() const;
const FPart& operator[](int32 Idx) const { return PathParts[Idx]; }
const TArray<FPart>& GetAll() const { return PathParts; }
private:
void ParsePath(const FString& InPath);
private:
TArray<FPart> PathParts;
};
using FJsonValuePair = TPair<TSharedPtr<FJsonValue>, TSharedPtr<FJsonValue>>;
class EDITORCONFIG_API FJsonConfig
{
public:
FJsonConfig();
void SetParent(TSharedPtr<FJsonConfig> Parent);
bool LoadFromFile(FStringView FilePath);
bool LoadFromString(FStringView Content);
bool SaveToFile(FStringView FilePath) const;
bool SaveToString(FString& OutResult) const;
bool IsValid() const { return MergedObject.IsValid(); }
const FJsonConfig* GetParentConfig() const;
template <typename T>
bool TryGetNumber(const FJsonPath& Path, T& OutValue) const;
bool TryGetBool(const FJsonPath& Path, bool& OutValue) const;
bool TryGetString(const FJsonPath& Path, FString& OutValue) const;
bool TryGetString(const FJsonPath& Path, FName& OutValue) const;
bool TryGetString(const FJsonPath& Path, FText& OutValue) const;
bool TryGetJsonValue(const FJsonPath& Path, TSharedPtr<FJsonValue>& OutValue) const;
bool TryGetJsonObject(const FJsonPath& Path, TSharedPtr<FJsonObject>& OutValue) const;
bool TryGetArray(const FJsonPath& Path, TArray<TSharedPtr<FJsonValue>>& OutArray) const;
TSharedPtr<FJsonObject> GetRootObject() const;
// these are specializations for arithmetic and string arrays
// these could be templated with enable-ifs,
// but it ended up being more lines of incomprehensible template SFINAE than this clear list of types is
bool TryGetArray(const FJsonPath& Path, TArray<bool>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<int8>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<int16>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<int32>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<int64>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<uint8>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<uint16>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<uint32>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<uint64>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<float>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<double>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<FString>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<FText>& OutArray) const;
bool TryGetArray(const FJsonPath& Path, TArray<FName>& OutArray) const;
bool TryGetMap(const FJsonPath& Path, TArray<FJsonValuePair>& OutMap) const;
// try to set a number - returns false if:
// - the path references an object that doesn't exist
// - the path references an index in an array that doesn't exist
template <typename T>
bool SetNumber(const FJsonPath& Path, T Value);
bool SetBool(const FJsonPath& Path, bool Value);
bool SetString(const FJsonPath& Path, FStringView Value);
bool SetString(const FJsonPath& Path, const FText& Value);
bool SetJsonValue(const FJsonPath& Path, TSharedPtr<FJsonValue> Value);
bool SetJsonObject(const FJsonPath& Path, TSharedPtr<FJsonObject> Object);
bool SetJsonArray(const FJsonPath& Path, const TArray<TSharedPtr<FJsonValue>>& Array);
bool SetRootObject(TSharedPtr<FJsonObject> Object);
bool HasOverride(const FJsonPath& Path) const;
private:
template <typename T, typename TGetter>
bool TryGetArrayHelper(const FJsonPath& Path, TArray<T>& OutArray, TGetter Getter) const;
template <typename T>
bool TryGetNumericArrayHelper(const FJsonPath& Path, TArray<T>& OutArray) const;
bool SetJsonValueInMerged(const FJsonPath& Path, TSharedPtr<FJsonValue> Value);
bool SetJsonValueInOverride(const FJsonPath& Path, TSharedPtr<FJsonValue> NewValue, TSharedPtr<FJsonValue> PreviousValue, TSharedPtr<FJsonValue> ParentValue);
bool SetArrayValueInOverride(TSharedPtr<FJsonValue> CurrentValue, const TArray<TSharedPtr<FJsonValue>>& NewArray, TSharedPtr<FJsonValue> ParentValue);
bool SetObjectValueInOverride(TSharedPtr<FJsonObject> CurrentObject, TSharedPtr<FJsonObject> NewObject, TSharedPtr<FJsonValue> ParentValue);
bool RemoveJsonValueFromOverride(const FJsonPath& Path, TSharedPtr<FJsonValue> PreviousValue);
bool MergeThisWithParent();
void OnParentConfigChanged();
private:
TFuture<void> SaveFuture;
FSimpleDelegate OnConfigChanged;
TSharedPtr<FJsonConfig> ParentConfig;
TSharedPtr<FJsonObject> OverrideObject;
TSharedPtr<FJsonObject> MergedObject;
};
}
#include "JsonConfig.inl"