Hitboxes and I-frames

@richard @InvalidProject @ZeroFall I’m currently working on a side project based off of the game “Nine Sols” and I wanted to make a proper damage-taking system. In my other games that I’ve made, I didn’t really include a hitbox nor I-frames in it. I have already made the I-frames and hitbox but I want to make it so that if the enemy has his sword slam animation playing and the player overlaps him, the player gets knocked back a tad bit, takes 1 bar of health out of the 4 that the player has and doesn’t take any extra unless there are other projectiles.

The problem with this though is that I since the sword slam animation in playing for 6-8 frames, the player will take more than 1 bar of health. I want to make it so that the hitbox stops receiving input from that one enemy if hit and deals only 1 bar of health all while receiving info from all the other sprites. Using I-frames won’t work when the player has to combat multiple enemies in a room segment. Do any of you have an idea or a working solution for this?

Thanks,
CrunchyToast

2 Likes

Dear CrunchyToast, I’m sure you have already heard of my leave on your project and any foreseeable projects you plan to make. I don’t know why you pinged me but I assume it was a mistake- I am not complaining however, just letting you know! As for the issue, I would use sprite-data to make I-frames instead of using other things like sprite kind!

4 Likes

Class Player:

def __init__(self, max_health=4):

    self.max_health = max_health

    self.current_health = max_health

    self.is_invulnerable = False

    self.invulnerable_duration = 0.5  # seconds

    self.damaged_enemies = set() # Use a set for efficient lookups

def apply_damage(self, enemy, damage_amount):

    if not self.is_invulnerable:

        self.current_health -= damage_amount

        self.is_invulnerable = True

        self.damaged_enemies.add(enemy)

        print(f"Player took {damage_amount} damage from {enemy}. Health: {self.current_health}")

def update(self, dt):

    if self.is_invulnerable:

        self.invulnerable_duration -= dt

        if self.invulnerable_duration <= 0:

            self.is_invulnerable = False

            self.invulnerable_duration = 0.5 #reset duration

            self.damaged_enemies.clear() # Clear the set after I-frames

Class Enemy:

def __init__(self, name):

    self.name = name

Example Usage

​player = Player()​

enemy1 = Enemy(“Goblin”)

enemy2 = Enemy(“Orc”)

Simulate collision

player.apply_damage(enemy1, 1) # Player takes damage from Goblin

player.apply_damage(enemy1, 1) # Player is invulnerable to Goblin

player.apply_damage(enemy2, 1) # Player takes damage from Orc

Simulate I-frame ending

player.update(1) # dt is 1 second, so I-frames end

player.apply_damage(enemy1, 1) # Player can take damage from Goblin again

I’m not sure if this helps or not but maybe…?

2 Likes

@CrunchyToast the easiest thing to do here would be to just set the “ghost through sprites” flag to true on the enemy attack when the player takes damage

2 Likes

I completely understand your situation but the reason I pinged you was to see if you had a solution. :slight_smile:

Yes that’s much smarter. Thank you.

1 Like