Ask about ACS, DECORATE, ZScript, or any other scripting questions here!
Moderator:GZDoom Developers
Forum rules
Before asking on how to use a ZDoom feature, read the ZDoom wiki first. If you still don't understand how to use a feature, then ask here.
Please bear in mind that the people helping you do not automatically know how much you know. You may be asked to upload your project file to look at. Don't be afraid to ask questions about what things mean, but also please be patient with the people trying to help you. (And helpers, please be patient with the person you're trying to help!)
native int ApplyDamageFactor(Name damagetype, int damage);
native static int ApplyDamageFactors(class<Inventory> itemcls, Name damagetype, int damage, int defdamage);
Last edited by Major Cooke on Fri Mar 03, 2017 3:05 pm, edited 1 time in total.
Major Cooke wrote:You haven't really told anyone what you wanted.
Ed the Bat wrote:Am I able to change type-specific DamageFactors for an actor, so as to modify only how much damage certain types, or "elements", will do to the actor?
override int DamageMobj(Actor inflictor, Actor source, int damage, Name mod, int flags = 0, double angle = 0)
{
if (mod == "HologramDmgType") return 0;
// Don't negate stuff if it's telefrag-esque damage amounts.
if (damage < TELEFRAG_DAMAGE)
{
// Reduce by 1% for every megasphere we've picked up.
// DoomDoll does not give this bonus.
int pc1 = Clamp(CountInv("D4MegasphereDamageReducer"),0,25);
if (pc1 > 0)
{
damage = Max(0,damage * (1 - (0.01 * pc1)));
}
}
return Super.DamageMobj(inflictor, source, damage, mod, flags, angle);
}
"mod" is the damagetype.
Last edited by Major Cooke on Fri Mar 03, 2017 3:14 pm, edited 1 time in total.
Major Cooke wrote:
And because of your ninja edit, yes, it's fully possible to make your own kind of look function. Bear in mind, mine doesn't do natural monster searching -- it only goes by TIDs.
Well a custom look function would cut all the crap with Thing_Hate I am using right now, I could make two types of monsters, and each would only target the TID of enemy. Anyway, for now I am sticking with Thing_Hate, I just had a small problem with spawned actors mid battle who did not know who to attack, but it's solved. Super crap method - just change them tid to temporary number 45, ask them to hate tid of -10, and change tid back to original. And yes, this are TID's I use.
Thanks for the code!
Anyway... I guess I can give that method a try. I just wish setting DamageFactor <type> was as simple as setting an actor's 'global' DamageFactor (i.e., DamageFactor=<number>;)
@Krokots: Just an FYI, I only did a TID search because A_Look is useless in my mod itself with team oriented goals, not to mention same-actor entities running all over the place. But the thing is, just check and find a target and then search for other targets via nearby allies. You always have things like iterators to help out.
@Ed: You can, if you use global variables. You still have to edit DamageMobj and apply it on all actors but it's only one place to have to edit it.
Last edited by Major Cooke on Fri Mar 03, 2017 3:21 pm, edited 1 time in total.
I've looked at the global variables thread. I'm really not seeing anything in it that would let me edit an actor to give him, for instance, DamageFactor "Fire",2.0; after he's already been created.
I saw the word "global" and thought you meant all actors, not just one.
In a way, you could kinda do it, individually still.
On (Post)BeginPlay, have two dynamic arrays set up: one for strings, one for floats. Then have the DamageMobj function run through those and compare. Put those in the global actor scope, mind.
EDIT: Fuck. I forgot strings and names don't mix well, last I checked. Could be wrong though, so give it a shot.
When I said 'global', I meant the "DamageFactor" property that applies to all damage types. That can be modified by simply saying DamageFactor=<number>; (as I thought I made clear with how often I say this). But again, that will apply to all types, not just "Fire", as per the example. So it's not a solution.
But it sounds like there's no simple or direct way to modify type-specific DamageFactors. I'll take what I can get, though, so next time I'm at my desk I'll see if I can make something of your suggestions.
In that case you just modify the Damage directly inside the function. Just take the guts out of what I had in my example and inside the passed telefrag check, add:
Note that the call to Super.DamageMobj will still apply damagefactors though. If you want absolute control without weird mash-ups you'll have to throw out all damagefactors and manually do them yourself. You will have to call Super.DamageMobj in order to kill something sanely. Or if you just want something simple like that and allow the damagefactors to be processed normally, the super call can also work as is after the damage change above, without throwing the damagefactors out.
Is there a way to just get the number for an actor's damagetype-based damagefactor?
I've got a fire actor that damages 1 point every couple tics for a set duration. If this is subject to a damagefactor of less than 1, it just rounds down to zero and the victim ends up taking no damage at all. I want to access the number so that the duration of the fire would be reduced instead of the amount of damage.
Nash wrote:Alright, noted... just how expensive is calling the global thinker, by the way? Since the code only does the Init once and never again after that...
It still uses a ThinkerIterator to retrieve the global object after it's been Init'd. There's that plus function call overhead, which currently isn't cheap in scripting-land. Something worth keeping in mind if this function of yours is meant to be called many times in a loop.
Here, the same applies as for every piece of code. If you can store the result of a costly operation in a local variable, do so. It may not register directly as performance loss but it will add up if done repeatedly.
So if I were to only retrieve the global thinker once per level load, and then do all real-time operations on - let's say - some dummy/temporary object I spawn in the world. And on every level change, just synchronize the variables together by copying the variables to/from the temporary object to the global thinker. Would that be better for performance?
Asking first before I actually do because this is a little complicated for my skill level and I don't want to waste time trying to do it when it won't bring me any benefit.