Best way to implement a buff/debuff system

Im working on a RTS game where units can apply different buffs/debuffs to each other.

Im just wondering what the best approach to this problem would be in terms of scalability and performance.

Buffs and debuffs may come in instant effects or effects over time (e.g decrease attack for a given duration or apply burn damage over time for a set amount of time and so on)

Suggestions are greatly appreciated, more than happy to provide further details upon request… many thanks.

(I made a few attempts at tackling the problem my self but not really satisfied with the result as it quickly became too messy)

1 Like

i dont know about ‘best’

but i like actor components, they make sense since a buff will be ‘attached’ to an actor but also, they’re replicated, can handle their own logic like durations and can bind to events or be bound to.

2 Likes

I thought about using that but wouldnt actor components also bring alot of ‘dead weight’?(useless variables and functionality that i wouldnt use which would impact performance when scaled up).

well consider your options,

cheapest would be a struct but then how would you handle trigger effects like DoTs or events.

objects would be nice but would have to be custom created in c++ for replication etc

everything else is more expensive than components? im curious what other people think too?

keep in mind if using inheritance there shouldnt be any dead weight on components

2 Likes

Components support inheritance, so little to no dead weight. Works pretty well, imho. And this is not what will impact performance. Unless used in a totally whack way, ofc.

1 Like

I thought bp components would have lifespan but from what i can see, that doesnt seem to be the case. So would you say pass in a duration float variable on spawn. Then on event begin play create a timer by event function which destroys the bp component?

1 Like

well you want them to be modular since your using inheritance. so you may create 2 events in the base, activate and deactivate.

in the child you could start the timer on activate and destroy itself on deactivate. or dont destroy it, just go inactive, this may be more performant.

you could have a few generic variables, level, strength, time, maxstacks etc.

Sorry im a little confused, when do we call activate? (and where from).

And when you say start the timer on activate, do you mean timer by event? (which would call deactivate?)

so that comes back to how do you want to apply the effect, id use an interface or manager component. so for instance when you damage an enemy you ‘apply burning damage’ so you’d call the interface for ‘add debuff’ this is where you’d create the component and/or ‘activate’ the component.

activate does whatever you want it to do, meaning whatever you override in the child component. for instance instant effects wont use a timer, so you call whatever you want to call on that and then end the effect which calls deactivate.

of course there are many ways to do what you want, this is just 1 idea

1 Like

Yeah, I had decided to use an ‘EffectManagerComponent’.

So heres what i got so far:

Unit calls ApplyEffect (passed struct with all data needed) function on target Actor (any oppositional unit) (Through an interface called effectable).

The unit on the receiving end calls the same function on its ‘EffectManagerComponent’ and passes on the struct.

The EffectManager figures out what type of effect it is (what specific debuff or buff it is), checks if we should apply the effect (units have accuracy and resistance; which work against each other) and then finally creates the specified EffectComponent to its owner and stores a ref to the effect in an array.

Does that look about right to you?

Also would you recommend i feed in the debuff strength to the specific buff/debuff component on spawn (Instance editable and expose on spawn variable) or just call a set on the variable after it is created?

Thanks for all the advise so far!

sounds good!

yeah you could add to the struct the ‘strength/level’ of the effect if you use that in your game since the enemy is what sets that

1 Like

Excellent… Thanks alot for your time!

1 Like

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.