itch.io is community of indie game creators and players

Devlogs

E.T. Returns Postmortem(ish) Part 3: Attack Patterns

E.T. Returns
A browser game made in HTML5

If you haven't read them yet, I recommend first checking out Part 1 and Part 2 of my E.T. Returns Postmortem(ish).

ENEMY ATTACK PATTERNS
E.T. Returns is a horde shooter where dozens of enemies simultaneously pursue the titular character.  When building the game, I wanted enemies to flock together into a massive horde that pursued the player while also having enough variability to make the game both challenging and fun.  To do so, I used a variety of steering behaviors that control enemy movement and attack patterns.  Steering behaviors are simply movement patterns that are applied to game characters to achieve some goal.  In this article I will review some of the core steering behaviors used in E.T. Returns and talk about a few things that could have been improved to get slightly better gameplay.

SEEK
The primary goal of all of the enemies in E.T. Returns is to damage and kill the player (in the this case the player is E.T.).   Enemies do not have projectile attacks so instead enemies must collide with the player to cause damage.  Seek is the primary steering behavior used by a majority of enemies to achieve this goal.  When using the seek steering behavior, enemies move directly towards the player in a straight line using a simple vector calculation.

enemyMovement = (playerTransform.localPosition - this.transform.localPosition).normalized * moveSpeed;

RANDOM ANGLE SEEK
Random angle seek is a seek variation where instead of moving in a straight line towards the player, the enemy moves towards the player in a more jagged, less predictable pattern.  To achieve this, I compute the movement vector from the enemy toward the player and offset it by a random angle.  

enemyMovement = (playerTransform.localPosition - this.transform.localPosition).normalized * moveSpeed * Quaternion.Euler(0, 0, Random.Range (-50f, 50f));

FIXED ANGLE SEEK
Fixed angle seek is similar to random angle seek, but instead of using a randomized angle, a constant angle is used.  

enemyMovement = (playerTransform.localPosition - this.transform.localPosition).normalized * moveSpeed * Quaternion.Euler(0, 0, 50f);

SIGHT
Most enemies use a sight distance to determine when to switch between different steering behaviors.  A distance is computed from the player to the enemy.  If the distance is GREATER than the sight distance, then the enemy cannot “see” the player and the enemy does not change behaviors.  If the distance between the enemy and the player is LESS than the sight distance, then the enemy can see the player and may shift to a different steering behavior.  For example, a surround enemy might switch to seek when they get close enough to the player using this sight distance calculation.

OTHER ATTACK PATTERNS
I use additional steering behaviors and attack patterns to implement unique attack or movement patterns.  FBI agents and scientists move towards locations located in 45 degree increments from E.T. - essentially trying to avoid the player.  River Raid planes and Moon Patrol rovers move in the straight horizontal lines across the screen.  Dig Dugs form in a circle around the player, wait, and then use a seek behavior.  These patterns add variety to the game and make it harder for the player to avoid and attack the horde as they must also navigate other enemy attack patterns. 

IMPROVEMENTS
For the short amount of time I took to build E.T. Returns, I’m quite happy with the enemy attack patterns.  There are, however, a few things that I think could be improved.

  1. Better handling of spread.  The spread steering behavior helps break up the horde and make enemy movement less predictable, but it’s not always clear how long an enemy should spread, if the enemy should immediately return to seek, or how this should be balanced with other enemies who are also spreading.  For example, I could have set an upper bound on how many enemies can simultaneously spread to maintain the integrity of the horde.
  2. Better handling of enemies hitting one another.  At present two enemies can run directly into one another and get stuck.  This typically resolves itself as E.T. moves around and the enemy target location changes.  However, when enemies collide and get stuck it makes the AI seem clunky and dim-witted.  A simple check for collision with another enemy could have been used to reroute stuck enemies.
  3. Better wall handling.  The walls of combat tanks both limit and control the playfield boundaries.  Enemies check for the tank walls and move away from them when they hit them.  However, I could have added another calculation here to make the movement appear more natural.  Similar to the sight distance used with the player, a sight distance could be implemented for the walls allowing enemies to detect an approaching wall and move in another direction (rather than blindly slamming into them and THEN reacting).  This would make the enemy AI seem more real-world and intelligent.

For the most part the enemy attack patterns do exactly what I was hoping for: a huge horde of enemies swarm the player with enough variation to keep the game interesting.  There are, however, places where the behaviors could be tweaked to attain a more realistic enemy AI.  In part 4 I’ll talk about balancing the game difficulty.  Onward!

TL;DR: Steering behaviors are used to control enemy movement with seek and seek variations being the key to the enemy attack patterns.  Spread is used to reduce the density of the horde.  I got the result I was looking for, but there is room for improvement with enemy-enemy and enemy-wall collisions.

Download E.T. Returns
Leave a comment