Skip to content

AI Path Finding and Steering

Brendan Walker edited this page Aug 17, 2014 · 5 revisions

The following page describes how the AI computes a path to their destination and locomotes to their next waypoint.

###Overview As mentioned in the Game Event System page, there are a few game events that are used to make entities move around the map. For Mobs it's the "GameEvent_MobMoved" event (the other movement events have a similar control flow). When this event is applied to the game state we call the RequestMoveTo() method on the mob entity. The PathFindingComponent on the mob is used to request new paths and maintain path waypoint state. The PathFindingSystem is used to maintain and update async path finding request processed by PathFindingComputer instances. The SteeringComponent on the mob entity is used generate throttle and facing requests toward the current path waypoint. The mob entity updates the position of the mob based on throttle. Finally the MobWidget drives animation based on throttle and facing.

###PathFindingComponent On a new path request the path finding component will reset it's path state and then send an asynchronous path finding request to the path finding system. The path finding system generates a new path, which should succeed because it was already solved on the server. When the path request comes back, the path waypoints are saved on the path component. The path component keeps track of which waypoint on the path the mob is currently heading toward. When the waypoint is reached, the current waypoint index is incremented. When there are no more waypoints, the path is marked as completed.

###PathFindingSystem The PathComputer class is used to generate a path between two locations on the nav mesh. The resulting path steps are stored in the path computer's result data. Path generation is done on the client asynchronously with the NonBlockingPathRequest() call, so that the game doesn't hitch (A* queries tend to be expensive). Async path finding requests are managed by the PathfindingSystem singleton. The path finding component gets notified when it's pending path finding request is complete.

###SteeringComponent The steering component is responsible for computing the current throttle, a zero to one length vector that points where the entity should be moving, and the facing, a unit vector that points where the entity should be facing. The steering component uses the path finding interface on it's parent entity to find out if the entity has an active path, and if so which waypoint it should be heading toward. If there is an active waypoint, we throttle directly at it and face it directly. Presently there is no inertia involved in changing facing (facing snaps to the target facing). That might change at some point if there is some interesting gameplay reason to have characters with non-zero turning radii.

###MobWidget The MobWidget is used to drive all of the renderable pieces of the mob. As far as path following animation goes the UpdateAnimation() method on the MobWidget pushes the throttle and facing data on to an instance of Unity's AnimationController component. If you open up an animation controller on any mob sprite, then open up the "Locomotion" state, and then open up the blend tree you'll see that different values of "Speed" , "FacingX" and "FacingY" parameters are bound to specific animation clips. Not gonna lie; setting up a new sprite and getting all of these clips and state wired up correctly is kind of a pain.

###Path Debugging If you want to see how a path would be computed for the player to a test location there are two helpful debug toggles you can turn on using the chat window. One toggle will render an outline of the nav mesh and the other will render a test path from the player to the mouse cursor.

:set entity.path_finding.render_nav_mesh true
:set entity.path_finding.render_debug_path true

Debug Path

Similarly, if you want to see if a location on the nav mesh is visible to the player you can turn on a toggle to render a visibility raycast from the player to the mouse cursor:

:set entity.path_finding.render_visibility true

Blocked Line of Sight:

Line of Sight Blocked

Unblocked Line of Sight:

Line of Sight Visible

High Level

Folder Organization

Game Design

Game Objective

Player Classes

Enemy Types

Loot

Web Server Documentation

Server Project Organization - How the files in the server project are arranged

Mob Types - Format for the mob type definitions

Room Templates - How the room templates are validated and stored in the DB

Navigation - How AI navigation is computed on the server

AI Decision Making - How AIs make decisions in response to players moves

Request Processors - How incoming JSON requests are processed

Database Query Layer - How database queries are structured and cached

Standalone And Embedded Web Server - How the stand alone and client embedded web server are structured

ASPX Web Service - How the IIS hosted web server is structured

Unity Client Documentation

Client Project Organization - How the files in the client project are arranged

UI System - Wrapper around Unity immediate mode UI and UI event handling

Asynchronous Request System - How JSON requests are sent to the web server

Game Event System - How the game state changes as a result of player actions

AI Path Finding and Steering - How the AI compute a path and drive toward path waypoints

IRC and Push Notifications - How chat and server push notifications are routed through IRC

Tools Documentation

OGMO Tile Editor

Verification Scripts

Build Scripts

Clone this wiki locally