虛幻四Gameplay Ability System入門(5)-沖刺奔跑和深入Attribute

在這篇文章開始前,先分享一個慘痛的經(jīng)歷,就因為在虛幻四的源碼中加了兩句注釋涝动,項目的編譯就走向了擁有3000+ Errors的不歸路 T T,這是啥原理啊炬灭。

這次我們要實現(xiàn)的功能是角色的沖刺奔跑醋粟,操作就是點擊shift后角色的移動速度會增加。這個能力的實現(xiàn)應(yīng)該是挺簡單的重归,但是我會擴展一部分的GAS源碼米愿,深入一下GAS的Attribute,希望能夠幫助到一部分讀者鼻吮。有問題也希望大家可以在評論或者私信告訴我育苟。

接下來進入正題,首先還是講解一下加速跑的實現(xiàn)過程:

  1. shift點擊后activiate加速跑技能狈网。
  2. 加速跑技能會添加一個GE宙搬,這個GE會增加角色Move Speed Attribute
  3. 角色的Character.h/cpp中添加function笨腥,將它與move speed的change delegate綁定在一起拓哺。在該function中會提高角色Movement Component的移動速度。
  4. shift鍵松開后發(fā)送一個Gameplay Event告訴奔跑能力End Ability脖母。

添加MoveSpeed Attribute

打開AttributeSetBase.h/cpp士鸥,然后添加MoveSpeed Attribute。這個操作流程已經(jīng)重復(fù)無數(shù)次啦谆级,相信能看到這里的讀者應(yīng)該都掌握了烤礁,我就不重復(fù)了讼积。

UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category="Attributes", ReplicatedUsing=OnRep_MoveSpeed)
    FGameplayAttributeData MoveSpeed;
    ATTRIBUTE_ACCESSORS(UAttributeSetBase, MoveSpeed);

UFUNCTION()
    virtual void OnRep_MoveSpeed(const FGameplayAttributeData& OldMoveSpeed);
復(fù)制代碼

但是我們創(chuàng)建了這么多次的Attibute,還不了解它的數(shù)據(jù)結(jié)構(gòu)是咋樣的脚仔,打開AttributeSetBase的父類AttributeSet.h勤众。我刪除了其它代碼,重要的是下面的部分鲤脏。它表明一個Attribute中有兩個float值Base Value们颜,和Current Value。

USTRUCT(BlueprintType)
struct GAMEPLAYABILITIES_API FGameplayAttributeData
{
    protected:
    UPROPERTY(BlueprintReadOnly, Category = "Attribute")
    float BaseValue;

    UPROPERTY(BlueprintReadOnly, Category = "Attribute")
    float CurrentValue;
};
復(fù)制代碼

為什么屬性需要Base和Current兩個值呢猎醇?根據(jù)大佬的文檔github.com/tranek/GASD…, Base Value的值屬性的基礎(chǔ)窥突,它是永久(permanent)的,Current Value相反硫嘶,它是臨時的阻问。

打個比方,比如我們要實現(xiàn)的加速奔跑沦疾,它改變的是實際是Current Value称近,當加速效果結(jié)束后,Current Value就會降低回默認值哮塞。類似的效果還有某種buff會暫時提高角色的生命值或者護甲等等煌茬,這個buff改變的就是這種屬性的Current Value。

相反彻桃,當角色的生命值被攻擊后扣除坛善,它改變的就是Health屬性的Base Value,可以把攻擊造成的傷害當作是永久改變的邻眷,畢竟沒有其它影響角色的生命值就不會發(fā)生改變了眠屎。

那么哪些操作會改變Base值,哪些會改變Current值呢肆饶?打開一個Gameplay Effect改衩,然后點擊Duration Policy,可以看到有三種模式驯镊,其中Instant改變的是Base值葫督,Infinite和Has Duration改變的是Current Value,因為某種意義上這兩個效果是有持續(xù)時間的板惑。但是Duration policy的特殊情況橄镜,當它存在period的時候,它改變的同樣是Base值冯乘,因為Period Duration可以理解為每一個period觸發(fā)一次的instant洽胶。
1.PNG

創(chuàng)建完畢后,記得需要給予MoveSpeed Attribute一個初值裆馒。
2.PNG

實現(xiàn)Sprint技能

創(chuàng)建Gameplay Ability命名為GA_Sprint姊氓,作為加速跑技能丐怯。創(chuàng)建Gameplay Effect命名為GE_Sprint_SpeedUp負責提高移動速度。
3.png

打開GE_Sprint_SpeedUp翔横。技能效果為永久(Infinite)提高MoveSpeed屬性2000读跷,同時需要給該GE添加Tag為Ability.Sprint.SpeedUp
5.PNG
5.1.png

然后打開GA_Sprint。Sprint的流程為對擁有該技能的角色申請一個GE禾唁,就是剛才我們創(chuàng)建的那個舔亭。然后等待Gameplay Event,這個事件帶有標簽Ability.Sprint.EndAbility蟀俊。接收到時間后钦铺,移除帶有Ability.Sprint.SpeedUp標簽的GE,然后結(jié)束能力肢预。
4.PNG

打開角色藍圖矛洞。

添加能力(Give Ability),綁定輸入烫映。這里當shift松開后沼本,會向自己發(fā)送一個Gameplay Event,帶有標簽Ability.Sprint.EndSprint锭沟。這就是在能力中等待的事件抽兆。
6.PNG

MoveSpeed Change Delegate

打開CharacterBase.h/cpp,然后創(chuàng)建function

void OnMoveSpeedAttributeChanged(const FOnAttributeChangeData& Data);
復(fù)制代碼

實現(xiàn)族淮,當接收到發(fā)生改變的Attribute后辫红,改變MovementComponent的MaxWalkSpeed,注意祝辣,這里不能直接通過GetCharacterMovement()修改移動速度贴妻。

void ACharacterBase::OnMoveSpeedAttributeChanged(const FOnAttributeChangeData& Data)
{
    UCharacterMovementComponent *MovementPtr =  Cast<UCharacterMovementComponent>(GetCharacterMovement());
    MovementPtr->MaxWalkSpeed = Data.NewValue;
}
復(fù)制代碼

然后在BeginPlay中將該function與MoveSpeed的Change Delegate綁定。

void ACharacterBase::BeginPlay()
{
    Super::BeginPlay();

    if(AbilitySystem)
    {
        AbilitySystem->GetGameplayAttributeValueChangeDelegate(UAttributeSetBase::GetMoveSpeedAttribute())
        .AddUObject(this, &ACharacterBase::OnMoveSpeedAttributeChanged);
    }
}
復(fù)制代碼

響應(yīng)Attribute的改變

剛才實現(xiàn)的相應(yīng)Attribute改變實際上發(fā)生在屬性值已經(jīng)改變后蝙斜,但是我們處理最大生命值名惩,生命值不能小于0等事件不適合在角色代碼里實現(xiàn),實際上GAS系統(tǒng)提供了接口可以在屬性值發(fā)生改變前進行處理孕荠。

重寫兩個方法娩鹉。PreAttributeChange負責在屬性值的Current Value發(fā)生改變前進行處理。PostGameplayEffectExecute發(fā)生在Base Value發(fā)生改變前稚伍。

virtual void PreAttributeChange(const FGameplayAttribute& Attribute, float& NewValue) override;

virtual void PostGameplayEffectExecute(const FGameplayEffectModCallbackData& Data) override;
復(fù)制代碼

我們可以在這里設(shè)置屬性值的范圍弯予。比如下圖的處理就可以讓生命值保持在0到100之間。

void UAttributeSetBase::PostGameplayEffectExecute(const FGameplayEffectModCallbackData& Data)
{
    Super::PostGameplayEffectExecute(Data);

    if(Data.EvaluatedData.Attribute == GetHealthAttribute())
    {
        SetHealth(FMath::Clamp(GetHealth(), 0.0f, 100.0f));
    }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末槐瑞,一起剝皮案震驚了整個濱河市熙涤,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌困檩,老刑警劉巖祠挫,帶你破解...
    沈念sama閱讀 210,978評論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異悼沿,居然都是意外死亡等舔,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 89,954評論 2 384
  • 文/潘曉璐 我一進店門糟趾,熙熙樓的掌柜王于貴愁眉苦臉地迎上來慌植,“玉大人,你說我怎么就攤上這事义郑〉粒” “怎么了?”我有些...
    開封第一講書人閱讀 156,623評論 0 345
  • 文/不壞的土叔 我叫張陵非驮,是天一觀的道長交汤。 經(jīng)常有香客問我,道長劫笙,這世上最難降的妖魔是什么芙扎? 我笑而不...
    開封第一講書人閱讀 56,324評論 1 282
  • 正文 為了忘掉前任,我火速辦了婚禮填大,結(jié)果婚禮上戒洼,老公的妹妹穿的比我還像新娘。我一直安慰自己允华,他們只是感情好圈浇,可當我...
    茶點故事閱讀 65,390評論 5 384
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著靴寂,像睡著了一般汉额。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上榨汤,一...
    開封第一講書人閱讀 49,741評論 1 289
  • 那天蠕搜,我揣著相機與錄音,去河邊找鬼收壕。 笑死妓灌,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的蜜宪。 我是一名探鬼主播虫埂,決...
    沈念sama閱讀 38,892評論 3 405
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼圃验!你這毒婦竟也來了掉伏?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,655評論 0 266
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎斧散,沒想到半個月后供常,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,104評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡鸡捐,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,451評論 2 325
  • 正文 我和宋清朗相戀三年栈暇,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片箍镜。...
    茶點故事閱讀 38,569評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡源祈,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出色迂,到底是詐尸還是另有隱情香缺,我是刑警寧澤,帶...
    沈念sama閱讀 34,254評論 4 328
  • 正文 年R本政府宣布歇僧,位于F島的核電站图张,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏馏慨。R本人自食惡果不足惜埂淮,卻給世界環(huán)境...
    茶點故事閱讀 39,834評論 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望写隶。 院中可真熱鬧倔撞,春花似錦、人聲如沸慕趴。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,725評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽冕房。三九已至躏啰,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間耙册,已是汗流浹背给僵。 一陣腳步聲響...
    開封第一講書人閱讀 31,950評論 1 264
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留详拙,地道東北人帝际。 一個月前我還...
    沈念sama閱讀 46,260評論 2 360
  • 正文 我出身青樓,卻偏偏與公主長得像饶辙,于是被迫代替她去往敵國和親蹲诀。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 43,446評論 2 348

推薦閱讀更多精彩內(nèi)容