Page 1 of 1

Creating a Standard - Unit Status Effects

Posted: 17 Mar 2012, 09:18
by UberWaffe
What this aims to do:
1. Flesh out what basic supporting code for unit status effects is required.
2. Create a standard approach

What this does not aim to do:
1. Dictate what status effects can/cannot do
2. Dictate personal preference to coding

Status effects? What are you talking about?
Examples might be the best at explaining this.
From Total Annihilation: Unit paralyzed. (Yes, handled differently in code, but concept applies).
From Spring Games (That I know of): Slowed in The Cursed, On fire in ZK. Sprinting from CT.
From Command and Conquer Generals: Infantry being poisoned, on fire, or irradiated.
From Yuri's Revenge: Being mind-controlled. Building being disabled due to low power.
From Supreme Commander: Unit being disabled by EMP.
Other possible uses I can think of: Infantry suppressed by heavy machine gun fire (Spring 1944). Unit hunkering (stops movement + shooting, heals X per second).

Why do I need this?
Well, you don't. Not really. This falls more under the category of ease of use than currently impossible to implement.

So then why mention it?
I had noticed that several games had effects and code that basically boiled down to status effects. For example, being on fire in ZK. Being slowed in The Cursed. I even remember a thread mentioning something similar to mind control (unit changes sides until capturer dies).
All of these have some commonalities in place, in that they translate some initial/re-iterating/finishing effect to a unit, and require some associated values to be attached to the unit.
So this aims more at creating a re-useable approach to the underlying mechanic (effect to unit link) than the actual effects themselves.

Okay, so what do you want?
Goal: creating the basic mechanics in either lua or the engine + lua. (Similar to how custom commands can be made).
Current milestone: decide on what the basic mechanics entail, and where to implement it.

Anything more than hot air to add?
Currently I have committed to helping Sanada on CT with some lua scripting. Help me learn as well. So these initial thoughts are not overly technical/code-like, nor final or fixed in any way.
Also, I'll be glad to help on this once I am finished with some of my current commitments on CT. Just don't want to split my attention away from CT entirely.

The effect class:
Variables:
effectID - Similar to unitID, this is the ID of the effect.
effectDefID - Similar to unitDefID, this is the ID of the specific effect type.
unitID - Unit that this status effect is attached to.
duration - Number of seconds this effect still has left before expiring. (Infinite duration can be achieved by simply specifying massive durations 9999999 seconds, or implementing a special handling, like -1 duration equals infinite, or a boolean that marks this effect as infinite)
params - Parameters to store for this effect, such as magnitude, or perhaps unitID of another unit, or whatever is required by the lua programmer of that specific effect. (Think of params on custom commands).
Possibly (down the line at least) also a means of attaching a graphic to the effect (such as little "I-am-stunned" stars)... but eh. For now at least I'd skip this.

Functions: (Mostly triggers. Lua coder for specific effect can then code what should happen in these.)
EffectOnCreate() - Triggered when the effect is first applied to a unit.
EffectOnEnd() - Triggered when the effect's duration runs out.
EffectOnSlowUpdate() - Triggered each game slow update.
EffectEnd() - Ends the effect if called, regardless of duration left.
EffectUpdate() - Can update variables attached to effect, such as duration, params (maybe even unitID, but I think ending the effect and creating it on the other unit would be better, so that OnCreate() and OnEnd() trigger properly).
EffectGetUnitID() - returns the unit ID it is attached to.
EffectGetDuration() - returns the duration left until expiring.
EffectGetParams() - returns the parameters.


Effect handler class:
Variables:
activeEffectsTable - Table of all effects that are active.

Functions:
CreateEffect() - Creates a new effect and attaches it to a unit, along with duration and params.
EndEffect() - Triggers the EffectEnd() function of the effectID specified.
UpdateEffect() - Triggers the EffectUpdate() function of the effectID specified.
FindAllForUnitID() - Returns all effects that have the specified unitID as its unitID.
FindAllForEffectDefID() - Returns all effects that have the specified effectDefID as its effectDefID.

This class would also iterate through all effects each SlowUpdate (or other) and decrement the remaining duration for each. It would call EndEffect() for any effect that expires (i.e. duration <= 0)


So, with this game makers/lua coders should be able to create any effect they please, without having to create the whole basic foundation again.

Anyway, that was my two cents on the matter. For now I simply wanted to post the idea so that some feedback can run on it.
If someone else with mega coding skills pulls this off in the meantime, I won't complain... too much. :mrgreen:

EDIT: spelling mistake. Also:
jcnossen:
- don't put up requests for a particular implementation of an idea if you aren't a game programmer.
I apologize for breaking the rule.

Re: Creating a Standard - Unit Status Effects

Posted: 17 Mar 2012, 16:10
by knorke
All those "effects" are lua gadgets and if they do not provide enough functionality you can edit them. Some stuff is even already done, eg the jumping gadget can call functions in the unitscript (like jumpStart, jumpEnd etc) so you can play animations. Generally those gadgets keep some table of affected units and if you want to share it between wupgets you can do so in various ways.
Why would you want to use some generic EffectOnEnd() function name instead of jumpStart()?
If you want some standardization for gadgets I think the only way is to make such gadgets ;)
Or are you looking for something like http://springrts.com/wiki/Lua_System#LuaRules_only ? It can basically store per-unit variables that wupgets can read. (settable who can read it)

Re: Creating a Standard - Unit Status Effects

Posted: 17 Mar 2012, 17:37
by Google_Frog
Are you suggesting that something like this should be added to the engine? I think that is a bad idea. Try to use the tools before inventing new standards. I have coded a lot of lua stuff and would not find the extra status effects useful. All the callins are much easier done with lua directly and you have missed a few that I use.

The createEffect <-> effectCreated pairs start and end in lua. Why does the engine have to be between. The update functions are easy to do in GameFrame. Many current implementations of effect <-> unit tables are only iterable in one direction because in that case bi-directional is not required.

As for standardisation within lua land. I make new stuff and keep to a lose personal standard, I do not want to be stuck in meetings to decide such standards. The closest standard piece of lua is probably the attributes gadget that car produced originally and I improved. This gadget provides a simple interface for other bits of lua to multiply buildpower, reload rate or unit speed. It deals with conflicts between different speed modifications by multiplying the incoming speed change requests instead of multiple gadgets handling those requests themselves.