UE4 UE4 C++ Gameplay Abilities 的AttributeSet和GameplayEffect
GAS参考文档
仅是个人理解,参考
AttributeSet是设置玩家属性的比如生命值、最大生命值、、、
GameplayEffect是用来对AttributeSet里的值做修改的
通过这两个东西做到:


一个加血的效果
先给玩家设置血量属性 做一个继承AttributeSet的类
// Fill out your copyright notice in the Description page of Project Settings.
#pragma once
#include "CoreMinimal.h"
#include "AbilitySystemComponent.h"
#include "AttributeSet.h"
#include "MyAttributeSet.generated.h"
/**
*
*/
#define ATTRIBUTE_ACCESSORS(ClassName,PropertyName) \
GAMEPLAYATTRIBUTE_PROPERTY_GETTER(ClassName,PropertyName) \
GAMEPLAYATTRIBUTE_VALUE_GETTER(PropertyName) \
GAMEPLAYATTRIBUTE_VALUE_SETTER(PropertyName) \
GAMEPLAYATTRIBUTE_VALUE_INITTER(PropertyName)
UCLASS()
class MYGAS_API UMyAttributeSet : public UAttributeSet
{
GENERATED_BODY()
public:
UPROPERTY(BlueprintReadOnly)
FGameplayAttributeData Health;
ATTRIBUTE_ACCESSORS(UMyAttributeSet, Health)
UPROPERTY(BlueprintReadOnly)
FGameplayAttributeData MaxHealth;
ATTRIBUTE_ACCESSORS(UMyAttributeSet, MaxHealth)
UPROPERTY(BlueprintReadOnly)
FGameplayAttributeData Damage;
ATTRIBUTE_ACCESSORS(UMyAttributeSet, Damage)
//更改之前会调用
virtual void PreAttributeChange(const FGameplayAttribute& Attribute, float& NewValue) override;
//更改之后
virtual void PostGameplayEffectExecute(const FGameplayEffectModCallbackData& Data) override;
protected:
void AdjustAttributeForMaxChange(FGameplayAttributeData& AffectedAttribute, const FGameplayAttributeData& MaxAttribute, float NewMaxValue, const FGameplayAttribute& AffectedAttributeProperty);
};
// Fill out your copyright notice in the Description page of Project Settings.
#include "GAS/MyAttributeSet.h"
#include "GameplayEffectExtension.h"
#include "MyGAS/MyGASCharacter.h"
void UMyAttributeSet::PreAttributeChange(const FGameplayAttribute& Attribute, float& NewValue)
{
Super::PreAttributeChange(Attribute, NewValue);
/*GetMaxHealthAttribute() 这个要给变量加了ATTRIBUTE_ACCESSORS(UMyAttributeSet, MaxHealth) 这个宏才可以调用*/
if (Attribute == GetMaxHealthAttribute())
{
AdjustAttributeForMaxChange(Health, MaxHealth, NewValue, GetHealthAttribute());
}
}
void UMyAttributeSet::PostGameplayEffectExecute(const FGameplayEffectModCallbackData& Data)
{
if (Data.EvaluatedData.Attribute == GetHealthAttribute())
{
SetHealth(FMath::Clamp(GetHealth(), 0.0f, GetMaxHealth()));
}
else if (Data.EvaluatedData.Attribute == GetDamageAttribute())
{
float CurrentDamage = GetDamage();
if (CurrentDamage > 0)
{
SetDamage(0);
SetHealth(FMath::Clamp(GetHealth() - CurrentDamage, 0.0f, GetMaxHealth()));
AActor* TargetActor = Data.Target.AbilityActorInfo->AvatarActor.Get();
AMyGASCharacter* TargetCharacter = Cast<AMyGASCharacter>(TargetActor);
TargetCharacter->OnDamaged(CurrentDamage);
}
}
}
void UMyAttributeSet::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);
}
}
把这个类初始化到玩家的类里面
像组件一样初始化好就行了


做血条UI
绑定血条的百分比

只有在玩家类里初始化了AttributeSet类才可以拿到

给玩家血条设置初始值
新建一个蓝图类的GameplayEffect:

设置好最大值和当前生命值
在玩家里调用就设置好了初始值

再搞个给玩家加血的GameplayEffect:

这里用到了一个曲线表格:

我们延迟一秒给玩家加50滴血

如果没有曲线表格,就在GE_Add 里面的1数字改为50
只是Level 那里填的50 就没有效果了
这篇博客介绍了如何在Unreal Engine 4 (UE4)中利用Gameplay Ability System (GAS)的AttributeSet和GameplayEffect来管理角色属性和实现加血等效果。首先定义了一个自定义的AttributeSet类`UMyAttributeSet`,包含了生命值、最大生命值和伤害属性,并使用ATTRIBUTE_ACCESSORS宏进行访问。然后在`PreAttributeChange`和`PostGameplayEffectExecute`方法中处理属性变化和效果应用。通过GameplayEffect,创建了加血和造成伤害的效果,包括延迟加血的曲线表格设置。博客还提到了如何在角色类中初始化AttributeSet,并为UI显示血条提供数据。
3684

被折叠的 条评论
为什么被折叠?



