vault backup: 2024-10-12 17:19:45
This commit is contained in:
@@ -0,0 +1,58 @@
|
||||
# Config
|
||||
|
||||
- **功能描述:** 指定配置文件的名字,把该对象的值保存到ini配置文件中。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** string="abc"
|
||||
- **作用机制:** Config文件名存在FName UClass::ClassConfigName这个参数里
|
||||
- **关联项:** [PerObjectConfig](PerObjectConfig.md)、[ConfigDoNotCheckDefaults](ConfigDoNotCheckDefaults.md)、[DefaultConfig](DefaultConfig/DefaultConfig.md)、[GlobalUserConfig](GlobalUserConfig/GlobalUserConfig.md)、[ProjectUserConfig](ProjectUserConfig/ProjectUserConfig.md)
|
||||
- **常用程度:★★★★★**
|
||||
|
||||
指定配置文件的名字,把该对象的值保存到ini配置文件中。
|
||||
|
||||
- 一整个类在ini中只有一个节的值,因此一般是保存的CDO对象,但也可以用普通对象。
|
||||
- Config文件名称的元数据值保存在FName UClass::ClassConfigName。
|
||||
- 默认是保存在Saved/XXX.ini的Local文件中。
|
||||
- 此说明符会传播到所有子类并且无法使此说明符无效,但是子类可通过重新声明config说明符并提供不同的ConfigName来更改配置文件。
|
||||
- 常见的ConfigName值是“Engine”、“Editor”、“Input”和“Game”。
|
||||
- 可以自己手动调用SaveConfig和LoadConfig来读写配置值。CDO的值会被引擎自己的从配置中读取而更新。
|
||||
- 想保存到配置文件里的属性要相应的用UPROPERTY(config)修饰。
|
||||
|
||||
## 示例代码:
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = Game)
|
||||
class INSIDER_API UMyClass_Config :public UObject
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite)
|
||||
int32 MyProperty = 123;
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
};
|
||||
|
||||
//测试代码
|
||||
UMyClass_Config* testObject = NewObject<UMyClass_Config>(GetTransientPackage(),TEXT("testObject"));
|
||||
testObject->SaveConfig();
|
||||
|
||||
//生成
|
||||
\Hello\Saved\Config\WindowsEditor\Game.ini
|
||||
[/Script/Insider.MyClass_Config]
|
||||
MyPropertyWithConfig=123
|
||||
```
|
||||
|
||||
## 原理:
|
||||
|
||||
在引擎启动的时候UObjectLoadAllCompiledInDefaultProperties会加载所有Class的CDO,在多个调用链条之后会自动的调用CDO的LoadConfig来初始化CDO的值。
|
||||
|
||||
```cpp
|
||||
static void UObjectLoadAllCompiledInDefaultProperties(TArray<UClass*>& OutAllNewClasses)
|
||||
{
|
||||
for (UClass* Class : NewClasses)
|
||||
{
|
||||
UE_LOG(LogUObjectBootstrap, Verbose, TEXT("GetDefaultObject Begin %s %s"), *Class->GetOutermost()->GetName(), *Class->GetName());
|
||||
Class->GetDefaultObject();
|
||||
UE_LOG(LogUObjectBootstrap, Verbose, TEXT("GetDefaultObject End %s %s"), *Class->GetOutermost()->GetName(), *Class->GetName());
|
||||
}
|
||||
}
|
||||
```
|
@@ -0,0 +1,93 @@
|
||||
# ConfigDoNotCheckDefaults
|
||||
|
||||
- **功能描述:** 指定在保存配置值的时候忽略上一级的配置值的一致性检查。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** bool
|
||||
- **作用机制:** 在ClassFlags中增加[CLASS_ConfigDoNotCheckDefaults](../../../Flags/EClassFlags/CLASS_ConfigDoNotCheckDefaults.md)
|
||||
- **关联项:** [Config](Config.md)
|
||||
- **常用程度:★**
|
||||
|
||||
指定在保存配置值的时候忽略上一级的配置值的一致性检查。
|
||||
|
||||
- 在保存配置的时候,决定是否要先根据Base或Default的配置来检查属性是否一致,如果一致就不用序列化写入下来。但加上这个标志后,即使同上一个层级的配置值相同也无论如何都要保存下来。
|
||||
|
||||
UCLASS(config=XXX,configdonotcheckdefaults):表示这个类对应的配置文件不会检查XXX层级上层的DefaultXXX配置文件是否有该信息(后面会解释层级),就直接存储到Saved目录下。
|
||||
|
||||
## 示例代码:
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = Game)
|
||||
class INSIDER_API UMyClass_Config :public UObject
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite)
|
||||
int32 MyProperty = 123;
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
};
|
||||
|
||||
UCLASS(Config = Game,configdonotcheckdefaults)
|
||||
class INSIDER_API UMyClass_ConfigDoNotCheckDefaults :public UMyClass_Config
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfigSub = 123;
|
||||
};
|
||||
|
||||
UCLASS(Config = Game)
|
||||
class INSIDER_API UMyClass_ConfigDefaultChild :public UMyClass_Config
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfigSub = 123;
|
||||
};
|
||||
```
|
||||
|
||||
## 示例效果:
|
||||
|
||||
```cpp
|
||||
void UMyClass_Config_Test::TestConfigCheckDefaultSave()
|
||||
{
|
||||
auto* testObject = NewObject<UMyClass_ConfigDoNotCheckDefaults>(GetTransientPackage(), TEXT("testObjectCheckDefault"));
|
||||
auto* testObject2 = NewObject<UMyClass_ConfigDefaultChild>(GetTransientPackage(), TEXT("testObjectDefaultChild"));
|
||||
|
||||
testObject->SaveConfig();
|
||||
testObject2->SaveConfig();
|
||||
}
|
||||
|
||||
生成:
|
||||
[/Script/Insider.MyClass_Config]
|
||||
MyPropertyWithConfig=777
|
||||
|
||||
[/Script/Insider.MyClass_ConfigDoNotCheckDefaults]
|
||||
MyPropertyWithConfigSub=123
|
||||
MyPropertyWithConfig=777
|
||||
|
||||
[/Script/Insider.MyClass_ConfigDefaultChild]
|
||||
MyPropertyWithConfigSub=123
|
||||
```
|
||||
|
||||
由此可见,MyClass_ConfigDoNotCheckDefaults中的MyPropertyWithConfig的值默认跟UMyClass_Config中的777值一致,但是依然会写入进来。在MyClass_ConfigDefaultChild类中,MyPropertyWithConfig的值因为没有改变,就会被略过。
|
||||
|
||||
在源码里搜configdonotcheckdefaults的时候发现常常和defaultconfig配合使用。什么时候应该使用configdonotcheckdefaults?感觉是为了保持自己的完整性,无论如何都要全部写入进去。在defaultConfig的时候,就可以不管Base里的值,都写入一份到Default配置里,这样在编辑上更加的完整。
|
||||
|
||||
## 原理:
|
||||
|
||||
```cpp
|
||||
const bool bShouldCheckIfIdenticalBeforeAdding = !GetClass()->HasAnyClassFlags(CLASS_ConfigDoNotCheckDefaults) && !bPerObject && bIsPropertyInherited;
|
||||
//简单的示例判断
|
||||
if (!bPropDeprecated && (!bShouldCheckIfIdenticalBeforeAdding || !Property->Identical_InContainer(this, SuperClassDefaultObject, Index)))
|
||||
{
|
||||
FString Value;
|
||||
Property->ExportText_InContainer( Index, Value, this, this, this, PortFlags );
|
||||
Config->SetString( *Section, *Key, *Value, PropFileName );
|
||||
}
|
||||
else
|
||||
{
|
||||
// If we are not writing it to config above, we should make sure that this property isn't stagnant in the cache.
|
||||
Config->RemoveKey( *Section, *Key, PropFileName );
|
||||
}
|
||||
```
|
@@ -0,0 +1,89 @@
|
||||
# DefaultConfig
|
||||
|
||||
- **功能描述:** 指定保存到的配置文件层级是Project/Config/DefaultXXX.ini。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** bool
|
||||
- **作用机制:** 在ClassFlags中增加[CLASS_DefaultConfig](../../../../Flags/EClassFlags/CLASS_DefaultConfig.md)
|
||||
- **关联项:** [Config](../Config.md)
|
||||
- **常用程度:★★★**
|
||||
|
||||
指定保存到的配置文件层级是Project/Config/DefaultXXX.ini。
|
||||
|
||||
- 而不是默认的Saved/XXX.ini
|
||||
- 一般用在编辑器里把Settings自动保存到Project/Config/DefaultXXX.ini里去
|
||||
|
||||
## 示例代码:
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = MyGame,DefaultConfig)
|
||||
class INSIDER_API UMyClass_DefaultConfig :public UDeveloperSettings
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
/** Gets the settings container name for the settings, either Project or Editor */
|
||||
virtual FName GetContainerName() const override { return TEXT("Project"); }
|
||||
/** Gets the category for the settings, some high level grouping like, Editor, Engine, Game...etc. */
|
||||
virtual FName GetCategoryName() const override { return TEXT("MyGame"); }
|
||||
/** The unique name for your section of settings, uses the class's FName. */
|
||||
virtual FName GetSectionName() const override { return TEXT("MyGame"); }
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
};
|
||||
|
||||
//保存的结果:
|
||||
//Config/DefaultMyGame.ini
|
||||
[/Script/Insider.MyClass_DefaultConfig]
|
||||
MyPropertyWithConfig=888
|
||||
|
||||
```
|
||||
|
||||
## 示例结果:
|
||||
|
||||

|
||||
|
||||
## 原理:
|
||||
|
||||
代码里要使用Settings->TryUpdateDefaultConfigFile();,但发现TryUpdateDefaultConfigFile不管有没有DefaultConfig都可以调用,都可以保存到Default里。因此应该调用哪个SaveConfig(TryUpdateDefaultConfigFile,UpdateGlobalUserConfigFile,UpdateProjectUserConfigFile)是可以手动指定的。
|
||||
|
||||
但是在编辑器里编辑的时候,则可以通过写好的代码来处理好逻辑。如SSettingsEditor.cpp里NotifyPostChange中调用Section->Save();则可以在内部再调用如下代码:
|
||||
|
||||
```cpp
|
||||
bool FSettingsSection::Save()
|
||||
{
|
||||
if (ModifiedDelegate.IsBound() && !ModifiedDelegate.Execute())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (SaveDelegate.IsBound())
|
||||
{
|
||||
return SaveDelegate.Execute();
|
||||
}
|
||||
|
||||
//更新到正确的文件里
|
||||
if (SettingsObject.IsValid())
|
||||
{
|
||||
if (SettingsObject->GetClass()->HasAnyClassFlags(CLASS_DefaultConfig))
|
||||
{
|
||||
SettingsObject->TryUpdateDefaultConfigFile();
|
||||
}
|
||||
else if (SettingsObject->GetClass()->HasAnyClassFlags(CLASS_GlobalUserConfig))
|
||||
{
|
||||
SettingsObject->UpdateGlobalUserConfigFile();
|
||||
}
|
||||
else if (SettingsObject->GetClass()->HasAnyClassFlags(CLASS_ProjectUserConfig))
|
||||
{
|
||||
SettingsObject->UpdateProjectUserConfigFile();
|
||||
}
|
||||
else
|
||||
{
|
||||
SettingsObject->SaveConfig();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
```
|
Binary file not shown.
After Width: | Height: | Size: 84 KiB |
@@ -0,0 +1,70 @@
|
||||
# EditorConfig
|
||||
|
||||
- **功能描述:** 用来在编辑器状态下保存信息。
|
||||
- **引擎模块:** Config, Editor
|
||||
- **元数据类型:** string="abc"
|
||||
- **作用机制:** 在Meta中增加[EditorConfig](../../../../Meta/Config/EditorConfig.md)
|
||||
- **常用程度:★**
|
||||
|
||||
用来在编辑器状态下保存信息。
|
||||
|
||||
一般用在EditorTarget的Module里,用于配置相应编辑器的信息,比如列宽,收藏夹之类的,用json保存。
|
||||
|
||||
保存在:C:\Users\{user name}\AppData\Local\UnrealEngine\Editor。当前有:
|
||||
|
||||

|
||||
|
||||
在源码里搜索后,使用的时候必须继承于基类:
|
||||
|
||||
```cpp
|
||||
/** Inherit from this class to simplify saving and loading properties from editor configs. */
|
||||
UCLASS()
|
||||
class EDITORCONFIG_API UEditorConfigBase : public UObject
|
||||
{
|
||||
GENERATED_BODY()
|
||||
|
||||
public:
|
||||
|
||||
/** Load any properties of this class into properties marked with metadata tag "EditorConfig" from the class's EditorConfig */
|
||||
bool LoadEditorConfig();
|
||||
|
||||
/** Save any properties of this class in properties marked with metadata tag "EditorConfig" into the class's EditorConfig. */
|
||||
bool SaveEditorConfig() const;
|
||||
};
|
||||
```
|
||||
|
||||
## 示例代码:
|
||||
|
||||
```cpp
|
||||
UCLASS(EditorConfig = "MyEditorGame")
|
||||
class INSIDER_API UMyClass_EditorConfig : public UEditorConfigBase
|
||||
{
|
||||
public:
|
||||
GENERATED_BODY()
|
||||
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, meta = (EditorConfig))
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
};
|
||||
|
||||
void UMyClass_EditorConfig_Test::TestConfigSave()
|
||||
{
|
||||
//must run after editor initialization
|
||||
auto* testObject = NewObject<UMyClass_EditorConfig>(GetTransientPackage(), TEXT("testObject_EditorConfig"));
|
||||
testObject->MyPropertyWithConfig = 777;
|
||||
testObject->SaveEditorConfig();
|
||||
|
||||
}
|
||||
|
||||
void UMyClass_EditorConfig_Test::TestConfigLoad()
|
||||
{
|
||||
auto* testObject = NewObject<UMyClass_EditorConfig>(GetTransientPackage(), TEXT("testObject_EditorConfig"));
|
||||
testObject->LoadEditorConfig();
|
||||
}
|
||||
|
||||
//运行Save后的保存结果:C:\Users\jack.fu\AppData\Local\UnrealEngine\Editor\MyEditorGame.json
|
||||
|
||||
{
|
||||
"$type": "MyClass_EditorConfig",
|
||||
"MyPropertyWithConfig": 777
|
||||
}
|
||||
```
|
Binary file not shown.
After Width: | Height: | Size: 128 KiB |
@@ -0,0 +1,74 @@
|
||||
# GlobalUserConfig
|
||||
|
||||
- **功能描述:** 指定保存到的配置文件层级是全局用户设置 Engine/Config/UserXXX.ini。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** bool
|
||||
- **作用机制:** 在ClassFlags中增加[CLASS_GlobalUserConfig](../../../../Flags/EClassFlags/CLASS_GlobalUserConfig.md)
|
||||
- **关联项:** [Config](../Config.md)
|
||||
- **常用程度:★★★**
|
||||
|
||||
指定保存到的配置文件层级是全局用户设置 Engine/Config/UserXXX.ini。
|
||||
|
||||
## 示例代码:
|
||||
|
||||
属性用Config或者GlobalConfig都是可以的。
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = MyGame, GlobalUserConfig)
|
||||
class INSIDER_API UMyClass_GlobalUserConfig:public UDeveloperSettings
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
/** Gets the settings container name for the settings, either Project or Editor */
|
||||
virtual FName GetContainerName() const override { return TEXT("Project"); }
|
||||
/** Gets the category for the settings, some high level grouping like, Editor, Engine, Game...etc. */
|
||||
virtual FName GetCategoryName() const override { return TEXT("MyGame"); }
|
||||
/** The unique name for your section of settings, uses the class's FName. */
|
||||
virtual FName GetSectionName() const override { return TEXT("MyGlobalGame"); }
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, GlobalConfig)
|
||||
int32 MyPropertyWithGlobalConfig = 456;
|
||||
};
|
||||
|
||||
保存到C:\Users\jack.fu\AppData\Local\Unreal Engine\Engine\Config\UserMyGame.ini
|
||||
[/Script/Insider.UMyClass_GlobalUserConfig]
|
||||
MyPropertyWithGlobalConfig=999
|
||||
```
|
||||
|
||||
## 示例效果:
|
||||
|
||||

|
||||
|
||||
## 源码例子:
|
||||
|
||||
```cpp
|
||||
UCLASS(config=Engine, globaluserconfig)
|
||||
class ANDROIDPLATFORMEDITOR_API UAndroidSDKSettings : public UObject
|
||||
{
|
||||
public:
|
||||
GENERATED_UCLASS_BODY()
|
||||
|
||||
// Location on disk of the Android SDK (falls back to ANDROID_HOME environment variable if this is left blank)
|
||||
UPROPERTY(GlobalConfig, EditAnywhere, Category = SDKConfig, Meta = (DisplayName = "Location of Android SDK (the directory usually contains 'android-sdk-')"))
|
||||
FDirectoryPath SDKPath;
|
||||
|
||||
// Location on disk of the Android NDK (falls back to NDKROOT environment variable if this is left blank)
|
||||
UPROPERTY(GlobalConfig, EditAnywhere, Category = SDKConfig, Meta = (DisplayName = "Location of Android NDK (the directory usually contains 'android-ndk-')"))
|
||||
FDirectoryPath NDKPath;
|
||||
|
||||
// Location on disk of Java (falls back to JAVA_HOME environment variable if this is left blank)
|
||||
UPROPERTY(GlobalConfig, EditAnywhere, Category = SDKConfig, Meta = (DisplayName = "Location of JAVA (the directory usually contains 'jdk')"))
|
||||
FDirectoryPath JavaPath;
|
||||
|
||||
// Which SDK to package and compile Java with (a specific version or (without quotes) 'latest' for latest version on disk, or 'matchndk' to match the NDK API Level)
|
||||
UPROPERTY(GlobalConfig, EditAnywhere, Category = SDKConfig, Meta = (DisplayName = "SDK API Level (specific version, 'latest', or 'matchndk' - see tooltip)"))
|
||||
FString SDKAPILevel;
|
||||
|
||||
// Which NDK to compile with (a specific version or (without quotes) 'latest' for latest version on disk). Note that choosing android-21 or later won't run on pre-5.0 devices.
|
||||
UPROPERTY(GlobalConfig, EditAnywhere, Category = SDKConfig, Meta = (DisplayName = "NDK API Level (specific version or 'latest' - see tooltip)"))
|
||||
FString NDKAPILevel;
|
||||
};
|
||||
```
|
Binary file not shown.
After Width: | Height: | Size: 86 KiB |
@@ -0,0 +1,73 @@
|
||||
# PerObjectConfig
|
||||
|
||||
- **功能描述:** 在已经有config配置文件名字的情况下,指定应该按每个对象实例来存储值,而不是一个类一个存储值。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** bool
|
||||
- **作用机制:** 在ClassFlags中增加[CLASS_PerObjectConfig](../../../Flags/EClassFlags/CLASS_PerObjectConfig.md)
|
||||
- **关联项:** [Config](Config.md)
|
||||
- **常用程度:★★★★★**
|
||||
|
||||
在已经有config配置文件名字的情况下,指定应该按每个对象实例来存储值,而不是一个类一个存储值。
|
||||
|
||||
- 此类的配置信息将按对象存储,在.ini文件中,每个对象都有一个分段,根据对象命名,格式为[ObjectName ClassName]。
|
||||
- 此说明符会传播到子类。指定该配置是对每个对象都单独保存。
|
||||
|
||||
## 示例代码:
|
||||
|
||||
注意ObjectName必须一致
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = Game,PerObjectConfig)
|
||||
class INSIDER_API UMyClass_PerObjectConfig :public UObject
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite)
|
||||
int32 MyProperty = 123;
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
};
|
||||
|
||||
void UMyClass_Config_Test::TestPerObjectConfigSave()
|
||||
{
|
||||
UMyClass_PerObjectConfig* testObject1 = NewObject<UMyClass_PerObjectConfig>(GetTransientPackage(), TEXT("testObject1"));
|
||||
testObject1->MyPropertyWithConfig = 456;
|
||||
testObject1->SaveConfig();
|
||||
|
||||
UMyClass_PerObjectConfig* testObject2 = NewObject<UMyClass_PerObjectConfig>(GetTransientPackage(), TEXT("testObject2"));
|
||||
testObject2->MyPropertyWithConfig = 789;
|
||||
testObject2->SaveConfig();
|
||||
|
||||
}
|
||||
|
||||
void UMyClass_Config_Test::TestPerObjectConfigLoad()
|
||||
{
|
||||
UMyClass_PerObjectConfig* testObject1 = NewObject<UMyClass_PerObjectConfig>(GetTransientPackage(), TEXT("testObject1"));
|
||||
//testObject1->LoadConfig(); //不需要显式调用LoadConfig
|
||||
|
||||
UMyClass_PerObjectConfig* testObject2 = NewObject<UMyClass_PerObjectConfig>(GetTransientPackage(), TEXT("testObject2"));
|
||||
//testObject2->LoadConfig();
|
||||
}
|
||||
|
||||
//\Saved\Config\WindowsEditor\Game.ini
|
||||
[testObject1 MyClass_PerObjectConfig]
|
||||
MyPropertyWithConfig=456
|
||||
|
||||
[testObject2 MyClass_PerObjectConfig]
|
||||
MyPropertyWithConfig=789
|
||||
```
|
||||
|
||||
## 原理:
|
||||
|
||||
对象构造的末期会尝试去读取配置。
|
||||
|
||||
```cpp
|
||||
void FObjectInitializer::PostConstructInit()
|
||||
{
|
||||
//在NewObject构造中后面会调用
|
||||
if (bIsCDO || Class->HasAnyClassFlags(CLASS_PerObjectConfig))
|
||||
{
|
||||
Obj->LoadConfig(NULL, NULL, bIsCDO ? UE::LCPF_ReadParentSections : UE::LCPF_None);
|
||||
}
|
||||
}
|
||||
```
|
@@ -0,0 +1,53 @@
|
||||
# ProjectUserConfig
|
||||
|
||||
- **功能描述:** 指定保存到的配置文件层级是项目用户设置 Project/Config/UserXXX.ini。
|
||||
- **引擎模块:** Config
|
||||
- **元数据类型:** bool
|
||||
- **作用机制:** 在ClassFlags中增加[CLASS_ProjectUserConfig](../../../../Flags/EClassFlags/CLASS_ProjectUserConfig.md)
|
||||
- **关联项:** [Config](../Config.md)
|
||||
- **常用程度:★★★**
|
||||
|
||||
指定保存到的配置文件层级是项目用户设置 Project/Config/UserXXX.ini。
|
||||
|
||||
## 示例代码:
|
||||
|
||||
保存的目录是\Hello\Config\UserMyGame.ini
|
||||
|
||||
```cpp
|
||||
UCLASS(Config = MyGame, ProjectUserConfig)
|
||||
class INSIDER_API UMyClass_ProjectUserConfig :public UDeveloperSettings
|
||||
{
|
||||
GENERATED_BODY()
|
||||
public:
|
||||
/** Gets the settings container name for the settings, either Project or Editor */
|
||||
virtual FName GetContainerName() const override { return TEXT("Project"); }
|
||||
/** Gets the category for the settings, some high level grouping like, Editor, Engine, Game...etc. */
|
||||
virtual FName GetCategoryName() const override { return TEXT("MyGame"); }
|
||||
/** The unique name for your section of settings, uses the class's FName. */
|
||||
virtual FName GetSectionName() const override { return TEXT("MyProjectGame"); }
|
||||
public:
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, Config)
|
||||
int32 MyPropertyWithConfig = 123;
|
||||
|
||||
UPROPERTY(EditAnywhere, BlueprintReadWrite, GlobalConfig)
|
||||
int32 MyPropertyWithGlobalConfig = 456;
|
||||
};
|
||||
|
||||
//结果:\Hello\Config\UserMyGame.ini
|
||||
[/Script/Insider.MyClass_ProjectUserConfig]
|
||||
MyPropertyWithConfig=777
|
||||
MyPropertyWithGlobalConfig=888
|
||||
```
|
||||
|
||||
## 示例效果:
|
||||
|
||||

|
||||
|
||||
## 在源码中搜索:
|
||||
|
||||
```cpp
|
||||
UCLASS(config = Engine, projectuserconfig, meta = (DisplayName = "Rendering Overrides (Local)"))
|
||||
class ENGINE_API URendererOverrideSettings : public UDeveloperSettings
|
||||
{
|
||||
}
|
||||
```
|
Binary file not shown.
After Width: | Height: | Size: 87 KiB |
Reference in New Issue
Block a user