Someone please help me with python on summit's gate!

I’m new here, so forgive me if I sound like a whiney brat that constantly feeds off of the work of others (I’m not). I’m on summit’s gate, and I just finished programming all of the attacks and stuff for section 1. For some reason, the computer says that there’s an infinite loop error, and all of my units, including me, just sit around doing nothing while they’re getting killed. I was hoping you guys could look at my code and tell me what’s wrong. I don’t know how to post code, so if you could tell me how, that would be great!

1 Like

Never mind about the “everyone’s doing nothing” part. That was just a naming error on my part. Of course, since I don’t know what the fireballs are called, I can’t use my function to dodge them, so all of my troops die. It would be great if someone could tell me the name in python. I’m pretty sure the infinite loop error is still there, though.

you copy it and paste it or you look at it and write it.:slightly_smiling_face:

To post your code from the game, use the </> button or it won’t format properly. When you click the </> button, the following will appear:
PostCode
Please paste ALL of your code inside the triple back tick marks.

``` <— Triple back tick marks.

Paste ALL of your code in here.

``` <— Triple back tick marks.

There are many people here willing and able to help. If you use the </> button correctly, then ALL of your code should look like this:

while True:
    enemy = hero.findNearestEnemy()
    if enemy:
        hero.attack(enemy)
    else:
        hero.say("My code is formatted properly")

If ALL of your code doesn’t look like the code above, then you’re doing it wrong and we can’t see the structure of the code to troubleshoot whether or not that is the issue. Use the </> button and help us help you. This works when sending a private message as well. Thank you.

# Fight your way into the Inner Sanctum of the ogre chieftain, and defeat her.

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findEnemies("???"))
    if fireball and unit.distanceTo(fireball) <= 10:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 21})
    fireball = hero.findNearest(hero.findByType("fire-shell"))
    if fireball and hero.distanceTo(fireball) <= 10:
        hero.moveXY(hero.pos.x, fireball.pos.y + 21)

def didPhaseEnd():
    enemy = hero.findNearestEnemy()
    if enemy and enemy.health > 0:
        return False
    else:
        return True

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2:
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16:
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth:
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

def summonGriffin():
    if hero.gold >= hero.costOf("griffin-rider"):
        hero.summon("griffin-rider")

def lowestFriend():
    friends = hero.findFriends()
    lowestFriend = None
    lowestHealth = 99999
    for friend in friends:
        if friend.type == "paladin":
            if friend.health/friend.maxHealth < lowestHealth and friend.health < friend.maxHealth:
                lowestFriend = friend
                lowestHealth = friend.health/friend.maxHealth
    if lowestFriend:
        return lowestFriend
    else:
        return None

def commandPaladin(paladin):
    needsHeal = lowestFriend()
    if needsHeal:
        if needsHeal == paladin:
            hero.command(paladin, "shield")
        elif paladin.canCast("heal", needsHeal):
            hero.command(paladin, "cast", "heal", needsHeal)
        else:
            target = paladin.findNearestEnemy()
            if target:
                if paladin.distanceTo(target) < 5:
                    hero.command(paladin, "shield")
                hero.command(paladin, "attack", target)
    else:
        target = paladin.findNearestEnemy()
        if target:
            if paladin.distanceTo(target) < 5:
                hero.command(paladin, "shield")
            hero.command(paladin, "attack", target)

def commandGriffin(griffin):
    target = griffin.findNearestEnemy()
    if target:
        hero.command(griffin, "attack", target)

def commandSoldier(soldier):
    target = soldier.findNearestEnemy()
    if target:
        hero.command(soldier, "attack", target)

def commandArcher(archer):
    if archer.pos.x < hero.pos.x + 5:
        hero.command(archer, "move", {'x': hero.pos.x + 5, 'y': archer.pos.y})
    target = archer.findNearestEnemy()
    if target and archer.distanceTo(target) <= 25:
        hero.command(archer, "attack", target)

def heroToBattle():
    enemy = hero.findNearestEnemy()
    if enemy:
        if hero.canCast("chain-lightning", enemy):
            hero.cast("chain-lightning", enemy)
        elif hero.isReady("power-up"):
            hero.powerUp()
        elif hero.isReady("bash"):
            hero.bash(enemy)
        else:
            hero.attack(enemy)
        hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        #avoidFireball(friend)
        if friend.type == "paladin":
            commandPaladin(friend)
        if friend.type == "griffin-rider":
            commandGriffin(friend)
        if friend.type == "soldier":
            commandSoldier(friend)
        if friend.type == "archer":
            commandArcher(friend)
    heroToBattle()

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()

Thanks for telling me how to paste.

Also, I’ll only be able to be here after 3 at least, because I have school until then. Your help is really appreciated!

Fireball is not an enemy. It is a missile that will damage every type of unit.

I think it is type “ball”

Thanks SO MUCH! I’ll change it right away, and I’ll post the new code.

Here’s my new code. Now I can use the function, but my allies still aren’t dodging the fireballs. Infinite loop error is still there also.

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findEnemyMissiles())
    if fireball and unit.distanceTo(fireball) <= 5:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 11})
    fireball = hero.findNearest(hero.findByType("fire-shell"))
    if fireball and hero.distanceTo(fireball) <= 5:
        hero.moveXY(hero.pos.x, fireball.pos.y + 11)

def didPhaseEnd():
    enemy = hero.findNearestEnemy()
    if enemy and enemy.health > 0:
        return False
    else:
        return True

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2:
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16:
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth:
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

def summonGriffin():
    if hero.gold >= hero.costOf("griffin-rider"):
        hero.summon("griffin-rider")

def lowestFriend():
    friends = hero.findFriends()
    lowestFriend = None
    lowestHealth = 99999
    for friend in friends:
        if friend.type == "paladin":
            if friend.health/friend.maxHealth < lowestHealth and friend.health < friend.maxHealth:
                lowestFriend = friend
                lowestHealth = friend.health/friend.maxHealth
    if lowestFriend:
        return lowestFriend
    else:
        return None

def commandPaladin(paladin):
    needsHeal = lowestFriend()
    if needsHeal:
        if needsHeal == paladin:
            hero.command(paladin, "shield")
        elif paladin.canCast("heal", needsHeal):
            hero.command(paladin, "cast", "heal", needsHeal)
        else:
            target = paladin.findNearestEnemy()
            if target:
                if paladin.distanceTo(target) < 5:
                    hero.command(paladin, "shield")
                hero.command(paladin, "attack", target)
    else:
        target = paladin.findNearestEnemy()
        if target:
            if paladin.distanceTo(target) < 5:
                hero.command(paladin, "shield")
            hero.command(paladin, "attack", target)

def commandGriffin(griffin):
    target = griffin.findNearestEnemy()
    if target:
        hero.command(griffin, "attack", target)

def commandSoldier(soldier):
    target = soldier.findNearestEnemy()
    if target:
        hero.command(soldier, "attack", target)

def commandArcher(archer):
    if archer.pos.x < hero.pos.x + 5:
        hero.command(archer, "move", {'x': hero.pos.x + 5, 'y': archer.pos.y})
    target = archer.findNearestEnemy()
    if target and archer.distanceTo(target) <= 25:
        hero.command(archer, "attack", target)

def heroToBattle():
    enemy = hero.findNearestEnemy()
    if enemy:
        if hero.canCast("chain-lightning", enemy):
            hero.cast("chain-lightning", enemy)
        elif hero.isReady("power-up"):
            hero.powerUp()
        elif hero.isReady("bash"):
            hero.bash(enemy)
        else:
            hero.attack(enemy)
        hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        avoidFireball(friend)
        if friend.type == "paladin":
            commandPaladin(friend)
        if friend.type == "griffin-rider":
            commandGriffin(friend)
        if friend.type == "soldier":
            commandSoldier(friend)
        if friend.type == "archer":
            commandArcher(friend)
    heroToBattle()

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()

Oh wait! I didn’t change the second one! I’ll post the function once I’m done!

allies still don’t dodge fireballs. But I do! If someone could tell me their exact range, that would be awesome. Infinite loop error is still there, obviously. Here it is:

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findEnemyMissiles())
    if fireball and unit.distanceTo(fireball) <= 5:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 11})
    fireball = hero.findNearest(hero.findEnemyMissiles())
    if fireball and hero.distanceTo(fireball) <= 5:
        hero.moveXY(hero.pos.x, fireball.pos.y + 11)

def didPhaseEnd():
    enemy = hero.findNearestEnemy()
    if enemy and enemy.health > 0:
        return False
    else:
        return True

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2:
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16:
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth:
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

def summonGriffin():
    if hero.gold >= hero.costOf("griffin-rider"):
        hero.summon("griffin-rider")

def lowestFriend():
    friends = hero.findFriends()
    lowestFriend = None
    lowestHealth = 99999
    for friend in friends:
        if friend.type == "paladin":
            if friend.health/friend.maxHealth < lowestHealth and friend.health < friend.maxHealth:
                lowestFriend = friend
                lowestHealth = friend.health/friend.maxHealth
    if lowestFriend:
        return lowestFriend
    else:
        return None

def commandPaladin(paladin):
    needsHeal = lowestFriend()
    if needsHeal:
        if needsHeal == paladin:
            hero.command(paladin, "shield")
        elif paladin.canCast("heal", needsHeal):
            hero.command(paladin, "cast", "heal", needsHeal)
        else:
            target = paladin.findNearestEnemy()
            if target:
                if paladin.distanceTo(target) < 5:
                    hero.command(paladin, "shield")
                hero.command(paladin, "attack", target)
    else:
        target = paladin.findNearestEnemy()
        if target:
            if paladin.distanceTo(target) < 5:
                hero.command(paladin, "shield")
            hero.command(paladin, "attack", target)

def commandGriffin(griffin):
    target = griffin.findNearestEnemy()
    if target:
        hero.command(griffin, "attack", target)

def commandSoldier(soldier):
    target = soldier.findNearestEnemy()
    if target:
        hero.command(soldier, "attack", target)

def commandArcher(archer):
    if archer.pos.x < hero.pos.x + 5:
        hero.command(archer, "move", {'x': hero.pos.x + 5, 'y': archer.pos.y})
    target = archer.findNearestEnemy()
    if target and archer.distanceTo(target) <= 25:
        hero.command(archer, "attack", target)

def heroToBattle():
    enemy = hero.findNearestEnemy()
    if enemy:
        if hero.canCast("chain-lightning", enemy):
            hero.cast("chain-lightning", enemy)
        elif hero.isReady("power-up"):
            hero.powerUp()
        elif hero.isReady("bash"):
            hero.bash(enemy)
        else:
            hero.attack(enemy)
        hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        avoidFireball(friend)
        if friend.type == "paladin":
            commandPaladin(friend)
        if friend.type == "griffin-rider":
            commandGriffin(friend)
        if friend.type == "soldier":
            commandSoldier(friend)
        if friend.type == "archer":
            commandArcher(friend)
    heroToBattle()

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()

I was editing my code, trying to find what was wrong, and wondered if the problem was including the door in the enemies. So, I changed the code to not see the door as an enemy, but my hero is still attacking the door! I changed the didPhaseEnd() function, so you should probably look at that for problems, but I’ll post the entire code just in case. Here it is:

# Fight your way into the Inner Sanctum of the ogre chieftain, and defeat her.

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findEnemyMissiles())
    if fireball and unit.distanceTo(fireball) <= 5:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 11})
    fireball = hero.findNearest(hero.findEnemyMissiles())
    if fireball and hero.distanceTo(fireball) <= 5:
        hero.moveXY(hero.pos.x, fireball.pos.y + 11)

def didPhaseEnd():
    enemy = hero.findNearestEnemy()
    if enemy.type != "door":
        if enemy and enemy.health > 0:
            return False
        else:
            return True

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2:
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16:
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth:
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

def summonGriffin():
    if hero.gold >= hero.costOf("griffin-rider"):
        hero.summon("griffin-rider")

def lowestFriend():
    friends = hero.findFriends()
    lowestFriend = None
    lowestHealth = 99999
    for friend in friends:
        if friend.type == "paladin":
            if friend.health/friend.maxHealth < lowestHealth and friend.health < friend.maxHealth:
                lowestFriend = friend
                lowestHealth = friend.health/friend.maxHealth
    if lowestFriend:
        return lowestFriend
    else:
        return None

def commandPaladin(paladin):
    needsHeal = lowestFriend()
    if needsHeal:
        if needsHeal == paladin:
            hero.command(paladin, "shield")
        elif paladin.canCast("heal", needsHeal):
            hero.command(paladin, "cast", "heal", needsHeal)
        else:
            target = paladin.findNearestEnemy()
            if target:
                if paladin.distanceTo(target) < 5:
                    hero.command(paladin, "shield")
                hero.command(paladin, "attack", target)
    else:
        target = paladin.findNearestEnemy()
        if target:
            if paladin.distanceTo(target) < 5:
                hero.command(paladin, "shield")
            hero.command(paladin, "attack", target)

def commandGriffin(griffin):
    target = griffin.findNearestEnemy()
    if target:
        hero.command(griffin, "attack", target)

def commandSoldier(soldier):
    target = soldier.findNearestEnemy()
    if target:
        hero.command(soldier, "attack", target)

def commandArcher(archer):
    if archer.pos.x < hero.pos.x + 5:
        hero.command(archer, "move", {'x': hero.pos.x + 5, 'y': archer.pos.y})
    target = archer.findNearestEnemy()
    if target and archer.distanceTo(target) <= 25:
        hero.command(archer, "attack", target)

def heroToBattle():
    enemy = hero.findNearestEnemy()
    if enemy:
        if hero.canCast("chain-lightning", enemy):
            hero.cast("chain-lightning", enemy)
        elif hero.isReady("power-up"):
            hero.powerUp()
        elif hero.isReady("bash"):
            hero.bash(enemy)
        else:
            hero.attack(enemy)
        hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        avoidFireball(friend)
        if friend.type == "paladin":
            commandPaladin(friend)
        if friend.type == "griffin-rider":
            commandGriffin(friend)
        if friend.type == "soldier":
            commandSoldier(friend)
        if friend.type == "archer":
            commandArcher(friend)
    heroToBattle()

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()

Just so you know, the other problems (allies won’t dodge fireballs and infinite loop error) are still there.

So, I’m not a python expert so don’t jump me for this if I’m wrong.

I think your infinite loop error is inside here:

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()

this line:
phaseEnded = didPhaseEnd()

needs to be moved inside the while loop or else once the while loop is entered, it will never come out(infinite loop)

I would suggest this instead:

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()
    phaseEnded = didPhaseEnd()

Hope that helps…

I tried what you said, and tweaked a reference error in line 13, but the infinite loop is still there. None of my allies seem to be dodging the fireballs, and my hero keeps treating the door as an enemy, so those might be clues. I made a few changes throughout the code since I last posted it, so here it is:

# Fight your way into the Inner Sanctum of the ogre chieftain, and defeat her.

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findByType("ball"))
    if fireball and unit.distanceTo(fireball) <= 5:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 11})
    fireball = hero.findNearest(hero.findEnemyMissiles())
    if fireball and hero.distanceTo(fireball) <= 5:
        hero.moveXY(hero.pos.x, fireball.pos.y + 11)

def didPhaseEnd():
    enemy = hero.findNearestEnemy()
    if enemy:
        
        if enemy.type != "door":
            if enemy and enemy.health > 0:
                return False
            else:
                return True
    else:
        return True

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2:
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16:
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth:
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

def summonGriffin():
    if hero.gold >= hero.costOf("griffin-rider"):
        hero.summon("griffin-rider")

def lowestFriend():
    friends = hero.findFriends()
    lowestFriend = None
    lowestHealth = 99999
    for friend in friends:
        if friend.type == "paladin":
            if friend.health/friend.maxHealth < lowestHealth and friend.health < friend.maxHealth:
                lowestFriend = friend
                lowestHealth = friend.health/friend.maxHealth
    if lowestFriend:
        return lowestFriend
    else:
        return None

def commandPaladin(paladin):
    needsHeal = lowestFriend()
    if needsHeal:
        if needsHeal == paladin:
            hero.command(paladin, "shield")
        elif paladin.canCast("heal", needsHeal):
            hero.command(paladin, "cast", "heal", needsHeal)
        else:
            target = paladin.findNearestEnemy()
            if target:
                if paladin.distanceTo(target) < 5:
                    hero.command(paladin, "shield")
                hero.command(paladin, "attack", target)
    else:
        target = paladin.findNearestEnemy()
        if target:
            if paladin.distanceTo(target) < 5:
                hero.command(paladin, "shield")
            hero.command(paladin, "attack", target)

def commandGriffin(griffin):
    target = griffin.findNearestEnemy()
    if target:
        hero.command(griffin, "attack", target)

def commandSoldier(soldier):
    target = soldier.findNearestEnemy()
    if target:
        hero.command(soldier, "attack", target)

def commandArcher(archer):
    if archer.pos.x < hero.pos.x + 5:
        hero.command(archer, "move", {'x': hero.pos.x + 5, 'y': archer.pos.y})
    target = archer.findNearestEnemy()
    if target and archer.distanceTo(target) <= 25:
        hero.command(archer, "attack", target)

def heroToBattle():
    enemy = hero.findNearestEnemy()
    if enemy:
        if hero.canCast("chain-lightning", enemy):
            hero.cast("chain-lightning", enemy)
        elif hero.isReady("bash"):
            hero.bash(enemy)
        else:
            hero.attack(enemy)
        hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        avoidFireball(friend)
        if friend.type == "paladin":
            commandPaladin(friend)
        if friend.type == "griffin-rider":
            commandGriffin(friend)
        if friend.type == "soldier":
            commandSoldier(friend)
        if friend.type == "archer":
            commandArcher(friend)
    heroToBattle()

phaseEnded = didPhaseEnd()
while not phaseEnded:
    armyAttack()
    phaseEnded = didPhaseEnd()
backToStandard()
door = hero.findNearest(hero.findByType("door"))
#if door:
#    while door.health > 0:
#        hero.attack(door)

The hashtags at the bottom are for what my hero will do when the current phase has ended.

First thing you have an infinite loop because as soon as one of your units is under the amount you said, your hero is stuck in a summon loop.
also if one of your unit is injured the code will stop until the paladin can heal the unit.

Using while loop will prevent all others code from happening unless you put a break or a condition that can happen.
if you want your code to go over all your units once, then use a for loop.

def backToStandard():
    paladins = hero.findByType("paladin")
    while len(paladins) < 2: <------------------------ # Problem Here
        if hero.gold >= hero.costOf("paladin"):
            hero.summon("paladin")
    archers = hero.findByType("archer")
    while len(archers) < 6:   <------------------------ # Problem Here
        if hero.gold >= hero.costOf("archer"):
            hero.summon("archer")
    soldiers = hero.findByType("soldier")
    while len(soldiers) < 16: <------------------------ # Problem Here
        if hero.gold >= hero.costOf("soldier"):
            hero.summon("soldier")
    friends = hero.findFriends()
    for friend in friends:
        while friend.health < friend.maxHealth: <------------------------ # Problem Here
            for paladin in paladins:
                if paladin.canCast("heal", friend):
                    hero.command(paladin, "cast", "heal", friend)
    while hero.health < hero.maxHealth:
        for paladin in paladins:
            if paladin.canCast("heal", hero):
                hero.command(paladin, "cast", "heal", hero)

Also for long missions like this one I recommend using a variable that will change. We usually call them flags.

You might need to change your strategy a couples of time during this mission.

in this example I use the flag strategy

strategy = 0
While True:
    # Do something everytime
    If strategy == 0:
        # Do something during this phase
        if condition == something: # condition that will make the phase change
            strategy += 1
    if strategy == 1:
        # Do something else during this phase

I did what you said, and deleted that function. And it worked! But my units still aren’t dodging the fireballs. I’ll post that function, and maybe you guys can see what’s wrong.

def avoidFireball(unit):
    fireball = unit.findNearest(hero.findEnemyMissiles())
    if fireball and unit.distanceTo(fireball) <= 5:
        hero.command(unit, "move", {'x': unit.pos.x, 'y': fireball.pos.y + 11})
    fireball = hero.findNearest(hero.findEnemyMissiles())
    if fireball and hero.distanceTo(fireball) <= 5:
        hero.moveXY(hero.pos.x, fireball.pos.y + 11)

Also, does anyone know the range of these things?

the only problem with this function is that the conditions are in the wrong place.
The real problem is in your armyAttack() function.

You want your units to avoid the fireball at all cost.

But something else move your units right after you asked them to move away from the fireball.

if fireball and unit.distanceTo(fireball) <= 5:

What if you reverse it?

if not fireball or unit.distanceTo(fireball) > 5:
What happen if there is no fireballs near?

Thanks a lot! I changed the function so it would return ‘true’ or ‘false’, for if a fireball is in range or not. Then, I incorporated the action into the armyAttack() function, giving an else statement for the attacking. All of my units seem to be dodging. However, I don’t think I put in the right numbers for how much a unit should move, and in which direction. If anyone could tell me the range of the fireballs, that would really help. I’ll probably just experiment with different numbers until I get something that works out.

Okay… never mind. My allies actually aren’t dodging the fireballs, so there’s still probably a problem. I’ll give you guys all the code related to this. It might just be a bug, though.

def shouldHeroDodge():
    fireball = hero.findNearest(hero.findByType("ball"))
    if not fireball or hero.distanceTo(fireball) > 5:
        return False
    else:
        return True

def shouldUnitDodge(unit):
    fireball = unit.findNearest(hero.findByType("ball"))
    if not fireball or unit.distanceTo(fireball) > 5:
        return False
    else:
        return True

def heroToBattle():
    fireball = shouldHeroDodge()
    if fireball:
        hero.moveXY(hero.pos.x + 5, hero.pos.y)
    else:
        enemy = hero.findNearestEnemy()
        if enemy:
            if hero.canCast("chain-lightning", enemy):
                hero.cast("chain-lightning", enemy)
            elif hero.isReady("bash"):
                hero.bash(enemy)
            else:
                hero.attack(enemy)
            hero.shield()

def armyAttack():
    summonGriffin()
    friends = hero.findFriends()
    for friend in friends:
        fireball = shouldUnitDodge(friend)
        if fireball:
            hero.command(friend, "move", {'x': friend.pos.x + 5, 'y': friend.pos.y})
        else:
            if friend.type == "paladin":
                commandPaladin(friend)
            if friend.type == "griffin-rider":
                commandGriffin(friend)
            if friend.type == "soldier":
                commandSoldier(friend)
            if friend.type == "archer":
                commandArcher(friend)
    heroToBattle()

door = hero.findNearest(hero.findByType("door"))
phaseEnded = didPhaseEnd(door)
while not phaseEnded:
    armyAttack()
    phaseEnded = didPhaseEnd(door)