How would I do something like playing an AnimMontage across on server and all clients?
I had a look at the NetExecutionPolicy and none of them multicast.
Also in the AbilitySystemComponent there is no MulticastTryActivateAbility function.
Am I meant to create own custom event to multicast or something?
EDIT: Tested the multicast out but it seems that ActorInfo is not getting replicated properly. I have the settings:
With the montages I want to get melee weapons working so I believe the minimum I will need is:
Make a GameplayAbility_PlayAttack (play an AnimMontage)
Make a GameplayAbility_DealDamage (call ApplyGameplayEffectToOwner)
Make a GameplayEffect_DealDamage (adjust Health attribute)
Make an AttributeSet with Health
And when I overlap an enemy with my weapon I will activate GameplayAbility_DealDamage.
Currently having issues now with my health not replicating in my AttributeSet.
I’ve set it up so I can decrease my health, but the change is only visible on the server and the value doesn’t get replicated to clients.
This is what I’ve done so far:
Made a custom AttributeSet with Health set to replicated
Made a GameplayEffect_DealDamage which minuses 10 from the Health attribute
Made a GameplayAbility_HitSelf with (NetExecutionPriority=ServerOnly) which calls GameplayEffect_DealDamage
BeginPlay on all characters: if HasAuthority() call AbilitySystem->InitStats
Call GetFloatAttributefromAbilitySystemComponent every tick to check what my health is
Checked my AbilitySystem component is replicated and my health attribute is replicated
EDIT: Just realised I completely forgot about AbilityTasks, which is I’m guessing is what PlayMontageAndWait is? Better try making one of those too.
EDIT*: The duration on my GameplayEffect was the problem. Changing this from Instant->Infinite fixed it.
EDIT**: While Infinite did fix the replication it doesn’t make any sense to use it when applying damage. It also screws up some things in the AttributeSet like PostGameplayEffectExecute checks. Still stumped on why replication isn’t working.
You do not need to set attributes to replicated. The system does this automatically for you, last I checked. Or at least it synchronizes attributes so long as you don’t head too far off into unconventional methods of doing things.
A character should init its ability system regardless of if they’re client or server. It’s the act of giving abilities that should be server-only, everything else can and likely should be done for everyone.
PlayMontageAndWait is an ability task, yes. It will report back to the blueprint when the montage has finished, has been interrupted or some toher such thing. These kinds of asynchrous exec paths are usually a telltale sign for soemthing being an Ability Task.
I am unsure why your attribute wouldn’t replicate either way though. Are you going through GameplayEffect modifiers as intended? Weird stuff happens when you try to change an attribute directly, and I believe modifiers without a gameplayeffect need to be sent through the network manually as well… or was that tags?
Anyhow, GameplayEffectExecution section in the OP is up. Fellas, today we will learn about using a GameplayEffectExecutionCalculation as global damage calculation for all kinds of effects and abilities to enjoy. Next lesson will be Gamepaly Events, it’s 7pm and I can’t be arsed to write all this stuff down in one session, either way.
Thanks for t he follow-up. The attribute capturing is EXTREMELY interesting, and extremely useful. Again, as discussed this whole system seems to be a bit overkill since I have a very similar underlying system in the works sans the replication support, but I will definitely be checking out how they’ve done the macro-based attribute capturing and see if that’s something I can implement. Since all of my combat attributes are based on GameplayTags as of yesterday, it’ll probably be easier to set up.
Ok so I’ve finally got my attribute set working by copying the AbilitySystemTestAttributeSet included in the engine. I’m not sure if I had to do this because I setup something wrong. So can anyone can confirm this?
Setup is as follows:
Make an attribute set with a float value
Make a gameplay effect that adjusts the float value, duration policy set to Instant
Make a gameplay ability which calls the effect, running on server only
According to my testing, your float value inside your attribute set should get adjusted on the server and not replicate to clients
To fix this I had to do this inside my Attribute Set:
Tag my variable as Replicated
Add the GetLifetimeReplicatedProps function as below.
And also include “Net/UnrealNetwork.h” for the DOREPLIFETIME macro.
If it didn’t compile properly, check the AbilitySystemTestAttributeSet class included in the engine which I used for reference.
EDIT: Found this post about replication settings when you want to run predictive calculations.
Huh, you’re right. Weird how I missed that. Did I forget about something? …
I’ll probably add the solution to the OP when I find it. Yours will likely work because you just replicate the float for the attribute directly(and the attribute set seems to already have replication through owner actor partially built in), but I’m not sure if that has any implications beyond that. There might be a macro or a hidden variable needed to be called as well, you never know.
Now that I check some more, I also notice that local-predicted timed gameplay effects can be funky for me modifier-wise. So it’s not just instant modifiers I guess, unless I’m dumb.
It’s weird too, this seems to happen with abilities regardless if they’re server-only or not for me(client will change for a frame and then snap back to its starting value for me), and only modifiers seem to be funky like that. This isn’t mentioned in the github sample project either. Coulda sworn this worked out of the box in that. Guess it isn’t quite as automatic after all…
Probably an easy fix when you find the intended solution, but, heh, that’s always a little difficult with this system.
In the sample code in the AbilitySystem plugin the attributes are replicated directly. See AbilitySystemTestAttributeSet.h and cpp. I’ve always assumed that if you’re doing a networked game you should follow that model.
Other good references in there are AbilitySystemTestPawn.h and GameplayEffectTests.cpp. I would encourage anyone looking into this to peruse all of the source code in \Engine\Plugins\Runtime\GameplayAbilities. There is some decent documentation in the comments of the code. I’ve made some pretty extensive changes to the system to support turn based and round based abilities and it has been surprisingly easy to modify.
Also I would recommend inheriting your pawn from IGameplayCueInterface as well in order to get the cue notifys to work with it.
KZJ - It looks like your “example github project” link is broken in the OP.
“attributes are replicated directly” I think this is true as long as the UExampleAttributeSet is replicated. Isn’t it?
I bet you need to tell the container (AttributeSet) to replicate in order to have the full mechanic replicated. Its just a guess.I had no time yet to play with this but I wish !!!
Half of those examples are severely, extremely outdated and/or partially incomplete/too simple, though, so I figured perhaps the system changed until then. It wouldn’t be the only thing that changed, frankly.
I assume this would allow you to activate GameplayCues without going throguh either a GameplayEffect or a GameplayAbility? Because those cues work without this interface(as long as the Ability System interface is implemented, anyway). It probably will not hurt to inherit the interface either way, but what exactly does it do?
No it isn’t, I just checked. However, you need to be logged into your github account, which should be linked to your Epic account to be eligible to access the UE4 source code. That is because the Gameplay Abilities Sample project comes with a version of the engine in one package, and as such it is private to anyone not within the Epic games group on github. It’s a bit roundabout, but at least you have an engine version guaranteed to work with the project. I guess.
This example project is from, one of the authors of the Gameplay Ability module, and while it is not yet complete and too simple itself(he said he works on it in his free time, so it isn’t an official example project per say. Well, not yet anyway. Maybe one day?), it is much more in-depth and up-to-date than the tests within the source overall, so it made sense to consider this project a better source than the source tests.
Anyhooow, so I set up replication on these attributes, with the little extra mentioned in the thread fpwong mentioned(creating an extra repnotify-function for each attribute is a huge pain in the posterior, by the way. I’d think just defining a macro somewhere specfically for the job would cut that work done tremendously fi you have a lot of attributes like me. Having to write a whole new function for every attribute sucks). Modifiers on timed/infinite GameplayEffects now seem to work perfectly as they should, but instant GameplayEffect modifiers still do not seem to do as they should when the ability giving out the GameplayEffect is set to execute locally for prediction, refusing to properly update every odd time(curiously, client and server resync every even attribute change. I don’t know). No prediction prompts the attribute change to occur correctly. This might not be related to attributes at all though, and it’s just a normal replication error that happens because I’m being retarded about it shrug.
Even more curiously, without the RepNotify function my attributes just wouldn’t update on my client at all.
This is really bizarre. I have the feeling we have set up the system differently. What are your results adding the RepNotify-function? Am I the fool with the wrong settings?
Not exactly sure what you mean by without the RepNotify but this is what works on my side.
OR simply
Can confirm running a modifier effect in a LocalPredictive ability does not act correctly. They skip PostGameplayEffectExecute and probably the other functions in your AbilitySet before snapping back to the server.
Also I cannot get a GameplayEffectExecutionCalculation in to work with a LocalPredictive ability.
Main issue is that Execute_Implementation never gets called on the client side.
I mean the OnRep function. I think blueprints call these repnotify function. May be incorrect though. ANYWAY:
Yeah, that one curiously does not work for me.
PostGameplayEffectExecute shouldn’t run after modifiers. They only run after an EffectExec has executed.
That being said, it’s strange because my localpredictive executions for health/damage/heals work perfectly for me, regardless of whether they’re local predicted, server-only, etc. This might be because I go through an extra attribute that isn’t actually Health and isn’t replicated directly, though(basically, I store potential damage in a HealthRemoval property first and then apply a modifier on health by that HealthRemoval property * -1. There’s no real benefit in doing this I don’t think).
I don’t know, I guess worst case I could try writing a message to one of the responsible heads behind the system and ask them how to handle attribute replication, and why instant gameplay effects behave so oddly. It’d be for a guide of a long undocumented system, so surely they would understand and help out if they have the free time required.
Before that though, I will finish the Gameplay Events section of this guide first.
Hmm have no idea why replicates doesn’t work, probably have to compare both attribute classes.
Does this mean you fixed this by adding an intermediate attribute? Cause that’s the problem I’m having.
Also how have you been setting initial attributes per character?
I’ve been trying InitStats which takes in a DataTable but I dunno what rows to set the DataTable.
EDIT: Checkout FAttributeSetInitter defined AttributeSet.h for initializing attributes.
EDIT*: Inside UAbilitySystemGlobals you set a GlobalCurveTable within your config file, along with a whole bunch of other config UPROPERTIES. You need to at minumum setup the GlobalCurveTable otherwise the FAttributeSetInitter will crash. Probably need someone to share their config file, seems like a huge pain to set it all up correctly.
Gameplay Event section is up. The art of triggering!
I think? This is the only thing I did meaningfully different in my own project than I did in this guide. It can’t hurt to try I guess. Do keep in mind though that even if you’re inside your attribute set, changing attribute floats directly past construction in the attribute set is a bad idea because other values will not update alongside it. As such, in your PostGameplayEffectExecution, do “GetOwningAbilitySystemComponent()->ApplyModToAttribute(FGameplayAttribute(FindFieldChecked<UProperty>(UMyAttributeSet::StaticClass(), GET_MEMBER_NAME_CHECKED(UMyAttributeSet, Health))), EGameplayModOp::Additive, -HealthRemoval)”, not “Health = Health - HealthRemoval”.
Setting them in my c++ character’s BeginPlay directly.
Something I perhaps forgot to mention is that you are required to link your github account with your Epic account to access it, due to being an entire engine version to go along with(and the engine source can only be downloaded from github if you accept to the terms of service by linking your account). Without the linking, the link will look like it broke, due to being inaccessible. Here are instructions on how to link your account. They’re a little basic, but eh, I think they’ll do.
I also corrected attribute replication instructions in the OP. Just throwing that out there for anyone reading.
First off, massive thanks for writing this guide. I’ve been looking through the sample and something that seemed interesting to me is that the projectile has no gameplay cue, instead having its visual effect tied to the projectile actor. This means if you turn on dedicated server and bump up net pktlag to 200 you’ll notice there’s a delay between attacking and the creation of the projectile. I’m curious if this is a standard approach, since my first thought would be to create a cue for the projectile and have the actor be only used for gameplay (onhit detection), as that would appear to fire the projectile immediately while keeping the server side checks for gameplay. A side effect of this would be that the actual location of the projectile might not match the cue in laggy circumstances with fast movement, but ideally the Actor would be able to notify the cue once it has spawned and replicated in order to correct its location. Has anyone tackled this kind of thing? Is the solution just to fudge it with animations and particle effects on the client side to distract the player so the projectile spawn lag is less noticeable?
The real solution for this is to spawn something on client side immediatly for a few milliseconds so the player saw something until the “real” server projectile actor is replicated. More, you may need to fix a delay on client side spawning if the ping is too high.
You can look at UT4 code to see how they dealt with this.
This is just a fake for the client to see “responsive action”, but all in all collision & explosion should be driven by server projectile.
Thanks, I hadn’t thought to look at UT4. Anywhere in particular I should start? In the time since posting this I actually had a look through GameplayPrediction.h and I think a suggested technique in there is to create the visual for the projectile immediately on the client, then destroy it once the actual projectile gets replicated via the ClientActivateAbilitySuceed RPC. I’m not sure how that works with something like a particle effect where timing is quite sensetive though.
Hey!
First, thank you so much for this post : amazing job!!
I’m having issue with Tag handling.
In a gameplay ability, I understand that if I say “ok, the one triggering this must posses a specific tag,if not, I’ll just don’t do it”
The problem that I’m facing is “How to I set a gameplay tag” on, per say, the BP_Hero in the example from .
To be working, must it implement the interface UGameplayTagAssetInterface ?
I’ve tried, in BP, the “Add Asset Tag” and “Add Granted Tag” but not working.
In dispair, I also tried to add a random GameplayTag variable but of course it didn’t work.