nosoop / SM-TFAttributeSupport

A SourceMod plugin that improves support for official TF2 attributes.
GNU General Public License v3.0
12 stars 4 forks source link

"add_onhit_addhealth" and "heal_on_kill" do not function correctly with negative values #5

Open SoulBlast35 opened 3 years ago

SoulBlast35 commented 3 years ago

"selfdmg on hit for rapidfire" has been in items_game.txt for a long while and uses the same attribute class as the old heal on hit attributes. Unlike "health regen"/"health drain", it does not work with a negative value. Applying a negative health on hit value causes you to heal +3 HP every hit for some reason. Heal on Kill shows a negative healing value on the HUD on kill, but does not actually subtract neither add health. Not sure if this is high priority or not.

nosoop commented 3 years ago

According to disassembly of newer game binaries, the new behavior is intentional — it specifically sets healing to 3 if the raw_damage_ratio = actual_damage / base_damage is less than 0, or if add_onhit_addhealth * raw_damage_ratio is less than 3. Provided add_onhit_addhealth is non-zero, of course.

There's no handling in place to maintain negative values before the second condition is checked, unfortunately. I'm not sure which items expect this behavior for add_onhit_addhealth so there may be unexpected consequences if the second check is bypassed.

The alternative is to jump into custom assembly in the middle of the function to modify the values within the registers. That's feasible, but not something I'd want to maintain for free in the long run.

SoulBlast35 commented 3 years ago

Ah I see. I only ask this because I remember seeing on one of the early versions of that god awful 30 Waves missions on some community MvM servers, there was a pyro robot on Wave 14 called the "Headless Ghost Pyro". The idea was it was invincible, had a monumental amount of health and had a constant slow health drain, but if it killed someone, it'd lose a big chunk of health on kill. This thing never worked and always softlocked the mission, mainly because the health drain would cause damage force that would proc the on hit uber effect and cause them to float in the skybox and never leave spawn. It does baffle me why there's a self damage on hit attribute and yet the attribute class is coded to prevent negative values, though.

nosoop commented 3 years ago

The previous iteration (prior to Jungle Inferno, also reflected in the code leak) didn't clamp the add_onhit_addhealth value, so the attribute originally indeed could damage the owner on hit if the value was negative. The code that handles dealing damage when it's negative is still there, actually — it's handled separately from being healed.

Probably a change oversight on Valve's part since selfdmg on hit for rapidfire isn't used in any official weapon.