• 🏆 Texturing Contest #33 is OPEN! Contestants must re-texture a SD unit model found in-game (Warcraft 3 Classic), recreating the unit into a peaceful NPC version. 🔗Click here to enter!
  • It's time for the first HD Modeling Contest of 2024. Join the theme discussion for Hive's HD Modeling Contest #6! Click here to post your idea!

[Trigger] Simple Damage Redistribution

Status
Not open for further replies.
Level 22
Joined
Jul 25, 2009
Messages
3,091
I have a squad system, the members of the squad are unselectable and locust units via a system I created with the insight of Fingolfin.

It's a standard squad system, all units are tethered by their custom values.

Ie, the leader has the same custom value of all members.

I want to redistribute the damage from the members to the squad leader.

If a squad member takes damage the leader takes the damage instead.

I'm not sure if I should do this with a checking loop, or a DDS? Or something more efficient. Right now I'm using a loop but it does not function properly.

Once the squad leader's hp drops below a certain threshhold, it will trigger the death of a squad member.

Example: Squad leaders health is 300, squad size is 3. Once the leader's health drops to 200, the squad size is reduced to 2, once it drops to 100, the squad size is reduced to 1 (just the leader remains).

This will make the squad system work exactly the same as in Dawn of War 2, where the health of the leader represents the health of the entire squad.

I've already devised a mathematical formula for removing member once the threshhold is reached, but it's not accurate enough, in the 300 HP example, the first threshhold is 198 instead of 200 and the second threshhold is 99 instead of 100.

  • Set GPercentage[GNumber] = (100.00 / (Real((Point-value of (Trained unit)))))
This sets a percentage to 100.00 / Squad Size (Point Value)

So 100.00 / 3 = 33.33

  • (Percentage life of GLeader[(Custom value of (Picked unit))]) Less than or equal to (GPercentage[(Custom value of (Picked unit))] x (GCurrentSquadSize[(Custom value of (Picked unit))] - 1.00))
This checks if the leader's hp is below the threshhold by checking if it's less than 33% * The Current Number of Squad Members - 1 (I deduct one to account for the leader)

  • Then - Actions
    • Set TempUnit = (Random unit from GSquadMembers[(Custom value of (Picked unit))])
    • Unit Group - Remove TempUnit from GSquadMembers[(Custom value of (Picked unit))]
    • Set GCurrentSquadSize[(Custom value of (Picked unit))] = (GCurrentSquadSize[(Custom value of (Picked unit))] - 1.00)
    • Unit - Kill TempUnit
This will remove the unit from the squad completely (after the threshhold is reached)

I will also need to be able to detect when health is regenerated so that I can add squad members back to the squad after the leader's health reaches the same 200 and 300 threshholds.

If you can help with any of these 3 issues chime in.
 
Level 12
Joined
Jan 2, 2016
Messages
973
In my opinion a DDS is needed for this to work. I'd advise you to use a more advanced one (like Bribe's), that can block the damage, unless you want to trigger the damage block yourself.
So when a unit takes damage - block it, and instead - damage the leader.

I'd also advise you to "tie" things up into a hashtable. Make a unit group, with the leader's squad, and save the group's handle into the leader's hashtable, and save the leader's handle into each of the units' (in the group) hashtable. This way references will be easier. You can also avoid using the units' custom value.

And about the regeneration - you should run an event every 0.25 seconds, that's checking the HP of each leader, and adding/removing units from his squad.
 
Last edited:
Level 22
Joined
Jul 25, 2009
Messages
3,091
I used Bribe's DDS initially, however I encountered a problem with the indexer in that, it uses custom values, so I can't index the squad members and the squad leaders together because the DDS can no longer properly detect damage if there is more than 1 unit on the map with the same custom values.

I'm thinking why not just have the check for HP run on a loop and cover both regenerating and removing members from squads, since I'll need a loop for gaining HP anyway.
 
Level 12
Joined
Jan 2, 2016
Messages
973
I'd also advise you to "tie" things up into a hashtable. Make a unit group, with the leader's squad, and save the group's handle into the leader's hashtable, and save the leader's handle into each of the units' (in the group) hashtable. This way references will be easier. You can also avoid using the units' custom value.

Or you can just use a hashtable instead of the units' custom values?
This can help you if you don't know how to use hashtables.
 
Level 7
Joined
Oct 19, 2015
Messages
286
Using a loop is fine for creating/destroying squad members, however you need damage detection in order to properly prevent damage. If you try doing that with a loop, you run the risk of a squad member dying between two loop updates if it takes too much damage at once.

Also, checking the life of all squad members all the time is inefficient, since most units probably won't take damage between most loop updates. Of course, using a damage detection system also has its cost, but in all likelihood it will be lower.
 

Bribe

Code Moderator
Level 50
Joined
Sep 26, 2009
Messages
9,456
Hashtables are fine, but if it's just about attaching data to a unit, an indexer for the custom value is faster, more readable, gives you access to onIndex/deindex events and GetUnitById.

Look at Unit Event, Knockback 2D, IsUnitMoving, Heal Event or Damage Engine. They have readable array variables to give the user more functionality. IsUnitMoving[(Custom value of Unit)] is straightforward syntax. IsUnitAlive[(Custom value of Unit)] is another really good one as GUI doesn't gove you access to UNIT_TYPE_DEAD nor a postprocessor-added UnitAlive native.
 
Level 22
Joined
Jul 25, 2009
Messages
3,091
I have solved this issue by using a custom value array style indexer, (it's the one included in the DDS I'm using, dunno who actually made it) and creating a single 0.03 that loops through all squad leaders and checks their hp and squad size to determine whether or not to remove or add members to the squad.

I added my own half ass DDS that just adds the amount of damage dealt back to the unit as HP, and redirects the damage taken to the leader, without an indexing or complex damage blocking and it works fine.

And the loop is inefficient yes, but it doesn't leak and hypothetically I can figure out a way to shut it off when all units on the battlefield are above their designated threshhold.

Tl;dr I seem to have finished the system myself you can close this thread.

Oh and a sidenote I am using the "IsUnitMoving" function for another system, so props.
 
Status
Not open for further replies.
Top