# Problem with Structuring AI Behaviour Move Commands...

This topic is 2463 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

My basic situation is: I have a 2D Top Down Shooter where I want an enemy to turn and face the player, then keeping moving in that direction, adjusting its path if necessary. The game only has 8 directions of movement like in the style of most of those games from 20 or so years ago.
I control the enemy movement by sending InputEvent messages to its input() function. E.g. enemy->input( InputEvent( MOVE_UP_BEGIN ) ); makes it start moving up the screen.
There's no problem with making it rotate to face the player (as best it can in 8 directions) and no problem with having it move in that direction. BUT... when the enemy is moving and must then CHANGE DIRECTION, the velocity of whatever the original direction was is still applied and so it moves all weird and in the wrong direction as a result.

This is because, when it stops moving say... left, the message MOVE_LEFT_END should be sent, but I can't figure out how to do that properly. It's easy with the player character, that works the same way and END messages are sent as soon as the player releases a key, but in the case of an AI character there is no key and I'm struggling to figure out what might do as an equivalent of that key release.

Any ideas? I need a way of telling when the AI has decided to stop moving in a direction. The code I have so far looks like this:
 //Move forward in face direction switch( Entity->getFaceDir() ) { case UP: Entity->input( InputEvent( MOVE_UP_BEGIN ) ); break; case UP_LEFT: Entity->input( InputEvent( MOVE_UP_BEGIN ) ); Entity->input( InputEvent( MOVE_LEFT_BEGIN ) ); break; case UP_RIGHT: Entity->input( InputEvent( MOVE_UP_BEGIN ) ); Entity->input( InputEvent( MOVE_RIGHT_BEGIN ) ); break; case DOWN: Entity->input( InputEvent( MOVE_DOWN_BEGIN ) ); break; case DOWN_LEFT: Entity->input( InputEvent( MOVE_DOWN_BEGIN ) ); Entity->input( InputEvent( MOVE_LEFT_BEGIN ) ); break; case DOWN_RIGHT: Entity->input( InputEvent( MOVE_DOWN_BEGIN ) ); Entity->input( InputEvent( MOVE_RIGHT_BEGIN ) ); break; case LEFT: Entity->input( InputEvent( MOVE_LEFT_BEGIN ) ); break; case RIGHT: Entity->input( InputEvent( MOVE_RIGHT_BEGIN ) ); break; } 

As you can see, moving in an Upward and Rightward direction applies both the UP and RIGHT velocities one after the other.

Is perhaps the only way to remember the previous facing direction and base it off that? Then again, I think that would require an ugly switch statement at this point, but I might look into that.

##### Share on other sites
If you have an algorithm that works satisfactorily for the player, use a similar algorithm for your AI characters. That is, before you call the function you posted, have a "thinking" phase (function call) wherein decisions are made about movement (and possibly other actions). In the case you mentioned above, there would be the equivalent of a sequence: "AI character should change direction" followed by setting flags or input data to do that appropriately. That could include sending a MOVE_LEFT_END or, perhaps, move generally, CLEAR_ALL_INPUTS. Then setup the appropriate movement flags.

##### Share on other sites

If you have an algorithm that works satisfactorily for the player, use a similar algorithm for your AI characters.

Well, the thing there was that the player releases keys to change move direction (or could hold them all down or something and get weird behaviour... like the one I was getting) whereas the AI had no such easy way of deciding what direction to keep moving in.

In the case you mentioned above, there would be the equivalent of a sequence: "AI character should change direction" followed by setting flags or input data to do that appropriately. That could include sending a MOVE_LEFT_END or, perhaps, move generally, CLEAR_ALL_INPUTS. Then setup the appropriate movement flags.

Main problem is... I need to KNOW when it's changing direction. Which is to say... when it should be moving in a direction now, but it wasn't moving in that direction before. Then it's complicated by sending separate UP and LEFT commands for example in order to go Up and Left. As such, I couldn't just clear it all because that would undo the previous move command if it was moving in 2 directions at once. That could've been remedied by making a new MOVE_UP_LEFT_BEGIN command but... I still didn't like the idea of forcibly resetting them all.

What I did in the end was a rather ugly switch system where all 3/2 other directions are checked and stopped if appropriate before starting to move in the remaining direction(s).

It does work like I want it to now, but there must a less long-winded way. Maybe I'd need to look at some of the rest of my design and change that up.

##### Share on other sites
the player releases keys to change move direction (or could hold them all down or something and get weird behaviour... like the one I was getting) whereas the AI had no such easy way of deciding what direction to keep moving in[/quote]
Having the AI make decisions is what the "thinking" phase is about. You apparently have code that "decides" the AI characters movements, even if it's just "face the player and pursue."

I need to KNOW when it's changing direction. Which is to say... when it should be moving in a direction now, but it wasn't moving in that direction before[/quote]
That's part of the decision process also - "Am I facing/moving in the right direction?" If so, continue. If not, change direction.

there must a less long-winded way[/quote]
Don't confuse the switch statements with the decision part of your AI. The switch statements are the implementation of the results of AI decisions. I'd suggest separating the two processes - i.e., A) decide what to do, then B) do it.