Animation - Mashing attack button (SOLVED)

I have read on the post stated above that animation using play_animation will always play to the end unless another animation started. Now, I pressed the attack button that plays attack animation once, it will play the animation to the end. Okay, if I pressed the attack button more than twice, the animation did not play to the end and it play only the early one. How to solve this? Thank you

Not sure what you’re after here?
Do you want the animation to play to the end, even though you call a new play_animation?
If so, you can have a flag saying you’re currently playing an animation. E.g.

self.is_attack_playing = true

You can then use that to avoid playing a new animation while the first one is playing.

And when the animation is done, you reset the flag.

2 Likes

yes i want the animation to play to the end. But i do not know how to to avoid play a new animation while the first one is playing. I already read on the animation_done, but i can’t figure out how to implement it

the attack animation restarted when i pressed the attack button twice.

Typing on a phone.

if self.attacking then return end
self.attacking = true
sprite.play_flipbook("#mysprite", "attack", function()
    self.attacking = false
end)
1 Like

it returns this following error:
Compilation failed: ‘)’ expected (to close ‘(’ at line 98) near ‘self’

You need to put a ) behind the last end.

if self.attacking then return end
self.attacking = true
sprite.play_flipbook("#mysprite", "attack", function()
	self.attacking = false
end)
2 Likes

thank you, no more error now, however it did not play attack animation. I put the code on the update. While on the input, i put the self.attacking = true.

if action.pressed then
-elseif action_id == hash(“attack”) then
self.attacking = true
end

Put all of the code in on_input

2 Likes

thank you so much, it works now. You are the best :grinning: :+1:

2 Likes

I am wondering, why it is not working after i pressed other animation? for an example, after i play the other animation like walking, then if i press attack again it does not play? I am sorry for asking a lot.

It’s probably because you play another animation which will cause the callback for the first to not get called and self.attacking remains true

1 Like

You can also check out my struggle with similar problem and a very helpful post here by @TheKing0x9

2 Likes

thank you so much. I will check it. :+1:

okay thank you, I will improve on it

hello, i still can not get it work. I am sorry. The attack animation did not played after walking animation is played. :tired_face:

Can you share your code here?

thank you for your response. When i check at the input, the attack id is received, it knows that the attack function are being launched. But the animation did not.

local ATTACK = hash("attack")
ATTACKS = {1, 2, 3, 4}

local function play_attack_anim(self, index)
	if not (self.anim == ATTACKS[index]) then 
		msg.post("#sprite", "play_animation", {id = hash("attack"..ATTACKS[index])})
		self.anim = ATTACKS[index]
		print("play animation")
	end
end

local function check_attacks(self)
	if self.completed_attacks < self.scheduled_attacks then
		play_attack_anim(self, self.completed_attacks % 3 + 1)
	elseif self.completed_attacks == self.scheduled_attacks then
		self.completed_attacks = 0
		self.scheduled_attacks = 0
	end
end

local function play_animation(self, animation)
	if self.current_animation ~= animation then
		self.current_animation = animation
		sprite.play_flipbook("#sprite", animation)
		print(animation)
	end
end

function init(self)
	--acquire input
	msg.post(".", "acquire_input_focus")

	self.scheduled_attacks = 0
	self.completed_attacks = 0
	
	self.anims = nil

	self.direction = vmath.vector3(0, 0, 0)
end

function final(self)
end

function update(self, dt)
	if self.completed_attacks == 0 and self.scheduled_attacks  == 0 then
		play_attack_anim(self, 4)
	end
end

function on_message(self, message_id, message, sender)
	if message_id == hash("animation_done") then
		self.completed_attacks = self.completed_attacks + 1
		print("attack animation complete")
	end
end

function on_input(self, action_id, action, animation)
	if action_id == ATTACK and action.pressed then
		check_attacks(self)
		self.scheduled_attacks = self.scheduled_attacks + 1
		print(self.scheduled_attacks, self.completed_attacks)
	end

	if action.pressed then

		if action_id == hash("left") then
			self.direction.x = -1
			msg.post("#sprite", "play_animation", {id = hash("move-left")})
			print("left animation complete")
		elseif action_id == hash("right") then
			self.direction.x = 1
			msg.post("#sprite", "play_animation", {id = hash("move-right")})
			print("right animation complete")
		end
	elseif action.released then

		if action_id == hash("left") then
			self.direction.x = 0
			if vmath.length(self.direction) == 0 then msg.post("#sprite", "play_animation", {id = hash("move-left")}) end
		elseif action_id == hash("right") then
			self.direction.x = 0
			if vmath.length(self.direction) == 0 then msg.post("#sprite", "play_animation", {id = hash("idle-right")}) end
		end
	end
end

function on_reload(self)
	
end
2 Likes

Add three " " " around your code, and it will display properly. Right now, all indentation and syntax highlighting got lost, which makes it very hard to read.

1 Like

okay i use the preformatted text to display the code.

1 Like