75 lines
2.8 KiB
Markdown
75 lines
2.8 KiB
Markdown
|
## 概述
|
|||
|
在GameplayAbility框架中,UAttributeSet负责管理各种属性。
|
|||
|
|
|||
|
## 定义宏
|
|||
|
在头文件中添加:
|
|||
|
```
|
|||
|
// 使用AttributeSet.h的宏
|
|||
|
#define ATTRIBUTE_ACCESSORS(ClassName, PropertyName) \
|
|||
|
GAMEPLAYATTRIBUTE_PROPERTY_GETTER(ClassName, PropertyName) \
|
|||
|
GAMEPLAYATTRIBUTE_VALUE_GETTER(PropertyName) \
|
|||
|
GAMEPLAYATTRIBUTE_VALUE_SETTER(PropertyName) \
|
|||
|
GAMEPLAYATTRIBUTE_VALUE_INITTER(PropertyName)
|
|||
|
```
|
|||
|
参考注释可以得知,使用这些宏可以让你少写各个属性的Get、Set、Init函数。如果不使用这个宏你也可以自己实现对应的函数。
|
|||
|
|
|||
|
这里用到了Ue4的反射。
|
|||
|
## 添加属性
|
|||
|
再以下格式添加属性:
|
|||
|
```
|
|||
|
UPROPERTY(BlueprintReadOnly, Category = "Health")
|
|||
|
FGameplayAttributeData Health;
|
|||
|
ATTRIBUTE_ACCESSORS(URPGAttributeSet, Health)
|
|||
|
```
|
|||
|
## 重写接口
|
|||
|
ActionRPG案例中重写了PreAttributeChange与PostGameplayEffectExecute接口。
|
|||
|
|
|||
|
前者会在属性被修改时调用,在案例中是为了在血量或魔法上限发生变动时,按比例调整当前血量或者魔法值。后者与GameplayEffect有关,等到编写完GameplayEffect时,再来编写。
|
|||
|
```
|
|||
|
void URPGAttributeSet::PreAttributeChange(const FGameplayAttribute & Attribute, float & NewValue)
|
|||
|
{
|
|||
|
Super::PreAttributeChange(Attribute, NewValue);
|
|||
|
|
|||
|
if (Attribute == GetMaxHealthAttribute())
|
|||
|
{
|
|||
|
AdjustAttributeForMaxChange(Health, MaxHealth, NewValue, GetHealthAttribute());
|
|||
|
}
|
|||
|
else if (Attribute == GetMaxManaAttribute())
|
|||
|
{
|
|||
|
AdjustAttributeForMaxChange(Mana, MaxMana, NewValue, GetManaAttribute());
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
void URPGAttributeSet::PostGameplayEffectExecute(const FGameplayEffectModCallbackData & Data)
|
|||
|
{
|
|||
|
Super::PostGameplayEffectExecute(Data);
|
|||
|
|
|||
|
}
|
|||
|
|
|||
|
void URPGAttributeSet::AdjustAttributeForMaxChange(FGameplayAttributeData& AffectedAttribute, const FGameplayAttributeData& MaxAttribute, float NewMaxValue, const FGameplayAttribute& AffectedAttributeProperty)
|
|||
|
{
|
|||
|
UAbilitySystemComponent* AbilityComp = GetOwningAbilitySystemComponent();
|
|||
|
const float CurrentMaxValue = MaxAttribute.GetCurrentValue();
|
|||
|
if (!FMath::IsNearlyEqual(CurrentMaxValue, NewMaxValue) && AbilityComp)
|
|||
|
{
|
|||
|
// Change current value to maintain the current Val / Max percent
|
|||
|
const float CurrentValue = AffectedAttribute.GetCurrentValue();
|
|||
|
float NewDelta = (CurrentMaxValue > 0.f) ? (CurrentValue * NewMaxValue / CurrentMaxValue) - CurrentValue : NewMaxValue;
|
|||
|
|
|||
|
AbilityComp->ApplyModToAttributeUnsafe(AffectedAttributeProperty, EGameplayModOp::Additive, NewDelta);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
```
|
|||
|
|
|||
|
## 个人的使用方案
|
|||
|
定义URPGAttributeSet作为基础属性集,里面定义通用属性。之后又定义URPGCharacterAttributeSet作为角色专用的属性集。
|
|||
|
|
|||
|
之后在角色类中的构造函数中挂载URPGAttributeSet对象。
|
|||
|
```
|
|||
|
UPROPERTY()
|
|||
|
URPGAttributeSet* AttributeSet;
|
|||
|
```
|
|||
|
```
|
|||
|
AttributeSet = CreateDefaultSubobject<URPGAttributeSet>(TEXT("AttributeSet"));
|
|||
|
```
|