mirror of
https://github.com/ENSL/NS.git
synced 2024-11-15 01:11:43 +00:00
58358d0927
* Initial bot commit * Added server commands and cvars for adding AI players to the game. * Added auto modes for automating the adding and removal of bots * Bots connect to the server and join teams correctly * Added round restart and new map detection for AI system Push before new project added for detour * Initial bot integration * Integrated all basic bot code for navigation and task performing * Added support for multi_managers to better understand how buttons and triggers affect doors * Improved bot understanding of door triggers and weldables * Reworked nav profiles Nav profiles for bots are now dynamically updated to take into account changing capabilities, such as picking up a welder * Improved bot door usage * Added weldable obstacles back into navigation Bots now understand how to get around weldable barriers * Replaced fixed arrays with vectors * Resource node and hive lists are now vectors. * Further improved bot weld behaviour * Added dynamic reachability calculations When barriers and doors are open/closed, new reachability calculations are done for structures and items so bots understand when items/structures become reachable or unreachable as the match progresses. * Added team-based reachability calculations Reachabilities for structures and items are now based on the team, so bots understand when they can't reach a structure from their spawn point. * Implemented long-range off-mesh connections and dynamic off-mesh connections * Implemented fully dynamic off-mesh connections Phase gates now use connections rather than custom path finding. Much more performant. * Replaced arrays with vectors for simpler code * Started Bot Swimming * Bots understand trigger_changetarget Bots can now navigate doors operated with a trigger_changetarget so they understand the sequence in which triggers must be activated to make it work * Push before trying to fix long-range connections * Implement new off-mesh connection system * Redid population of door triggers * Fixed trigger types and links to doors * Added lift and moving platform support * Lift improvements * Bots avoid getting crushed under a lift when summoning it * Bots are better at judging which stop a platform needs to be at * Tweak lift and welder usage * Fixed bug with multiple off-mesh connections close together * Finish lift movement * Fixed dodgy path finding * Improved skulk ladder usage and lerk lift usage * Fix crash with path finding * Re-implement commander AI * Commander improvements * Improve commander sieging * Commander scanning tweak * Reimplemented regular marine AI * Start reimplementing alien AI * Implement gorge building behaviours * Start alien tactical decisioning * Continuing alien building and other non-combat logic * More alien role work * Adjusted base node definitions * Iterate Capper Logic * Alien assault AI * Alien Combat * Fix grenade throwing, better combat * Marine combat AI improvements * Commander improvements * Commander + nav improvements * Drop mines * Improved bot stuck detection * Commander supply improvements * Bot fill timing config * Added nsbots.cfg to configure internal bots * Changed bot config file to "nsbots.cfg" * Bug fixing with navigation * Fix skulk movement on ladders * Improved commander placement and tactical refresh * Fixed bug with ladder climbing * Doors block off-mesh connections * Finished doors blocking connections * Marine and alien tactical bug fixes * Add commander beacon back in * Start combat mode stuff * First pass at combat mode * Bots attack turrets * Fix ladder and wall climbing * Commander chat request * Improved skulk ladders * Added nav meshes for new bot code * Added bot configuration to listen server menu * Added bot config file * Added default bot config to listenserver.cfg * Added default bot settings to server.cfg * Include VS filter for bot files * Crash fixes * Bot improvements * Bot stability and mine placement improvements * Fixed crash on new map start with bots * Reverted Svencoop fix * Fixed crash, added more cvars * Performance improvement * Commander building improvements * Stop bot spasming when waiting to take command * Fixed doors not blocking connections * Added bot disabled guard to round start * Commander improvements, movement improvements * Tweaked level load sequence * Performance improvements * Bot load spread * Fixed commander update * Refactor bot frame handling * Bug fixes + Pierow's dynamic load spread * Minor bug fixes * Fix door detection, prep for test * Fixed commander siege spam * linux compile test * fix hardcoded inlcudes * O1 compile flag for detour - fix linux server crash * Revert detour compile flags to original for windows * linux build update * remove x64 build configs * update bot nav meshes and configs * fix bot physics at high server fps, update navmeshes. from @RGreenlees --------- Co-authored-by: RGreenlees <RGreenlees@users.noreply.github.com> Co-authored-by: RichardGreenlees <richard.greenlees@forecast.global>
318 lines
9.1 KiB
C++
318 lines
9.1 KiB
C++
#ifndef DETOURTILECACHE_H
|
|
#define DETOURTILECACHE_H
|
|
|
|
#include "DetourStatus.h"
|
|
#include "DetourNavMesh.h"
|
|
|
|
#include <vector>
|
|
|
|
typedef unsigned int dtObstacleRef;
|
|
typedef unsigned int dtOffMeshConnectionRef;
|
|
|
|
typedef unsigned int dtCompressedTileRef;
|
|
|
|
/// Flags for addTile
|
|
enum dtCompressedTileFlags
|
|
{
|
|
DT_COMPRESSEDTILE_FREE_DATA = 0x01, ///< Navmesh owns the tile memory and should free it.
|
|
};
|
|
|
|
struct dtCompressedTile
|
|
{
|
|
unsigned int salt; ///< Counter describing modifications to the tile.
|
|
struct dtTileCacheLayerHeader* header;
|
|
unsigned char* compressed;
|
|
int compressedSize;
|
|
unsigned char* data;
|
|
int dataSize;
|
|
unsigned int flags;
|
|
dtCompressedTile* next;
|
|
};
|
|
|
|
enum ObstacleState
|
|
{
|
|
DT_OBSTACLE_EMPTY,
|
|
DT_OBSTACLE_PROCESSING,
|
|
DT_OBSTACLE_PROCESSED,
|
|
DT_OBSTACLE_REMOVING,
|
|
};
|
|
|
|
enum ObstacleType
|
|
{
|
|
DT_OBSTACLE_CYLINDER,
|
|
DT_OBSTACLE_BOX, // AABB
|
|
DT_OBSTACLE_ORIENTED_BOX, // OBB
|
|
};
|
|
|
|
struct dtObstacleCylinder
|
|
{
|
|
float pos[ 3 ];
|
|
float radius;
|
|
float height;
|
|
int area;
|
|
};
|
|
|
|
struct dtObstacleBox
|
|
{
|
|
float bmin[ 3 ];
|
|
float bmax[ 3 ];
|
|
int area;
|
|
};
|
|
|
|
struct dtObstacleOrientedBox
|
|
{
|
|
float center[ 3 ];
|
|
float halfExtents[ 3 ];
|
|
float rotAux[ 2 ]; //{ cos(0.5f*angle)*sin(-0.5f*angle); cos(0.5f*angle)*cos(0.5f*angle) - 0.5 }
|
|
int area;
|
|
};
|
|
|
|
static const int DT_MAX_TOUCHED_TILES = 8;
|
|
struct dtTileCacheObstacle
|
|
{
|
|
union
|
|
{
|
|
dtObstacleCylinder cylinder;
|
|
dtObstacleBox box;
|
|
dtObstacleOrientedBox orientedBox;
|
|
};
|
|
|
|
dtCompressedTileRef touched[DT_MAX_TOUCHED_TILES];
|
|
dtCompressedTileRef pending[DT_MAX_TOUCHED_TILES];
|
|
unsigned short salt;
|
|
unsigned char type;
|
|
unsigned char state;
|
|
unsigned char ntouched;
|
|
unsigned char npending;
|
|
dtTileCacheObstacle* next;
|
|
};
|
|
|
|
struct dtTileCacheParams
|
|
{
|
|
float orig[3];
|
|
float cs, ch;
|
|
int width, height;
|
|
float walkableHeight;
|
|
float walkableRadius;
|
|
float walkableClimb;
|
|
float walkableSlope;
|
|
float maxSimplificationError;
|
|
int maxTiles;
|
|
int maxObstacles;
|
|
int maxOffMeshConnections;
|
|
};
|
|
|
|
struct dtTileCacheMeshProcess
|
|
{
|
|
virtual ~dtTileCacheMeshProcess() { }
|
|
|
|
virtual void process(struct dtNavMeshCreateParams* params,
|
|
unsigned char* polyAreas, unsigned int* polyFlags) = 0;
|
|
|
|
|
|
};
|
|
|
|
|
|
class dtTileCache
|
|
{
|
|
public:
|
|
dtTileCache();
|
|
~dtTileCache();
|
|
|
|
struct dtTileCacheAlloc* getAlloc() { return m_talloc; }
|
|
struct dtTileCacheCompressor* getCompressor() { return m_tcomp; }
|
|
struct dtTileCacheMeshProcess* getMeshProcess() { return m_tmproc; }
|
|
const dtTileCacheParams* getParams() const { return &m_params; }
|
|
|
|
|
|
inline int getTileCount() const { return m_params.maxTiles; }
|
|
inline const dtCompressedTile* getTile(const int i) const { return &m_tiles[i]; }
|
|
|
|
inline int getOffMeshCount() const { return m_params.maxOffMeshConnections; }
|
|
inline int getObstacleCount() const { return m_params.maxObstacles; }
|
|
inline const dtTileCacheObstacle* getObstacle(const int i) const { return &m_obstacles[i]; }
|
|
inline const dtOffMeshConnection* getOffMeshConnection(const int i) const { return &m_offMeshConnections[i]; }
|
|
|
|
const dtTileCacheObstacle* getObstacleByRef(dtObstacleRef ref);
|
|
dtOffMeshConnection* getOffMeshConnectionByRef(dtOffMeshConnectionRef ref);
|
|
|
|
dtObstacleRef getObstacleRef(const dtTileCacheObstacle* obmin) const;
|
|
dtOffMeshConnectionRef getOffMeshRef(const dtOffMeshConnection* con) const;
|
|
|
|
dtStatus init(const dtTileCacheParams* params,
|
|
struct dtTileCacheAlloc* talloc,
|
|
struct dtTileCacheCompressor* tcomp,
|
|
struct dtTileCacheMeshProcess* tmproc);
|
|
|
|
int getTilesAt(const int tx, const int ty, dtCompressedTileRef* tiles, const int maxTiles) const ;
|
|
|
|
dtCompressedTile* getTileAt(const int tx, const int ty, const int tlayer);
|
|
dtCompressedTileRef getTileRef(const dtCompressedTile* tile) const;
|
|
const dtCompressedTile* getTileByRef(dtCompressedTileRef ref) const;
|
|
|
|
dtStatus addTile(unsigned char* data, const int dataSize, unsigned char flags, dtCompressedTileRef* result);
|
|
|
|
dtStatus removeTile(dtCompressedTileRef ref, unsigned char** data, int* dataSize);
|
|
|
|
// Cylinder obstacle.
|
|
dtStatus addObstacle(const float* pos, const float radius, const float height, const int area, dtObstacleRef* result);
|
|
|
|
dtStatus addOffMeshConnection(const float* spos, const float* epos, const float radius, const unsigned char area, const unsigned int flags, const bool bBiDirectional, dtOffMeshConnectionRef* result);
|
|
dtStatus modifyOffMeshConnection(dtOffMeshConnectionRef ConRef, const unsigned int newFlag);
|
|
|
|
// Aabb obstacle.
|
|
dtStatus addBoxObstacle(const float* bmin, const float* bmax, dtObstacleRef* result);
|
|
|
|
// Box obstacle: can be rotated in Y.
|
|
dtStatus addBoxObstacle(const float* center, const float* halfExtents, const float yRadians, dtObstacleRef* result);
|
|
|
|
dtStatus removeObstacle(const dtObstacleRef ref);
|
|
dtStatus removeOffMeshConnection(const dtOffMeshConnectionRef ref);
|
|
|
|
dtStatus queryTiles(const float* bmin, const float* bmax,
|
|
dtCompressedTileRef* results, int* resultCount, const int maxResults) const;
|
|
|
|
/// Updates the tile cache by rebuilding tiles touched by unfinished obstacle requests.
|
|
/// @param[in] dt The time step size. Currently not used.
|
|
/// @param[in] navmesh The mesh to affect when rebuilding tiles.
|
|
/// @param[out] upToDate Whether the tile cache is fully up to date with obstacle requests and tile rebuilds.
|
|
/// If the tile cache is up to date another (immediate) call to update will have no effect;
|
|
/// otherwise another call will continue processing obstacle requests and tile rebuilds.
|
|
dtStatus update(const float dt, class dtNavMesh* navmesh, bool* upToDate = 0);
|
|
|
|
dtStatus buildNavMeshTilesAt(const int tx, const int ty, class dtNavMesh* navmesh);
|
|
|
|
dtStatus buildNavMeshTile(const dtCompressedTileRef ref, class dtNavMesh* navmesh);
|
|
|
|
void calcTightTileBounds(const struct dtTileCacheLayerHeader* header, float* bmin, float* bmax) const;
|
|
|
|
void getObstacleBounds(const struct dtTileCacheObstacle* ob, float* bmin, float* bmax) const;
|
|
|
|
|
|
/// Encodes a tile id.
|
|
inline dtCompressedTileRef encodeTileId(unsigned int salt, unsigned int it) const
|
|
{
|
|
return ((dtCompressedTileRef)salt << m_tileBits) | (dtCompressedTileRef)it;
|
|
}
|
|
|
|
/// Decodes a tile salt.
|
|
inline unsigned int decodeTileIdSalt(dtCompressedTileRef ref) const
|
|
{
|
|
const dtCompressedTileRef saltMask = ((dtCompressedTileRef)1<<m_saltBits)-1;
|
|
return (unsigned int)((ref >> m_tileBits) & saltMask);
|
|
}
|
|
|
|
/// Decodes a tile id.
|
|
inline unsigned int decodeTileIdTile(dtCompressedTileRef ref) const
|
|
{
|
|
const dtCompressedTileRef tileMask = ((dtCompressedTileRef)1<<m_tileBits)-1;
|
|
return (unsigned int)(ref & tileMask);
|
|
}
|
|
|
|
/// Encodes an obstacle id.
|
|
inline dtObstacleRef encodeObstacleId(unsigned int salt, unsigned int it) const
|
|
{
|
|
return ((dtObstacleRef)salt << 16) | (dtObstacleRef)it;
|
|
}
|
|
|
|
/// Encodes an obstacle id.
|
|
inline dtOffMeshConnectionRef encodeOffMeshId(unsigned int salt, unsigned int it) const
|
|
{
|
|
return ((dtOffMeshConnectionRef)salt << 16) | (dtOffMeshConnectionRef)it;
|
|
}
|
|
|
|
/// Decodes an obstacle salt.
|
|
inline unsigned int decodeObstacleIdSalt(dtObstacleRef ref) const
|
|
{
|
|
const dtObstacleRef saltMask = ((dtObstacleRef)1<<16)-1;
|
|
return (unsigned int)((ref >> 16) & saltMask);
|
|
}
|
|
|
|
inline unsigned int decodeOffMeshIdSalt(dtOffMeshConnectionRef ref) const
|
|
{
|
|
const dtOffMeshConnectionRef saltMask = ((dtOffMeshConnectionRef)1 << 16) - 1;
|
|
return (unsigned int)((ref >> 16) & saltMask);
|
|
}
|
|
|
|
/// Decodes an obstacle id.
|
|
inline unsigned int decodeObstacleIdObstacle(dtObstacleRef ref) const
|
|
{
|
|
const dtObstacleRef tileMask = ((dtObstacleRef)1<<16)-1;
|
|
return (unsigned int)(ref & tileMask);
|
|
}
|
|
|
|
inline unsigned int decodeOffMeshIdCon(dtOffMeshConnectionRef ref) const
|
|
{
|
|
const dtOffMeshConnectionRef tileMask = ((dtOffMeshConnectionRef)1 << 16) - 1;
|
|
return (unsigned int)(ref & tileMask);
|
|
}
|
|
|
|
|
|
private:
|
|
// Explicitly disabled copy constructor and copy assignment operator.
|
|
dtTileCache(const dtTileCache&);
|
|
dtTileCache& operator=(const dtTileCache&);
|
|
|
|
enum ObstacleRequestAction
|
|
{
|
|
REQUEST_ADD,
|
|
REQUEST_REMOVE,
|
|
};
|
|
|
|
enum OffMeshRequestAction
|
|
{
|
|
REQUEST_OFFMESH_ADD,
|
|
REQUEST_OFFMESH_REFRESH,
|
|
REQUEST_OFFMESH_REMOVE
|
|
};
|
|
|
|
struct ObstacleRequest
|
|
{
|
|
int action;
|
|
dtObstacleRef ref;
|
|
};
|
|
|
|
struct OffMeshRequest
|
|
{
|
|
int action;
|
|
dtOffMeshConnectionRef ref;
|
|
};
|
|
|
|
int m_tileLutSize; ///< Tile hash lookup size (must be pot).
|
|
int m_tileLutMask; ///< Tile hash lookup mask.
|
|
|
|
dtCompressedTile** m_posLookup; ///< Tile hash lookup.
|
|
dtCompressedTile* m_nextFreeTile; ///< Freelist of tiles.
|
|
dtCompressedTile* m_tiles; ///< List of tiles.
|
|
|
|
unsigned int m_saltBits; ///< Number of salt bits in the tile ID.
|
|
unsigned int m_tileBits; ///< Number of tile bits in the tile ID.
|
|
|
|
dtTileCacheParams m_params;
|
|
|
|
dtTileCacheAlloc* m_talloc;
|
|
dtTileCacheCompressor* m_tcomp;
|
|
dtTileCacheMeshProcess* m_tmproc;
|
|
|
|
dtTileCacheObstacle* m_obstacles;
|
|
dtTileCacheObstacle* m_nextFreeObstacle;
|
|
|
|
dtOffMeshConnection* m_offMeshConnections;
|
|
dtOffMeshConnection* m_nextFreeOffMeshConnection;
|
|
|
|
static const int MAX_REQUESTS = 512;
|
|
ObstacleRequest m_reqs[MAX_REQUESTS];
|
|
int m_nreqs;
|
|
|
|
OffMeshRequest m_OffMeshReqs[MAX_REQUESTS];
|
|
int m_nOffMeshReqs;
|
|
|
|
static const int MAX_UPDATE = 512;
|
|
dtCompressedTileRef m_update[MAX_UPDATE];
|
|
int m_nupdate;
|
|
};
|
|
|
|
dtTileCache* dtAllocTileCache();
|
|
void dtFreeTileCache(dtTileCache* tc);
|
|
|
|
#endif
|