Pause until animation completes


I have two animations that need to play:

  1. A fire animation that moves the FPS arms:
    ownarms.playAction(“FPS.Arms.SGun.SFire”, 1, 20, 0, 1, 5, bge.logic.KX_ACTION_MODE_PLAY, 0, 1)

  2. An idle animation that moves the FPS arms:
    ownarms.playAction(“FPS.Arms.Sgun.Idle”, 1, 60, 0, 1, 5, bge.logic.KX_ACTION_MODE_LOOP, 0, 1)

I can’t put these on two separate layers as the “blend-in” option doesn’t work between layers and I get a jerking motion. I can’t put these as separate priorities, since if the idle is first, the fire anim never plays… if the fire anim is first, the idle animation never starts again! (Until I walk/sight in, get out of the loop)

If i use ownarms.stopAction(0), the fire animation will never complete, the idle anim takes over almost instantly.

How do I make sure the fire animation completes before the idle animation starts again?

You should be able to play the firing animation over the idle animation with priorities. Maybe the issue is combining animations with blend-in. Have you tried putting the priorities higher on the firing animation and ensuring the idle animation doesn’t play if the firing animation is doing so? Just a thought.

Anyway, as for your question, you can get the current animation frame with obj.getActionFrame().

Yes, I can get the firing animation to play over the idle animation, just having issues getting the idle animation to start again after that, since they are playing on the same layer, and the fire animation has a higher priority.

if single_fire.positive and fire_state == 0 and run_state == 0: 
		own["fire"] = 1
		owngun.playAction("FPS.Spas-12.SFire", 1, 20, 0, 0, 5, bge.logic.KX_ACTION_MODE_PLAY, 0, 1)#need to play 2 animations at the same time for firing... one on the arms rig and one on the gun rig
		ownarms.playAction("FPS.Arms.SGun.SFire", 1, 20, 0, 0, 5, bge.logic.KX_ACTION_MODE_PLAY, 0, 1)

	if not single_fire.positive:
		own["fire"] = 0

if ([sspeed, fspeed, jspeed] == [0, 0, 0]): #if doing nothing		print("idle")
		curFFrame = ownarms.getActionFrame(0)
		ownarms.playAction("FPS.Arms.Sgun.Idle", 1, 60, 0, 1, 5, bge.logic.KX_ACTION_MODE_LOOP, 0, 1)

Output from terminal:

As you can see from the output, (btw top just means top of script) once I hit fire, (while standing still, doing nothing) it goes to the idle loop, where the frame is determined to be (1), then it goes out and back to the idle loop, where the frame is only 2.5, but it will stay there until I move around… not sure how to fix that issue.

If I recall correctly, playAction is a Python command that should be triggered only the times that you need to start playing the animation. Issue the function call once, and the BGE handles actually playing it through.

So, for example, you can set a variable (i.e. obj[‘currentanim’]) to represent the currently playing animation. If the currently playing animation is different from the one you want to play, then issue the playAction command with the animation settings the way you want, and then set obj[‘currentanim’] to be the animation that you want to play. That way, playAction only runs once to begin the animation.

You can also control the play speed with armature.setActionFrame so that you can have control over how an animation plays or loops.

Not quite sure I understand how to set a variable that contains the current object animation, but I still don’t think that will solve my issue…

What I need to do is PLAY MY ENTIRE FIRE ANIMATION, which is triggered when I press the left mouse button. However, that is only a split second, so the python continues on to the next bit of code, which is IDLE. However, when in the IDLE block, I AM STILL PLAYING THE FIRE ANIMATION. Since the FIRE anim is a higher priority, the IDLE animation is not kicked off, and as the python remains in the IDLE loop waiting, NO animation plays. It will start to play once I move and get out of that loop, but until then, nothing.

For example, if I HOLD DOWN the left mouse button for about a full second, it works FINE, no issues, because it finishes the animation entirely, and when I let go of the button the idle animation is not conflicting.

I either need to literally set up a timer in the idle loop that will somehow wait till the fire anim is all done then kick off the idle anim or setup a timer in the fire anim loop to wait it out… not ideal, but I guess that might have to be what I do…

I understand that scripting and using the BGE can be frustrating, especially when you’re trying to do something that you know is possible and the engine just doesn’t quite seem to work the way you want it to. I’m sorry, as well, if I seem like I’m not listening to your problem. Posting a blend file would be very useful if nobody (like me, in this case) seems to understand your problem.

Keep calm and remember that it’s just a game that you’re working with. If you can’t seem to fix an issue, come back to it later on, or even another day or month, perhaps after working on something else entirely. Find a way to keep your mind clear when you program, and you’ll understand more and more of the BGE.

I would also like to apologize since I was mistaken - playAction can be triggered more than once, and it won’t change the animation process (at least, on the Blender version I use).

Anyway, if I’m understanding you correctly, you want to:

  • Play an animation when you left-click,
  • Have it play all the way through (regardless of whether or not you’re holding down the left mouse button), and
  • When finished, revert to a looping ‘idling’ animation.

If so, here’s an example that should give you what you’re trying to set up.

ArmatureExample.blend (437 KB)

I’m sorry if I seemed frustrated, I was only capping words for emphasis, since I wanted to explain the issue as best I could. I know you are listening, when approaching something from the outside it is much harder to grasp the intricacies in one go, don’t worry, I was calm when posting, just trying to emphasize exactly what the issue was.

Here is the link to the blend if anyone wants to test:

I will take a look at your blend file and see if I can get it working in mine. I just wish there was a good FPS arms full-fledged template or full game that I could learn from, since at this point I am past all the tutorials/templates I could find on this exact topic…

Trust me, I appreciate all the work you have done for me :smiley:

So, I basically just changed line 44 where it says “own[‘fire’] = 0” before the “if g1 or g2 or g3 or g4” block to:

if own['fire']:

     if ownarms.getActionFrame() >= 18:
          own['fire'] = 0

That will stop the ‘firing’ state when the animation finishes (or rather, is close - 18 rather than 20, because I want to ensure I catch the end and not let the animation start again). If you need the complete blend file, I can send it back to you.

I would love it if you could send the whole file back… I changed the lines shown and the fire animation will play fully, but the idle animation will not kick back in until I move again. If I just hit “p” and then “left mouse”, the fire anim will play, but the idle animation will not play after the fire anim until I move.

Um, My method does this :slight_smile:
Property Trigger
Keypress X ---------and-----------Trigger =1
if Trigger=0---------/
if trigger >1 but <10 --and---------add 1
if trigger = 10 --------and---------trigger =0

if trigger = 1---------and---------play action frame1
if trigger = 2---------and---------play action frame2

this can both apply forces and advance an animation based on the “trigger”
it can also do stateless delays, and alot of other neat stuff

So I took a look at your script in your example and I think I understand it… your script manages to loop continuously, all the way through, allowing this method to work… however mine apparently does not… I am not sure why not. I may have to see if it is possible to write another python script entirely to see if that works for just controlling the shooting animations and logic.

see my logic solution? seems a tad smaller…

Unfortunately, I am doing a few things when I do my fire animation. I am also checking to see if the run_state variable is set, and in the future will be checking to see if I am crouched as I might have a different animation to play.

I am also making sure that my feet are touching the ground when I am firing (no jumping and firing) Also play on speeding up/slowing down animations in accordance with damage level (eventually), so I don’t think logic bricks will do all that, and if they do, it will be a tangled mess…

Nope, my whole game runs on them, just make sure they are labeled etc, I code better this way, it might not be best for you :slight_smile:
I can - grab and assemble machines in game, and test them,I have about 66% of the engine done(walking jumping, carrying,climbing etc, but I need to get all the animations through Ik target manipulation and application of forces etc honed in :slight_smile:

It will be free/open source with ad an ad retention clause
(My google ads will still be in game)

O yea, I don’t use any pre rendered animations or pre-keyed :slight_smile:

Not one python line in this :slight_smile:

Well once it is done I would love to see it… I started out with logic bricks but they quickly became too confusing for me, had too many bricks that would be on separate objects tied together by messaging, I would easily get lost. With code, most of it is grouped well enough, and I can comment everything on it easily, and it just seemed to have more control.

I’ve only been using Blender a few months, so can’t say I know what you mean by that… I think I must have keyed animations? I hit “I” to insert the keyframes I need for my animations.

Yeah, I use armatures and run the armature to do skeletal animation, you can accomplish the same results, but with alot less code, check this out

here is a armature man

here is a simple ai thingus


RigaMandit.blend (626 KB)LikeClockwork.blend (445 KB)

Well, after some more investigation, I managed to solve the issue (extremely simple as it turns out). Your example loops the python script continuously, but mine would not do so! After examining the code, could not figure it out, but finally realized the script was only triggered when a sensor was activated, and your blend file had an always logic block set to pulse mode that was constantly looping the python script. All I had to do was setup an always logic brick on mine, then do the following code:

	if ([sspeed, fspeed, jspeed] == [0, 0, 0]): #if doing nothing		if not fire_state:
			ownarms.playAction("FPS.Arms.Sgun.Idle", 1, 60, 0, 0, 5, bge.logic.KX_ACTION_MODE_LOOP, 0, 1)
		if fire_state:
			if ownarms.getActionFrame(0) &gt; 19:			
				if own["fire"]:
					ownarms.playAction("FPS.Arms.Sgun.Idle", 1, 60, 0, 0, 5, bge.logic.KX_ACTION_MODE_LOOP, 0, 1)