Overhealing vs. strictly healing past damage: fixing inconsistencies based off of intent order



  • Let's consider the following scenario:

    Creep A has 5 move parts and 45 non-boosted ATTACK parts, and creep B has 5 move parts and 45 fully-boosted HEAL parts. In two consecutive ticks, creep A attacks creep B twice, and creep B heals itself twice. What happens?

    This may seem like a simple question, but there are actually multiple possible outcomes, each approximately equally likely, depending on the order in which the HEAL/ATTACK intents are input into the database.

    Case 1: tick 1: heal->attack, tick 2: heal-> attack: First tick, heal does nothing, as creep B is at full health, and attack brings creep B down to half health. Tick 2, heal (now with half as many effective parts) brings creep B up to 3/4 health, and attack brings creep B down to 1/4 health.

    Case 2: tick 1: attack->heal, tick 2: attack -> heal: First tick, attack brings creep B down to half health, heal (now with half as many effective parts) brings creep B up to 3/4 health. Tick 2, attack brings creep B down to 1/4 health, heal (now with a quarter the parts) brings creep B up to 1/2 health.

    Case 3: tick 1: heal->attack, tick 2: attack-> heal: First tick, heal does nothing, attack brings creep B down to half health. Tick 2, attack brings creep B down to 0 health, kills it, and as creep B is now dead, heal does nothing.

    Case 4: tick 1: attack->heal, tick 2: heal-> attack: First tick, attack brings creep B down to half health, heal brings creep B up to 3/4 health. Tick 2, heal brings creep B up to full health, attack brings it down to half health.

     

    As you can see, this can cause complete inconsistencies, based purely off of the order in which intents are stored in the server's database between ticks.

    In the past few days, I heard about this from a few other members of the community, dissi and sheeo in particular were discussing it. To help fix this, I've made two different pull requests to the server's engine project on github which should solve this inconsistency. However, there's one question to be answered: should we allow heal parts to heal damage that occurs during the same tick as heal() is executed?

    This is a question because, in the current server, whether this is allowed or not completely depends on the order of 'intents'. In an effort to remove such pseudo-random behavior, we should choose one or the other: to either have heal operations only heal damage that existed the tick before the heal operation, or to have heal operations somewhat 'block' damage from occurring the same tick heal is executed.

    I don't know if there's one clear answer as to which way this should be done, but either way it will effect the balance of attacking/defending in this game. For this purpose, I've created this thread for discussion of the merits or disadvantages of allowing/disallowing 'overhealing'.

    Pull request allowing 'overhealing': https://github.com/screeps/engine/pull/15

    Pull request stopping 'overhealing': https://github.com/screeps/engine/pull/16



  • I am strongly in favor of "overhealing".

    Even if this mechanism exists, the healer still has to anticipate where the enemy will direct its attack.

    As things are currently, damage potential is too high which in many cases means instakill of units. This often times leads to rooms with active defense being "impenetrable" since active defenders dish out damage which cannot be countered.

    Overheal allows an attacker at least a small chance of success if he is able to systematically anticipate the defender's target.

    Kind regards,
    Atavus


  • Culture

    I'm in favor of overhealing as well, as it's not really overhealing in my regard, though I do see positive and negative issues with this:

    Overhealing pro's:

    • You first get damage and later you heal again.
    • If you heal at full health you still spend 0.2 CPU for that action.
    • Gets a chance to defend against 44A/6M boosted attack
    • Acts like damage blocking.

    Overhealing cons:

    • Hard to kill the creeps
    • No game does healing of incoming damage
    • Defence of a room will become much harder

    I'm very happy you made these pull requests, excellent work. It will make fending off invaders a whole lot more consistent as well.


  • SUN

    i'd say that if you don't allow overhealing, then that means that state from the PREVIOUS tick should be used when resolving, not state resulting from previous intents.
    THis means that in case 2 tick 1 for example, all heal parts would be able to heal, and not only those that survived the first attack intent.

    So I think there are 2 questions, should previous intent be able to influence results of following intents (in the same tick) and should the order of intent be dependent on player (order of) actions



  • To simplify the problem. This is how I think the game should treat heal/damage of a creep.

    Sum up all heal
    Sum up all damage
    Apply damage to hits
    Apply heal to hits

    If hits below 0 creep dies
    If hits above maxHits limit

    Tough parts are another important point. Imho the damage applied should be modified by Tough parts only so much as those Tough parts can absorb.



  • Balance wise right now -- I think we should allow healing to heal damage applied in the same tick. Otherwise defending seems too powerful. A 40-boosted ATTACK part creep will deal 4800 dmg/tick. This requires 15 ghodium-boosted TOUGH parts to tank -- if the defender has two such creeps in range, you need 30 of those parts, leaving only 10 slots in a T3 boosted creep for anything else.

    Either way -- both PR's are very important for fixing the currently broken damage system, where you need to build your creeps anticipating to tank two hits from any expected attackers, e.g. worst-case 19200 dmg from two melee defenders on ramparts -- effectively not tankable even with 50 x ghodium-boosted TOUGH.




  • For what is essentially a turn based combat system there definitely needs to be a fixed turn order. In my mind it should be  apply damage -> apply heals -> test if dead. -> next creep. 


    Over healing is fine imo as a mechanic it essentially balances itself. So you can pre-heal a creep that effectively loses you a tick of heal if there is DPS swap. Assuming the difference between heals and damage is close clever target swapping will still break a creep formations tank. All pre healing does is make it harder to alpha a creep. On top of this you would still need some way to workout if a creep makes a sensible target in the first place.



  • Just adding a response to Finndibaen:

    In both of the pull requests I made, all bodypart calculations due to healing/damage should be delayed until the end of the tick anyways. So with or without overhealing, it should work that way.

     

    With boosted TOUGH parts though: that is another consideration I had not accounted for in the pull requests I've now made, though I could add additional commits to allow for that. There's another question now though: if a creep has multiple dead boosted TOUGH parts, and it's both healed and damaged in one tick, should the damage or the heal apply first? I think this is another issue whether or not overhealing is allowed.

    If heal is applied first, that would mean some of the boosted TOUGH parts could be revived, and then those would block damage. If damage is applied first, that would probably mean that there wouldn't be any boosted TOUGH parts blocking damage (since they're all dead), and the creep would sustain more damage.



  • I am against "overhealing".

    This is because it breaks the normal rules of thumb and general practises of game development.
    Not only is it standard to apply damage first then heal.

    If body parts at the current work as command is executed on the tick. Then healing should occur same tick but it should be applied after damage.
    Else one should be defining what happens next tick and the heal should occur at the start of the next tick.

    Either way the idea of healing when there is no damage yet is in my opinion incorrect.
    It is the equivalent of trying to sow shut a stab wound you have not yet received. That is just not how the world works.

    Alternatively you can not kill the unit if enough healing is applied for them to survive damage - heal.

    At least that is my way of looking at it.

    - DeathTech

     



  • @deathtech the best games are those that defy conventions and Screeps is certainly an unconventional game.

    @dabross here I feel the middle path is the best. If we allow overhealing, then we should not allow tough parts to be revived.

    Apply damage
    Apply heal
    If creep still has hits it lives


  • SUN

    So lets approach this from the gamers POV during code time?

    on tick 1, player Y enters room with healer full health. since the information the coder has druing tick 1 is 0 damage to his creep, he wont order the heal on his creep within the next tick.

    on tick 1, player Z order tower to attack player Y's creep. damage will be allplied on the next tick.

    --

    on tick 2, player Y has the information on damage on his creep, he orders the heal on the next tick

    on tick 2, player Z orders another attack on player Y's creep. damage will be applied on the next tick.

    --

    on tick 3, we have the scenario of heal vs damage for the first time... in order of fairness, process all heal commands prior to all damage commands now. meaning, that all heals commanded on tick prior to the current one, apply the heal and then the damage gets added.

    there is no feasable way, for a "coder" to start guessing on whom to preemtivly heal, if the order was vice versa. Also, i believe that is common sense, that i would not order a heal on creep, that has full health (scenario in tick 1, could have preemtivly healed... but why would i? i dont even have the information of being damaged anyway...)

     


  • Culture

    Idea for healing issues:

    Some description:

     

    ATTACK – does 200 damage

    HEAL – does 100 healing

     

    Creep "BOB 1000/1000" – Bob has 1 heal part.

    The story will be over 2 ticks:

     

    Tick 1:

    Bob gets attacked for 200 damage

    Bob always does HEAL each tick

     

    Result of tick 1:

    [1] 1000 HP + HEAL = 1100

    [1] Max is 1000 HP

    [1] BOB has 1000 hp.

    [1] Bob gets 200 incoming damage.

    [1] 1000 HP – ATTACK = 800

     

    End of tick 1: Bob has 800/1000

     

    Tick 2:

    Bob gets attacked for 200 damage

    Bob always does HEAL each tick

     

    Result of tick 2:

    [2] 800 HP + HEAL = 900

    [2] Max is 1000 HP

    [2] BOB has 900 hp.

    [2] Bob gets 200 incoming damage.

    [2] 900 HP – ATTACK = 700

     

    End of tick 2: Bob has 700/1000

     

    This seems the most logical course of action

     

     

     



  • Summary: overhealing favors experienced attackers and favors siege offense.

    Requiring healing creeps to target their heals in order to prevent overhealing (and not waste CPU/energy/ticks) will make the underdog force's targeting much more important.

    Allowing overhealing makes targeting strategies boring, here's how:
    * in lower-tier combat breaking a line of siege workers is very important. If I alternate aoe then focus you are caught anticipating where to spend your heals.
    * if the attacker could overheal, then your anticipation will much more easily overcome scatter/focus alternation and you have a wider pool of health to regain your healing efficiency

    So, if healers can just spam their ability on any target without regard for efficiency then there's no need to finesse your healing OR dps targeting strategies.

    Therefore allowing overhealing favors established players, it favors higher RCL / GCL.

    Preventing overhealing favors refined code.

     

    As a newer player, and a player very interested in military strategy being overcome with code refinements I am strongly opposed to overhealing.



  • @BlackLotus You don't know who is going to get injured so you can't target them.

    Just like you can't treat a soldier on the battlefield for a bullet wound they haven't yet received. That's the way of the world.
    So I agree with no overhealing but disagree that that you should heal a wound that is not there yet.


  • SUN

    You cant.... max HP is max HP... and if heal is interpreted prior to damage, you would not be healing the bullet...only the wound on the next tick... And why would heal sth, that with your current information is at full health anyways?



  • Just going to add one point here for the 'overhealing' side:

    Calling it "overhealing" may have been a bit exaggerating, one person in the slack chat brought up another way you could think about it. It would be like having creepA.heal(creepC) not mean 'creep A should immediately heal all of creep C's wounds', but rather 'creep A should spend all of the following tick healing creep C up to it's own heal capacity'.

    I'm not sure which is better from a game mechanic point of view, but thinking about it this way, for me at least, makes it more intuitive that either could be considered 'correct'.



  • @K-C - I somewhat see your point, but could you expand on how you think overhealing would allow healers to "just spam their ability on any target without regard for efficiency"?

     

    The proposal for allowing this would still keep each creep with HEAL parts only healing one creep per tick, and no 'heal' would ever carry between ticks. It would definitely give small healer/attack pairs more ability to defend, but I don't see how it would let healers require less finesse.

    If anything, it seems to me like this would introduce a whole new layer of complexity and room for refinement, being that healers would have to decide whether they should heal the already damaged creep, or heal the creep they think is going to be damaged during this tick. Could you clarify how this would be the opposite?

     

    My only other question would be: what do you mean by 'aoe'? I don't believe I am familiar with that term.



  • aoe - by this I mean rangedMassAttack

    My examale about alternating scatter fire and focused fire is an attempt to demonstrate an attack strategy which is partially neutralized by overhealing. If you are forced to wager that I could choose a different target for my attack each turn then you will not be able to carry forward the effectiveness of the previous ticks heal.

    With overhealing implemented my strategy would be more predictable because I would be incentivized to only attack creeps with maximum health in order to break up my target's strategy and expose its flaws. Alternatively I could start to burst down one creep more reliably.



  • *only attack creeps with full health. Can't edit on mobile.


  • YP

    I would favor case 1 from the original post. Healing should be executed first, but you can only heal what was already damaged in the last tick. There should be no random in it.

    This makes most sense for me.. if you want to fix something it has to be damaged.

     

    If from balancing perspective something else makes more sense that should be not part of this fix. If there should be some kind if shielding for the next tick... implement shields 🙂

    From a gamedev perspective: defenders should have an advantage... attacking should be harder then defending.