navMesh.h

Engine/source/navigation/navMesh.h

More...

Classes:

class

Represents a set of bounds within which a Recast navigation mesh is generated.

class

Intermediate data for tile creation.

Public Typedefs

NavMeshWaterMethod 

Detailed Description

Public Typedefs

typedef NavMesh::WaterMethod NavMeshWaterMethod 

Public Functions

DefineEnumType(NavMeshWaterMethod )

  1
  2//-----------------------------------------------------------------------------
  3// Copyright (c) 2014 Daniel Buckmaster
  4//
  5// Permission is hereby granted, free of charge, to any person obtaining a copy
  6// of this software and associated documentation files (the "Software"), to
  7// deal in the Software without restriction, including without limitation the
  8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  9// sell copies of the Software, and to permit persons to whom the Software is
 10// furnished to do so, subject to the following conditions:
 11//
 12// The above copyright notice and this permission notice shall be included in
 13// all copies or substantial portions of the Software.
 14//
 15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
 21// IN THE SOFTWARE.
 22//-----------------------------------------------------------------------------
 23
 24#ifndef _NAVMESH_H_
 25#define _NAVMESH_H_
 26
 27#include <queue>
 28
 29#include "scene/sceneObject.h"
 30#include "collision/concretePolyList.h"
 31#include "recastPolyList.h"
 32#include "util/messaging/eventManager.h"
 33
 34#include "torqueRecast.h"
 35#include "duDebugDrawTorque.h"
 36#include "coverPoint.h"
 37
 38#include <Recast.h>
 39#include <DetourNavMesh.h>
 40#include <DetourNavMeshBuilder.h>
 41#include <DebugDraw.h>
 42#include <DetourNavMeshQuery.h>
 43
 44/// @class NavMesh
 45/// Represents a set of bounds within which a Recast navigation mesh is generated.
 46/// @see NavMeshPolyList
 47/// @see Trigger
 48class NavMesh : public SceneObject {
 49   typedef SceneObject Parent;
 50   friend class NavPath;
 51
 52public:
 53   /// @name NavMesh build
 54   /// @{
 55
 56   /// Initiates the navmesh build process, which includes notifying the
 57   /// clients and posting an event.
 58   bool build(bool background = true, bool saveIntermediates = false);
 59   /// Stop a build in progress.
 60   void cancelBuild();
 61   /// Generate cover points from a nav mesh.
 62   bool createCoverPoints();
 63   /// Remove all cover points
 64   void deleteCoverPoints();
 65
 66   /// Save the navmesh to a file.
 67   bool save();
 68   /// Load a saved navmesh from a file.
 69   bool load();
 70
 71   /// Instantly rebuild the tiles in the navmesh that overlap the box.
 72   void buildTiles(const Box3F &box);
 73
 74   /// Instantly rebuild a specific tile.
 75   void buildTile(const U32 &tile);
 76
 77   /// Rebuild parts of the navmesh where links have changed.
 78   void buildLinks();
 79
 80   /// Data file to store this nav mesh in. (From engine executable dir.)
 81   StringTableEntry mFileName;
 82
 83   /// Name of the SimSet to store cover points in. (Usually a SimGroup.)
 84   StringTableEntry mCoverSet;
 85
 86   /// Cell width and height.
 87   F32 mCellSize, mCellHeight;
 88   /// @name Actor data
 89   /// @{
 90   F32 mWalkableHeight,
 91      mWalkableClimb,
 92      mWalkableRadius,
 93      mWalkableSlope;
 94   /// @}
 95   /// @name Generation data
 96   /// @{
 97   U32 mBorderSize;
 98   F32 mDetailSampleDist, mDetailSampleMaxError;
 99   U32 mMaxEdgeLen;
100   F32 mMaxSimplificationError;
101   static const U32 mMaxVertsPerPoly;
102   U32 mMinRegionArea;
103   U32 mMergeRegionArea;
104   F32 mTileSize;
105   U32 mMaxPolysPerTile;
106   /// @}
107
108   /// @name Water
109   /// @{
110   enum WaterMethod {
111      Ignore,
112      Solid,
113      Impassable
114   };
115
116   WaterMethod mWaterMethod;
117   /// @}
118
119   /// @}
120
121   /// Return the index of the tile included by this point.
122   S32 getTile(const Point3F& pos);
123
124   /// Return the box of a given tile.
125   Box3F getTileBox(U32 id);
126
127   /// @name Links
128   /// @{
129
130   /// Add an off-mesh link.
131   S32 addLink(const Point3F &from, const Point3F &to, U32 flags = 0);
132
133   /// Get the ID of the off-mesh link near the point.
134   S32 getLink(const Point3F &pos);
135
136   /// Get the number of links this mesh has.
137   S32 getLinkCount();
138
139   /// Get the starting point of a link.
140   Point3F getLinkStart(U32 idx);
141
142   /// Get the ending point of a link.
143   Point3F getLinkEnd(U32 idx);
144
145   /// Get the flags used by a link.
146   LinkData getLinkFlags(U32 idx);
147
148   /// Set flags used by a link.
149   void setLinkFlags(U32 idx, const LinkData &d);
150
151   /// Set the selected state of a link.
152   void selectLink(U32 idx, bool select, bool hover = true);
153
154   /// Delete the selected link.
155   void deleteLink(U32 idx);
156
157   /// @}
158
159   /// Should small characters use this mesh?
160   bool mSmallCharacters;
161   /// Should regular-sized characters use this mesh?
162   bool mRegularCharacters;
163   /// Should large characters use this mesh?
164   bool mLargeCharacters;
165   /// Should vehicles use this mesh?
166   bool mVehicles;
167
168   /// @name Annotations
169   /// @{
170   /* not implemented
171   /// Should we automatically generate jump-down links?
172   bool mJumpDownLinks;
173   /// Height of a 'small' jump link.
174   F32 mJumpLinkSmall;
175   /// Height of a 'large' jump link.
176   F32 mJumpLinkLarge;
177   */
178   /// Distance to search for cover.
179   F32 mCoverDist;
180
181   /// Distance to search horizontally when peeking around cover.
182   F32 mPeekDist;
183
184   /// Add cover to walls that don't have corners?
185   bool mInnerCover;
186
187   /// @}
188
189   /// @name SimObject
190   /// @{
191
192   virtual void onEditorEnable();
193   virtual void onEditorDisable();
194
195   void write(Stream &stream, U32 tabStop, U32 flags);
196
197   /// @}
198
199   /// @name SceneObject
200   /// @{
201
202   static void initPersistFields();
203
204   bool onAdd();
205   void onRemove();
206
207   enum flags {
208      BuildFlag    = Parent::NextFreeMask << 0,
209      LoadFlag     = Parent::NextFreeMask << 1,
210      NextFreeMask = Parent::NextFreeMask << 2,
211   };
212
213   U32 packUpdate(NetConnection *conn, U32 mask, BitStream *stream);
214   void unpackUpdate(NetConnection *conn, BitStream *stream);
215
216   void setTransform(const MatrixF &mat);
217   void setScale(const VectorF &scale);
218
219   /// @}
220
221   /// @name ProcessObject
222   /// @{
223
224   void processTick(const Move *move);
225
226   /// @}
227
228   /// @name Rendering
229   /// @{
230
231   void prepRenderImage(SceneRenderState *state);
232   void render(ObjectRenderInst *ri, SceneRenderState *state, BaseMatInstance *overrideMat);
233   void renderLinks(duDebugDraw &dd);
234   void renderTileData(duDebugDrawTorque &dd, U32 tile);
235
236   bool mAlwaysRender;
237
238   /// @}
239
240   NavMesh();
241   ~NavMesh();
242   DECLARE_CONOBJECT(NavMesh);
243
244   /// Return the server-side NavMesh SimSet.
245   static SimSet *getServerSet();
246
247   /// Return the EventManager for all NavMeshes.
248   static EventManager *getEventManager();
249
250   void inspectPostApply();
251
252protected:
253
254   dtNavMesh const* getNavMesh() { return nm; }
255
256private:
257   /// Generates a navigation mesh for the collection of objects in this
258   /// mesh. Returns true if successful. Stores the created mesh in tnm.
259   bool generateMesh();
260
261   /// Builds the next tile in the dirty list.
262   void buildNextTile();
263
264   /// Save imtermediate navmesh creation data?
265   bool mSaveIntermediates;
266
267   /// @name Tiles
268   /// @{
269
270   struct Tile {
271      /// Torque-space world box of this tile.
272      Box3F box;
273      /// Local coordinates of this box.
274      U32 x, y;
275      /// Recast min and max points.
276      F32 bmin[3], bmax[3];
277      /// Default constructor.
278      Tile() : box(Box3F::Invalid), x(0), y(0)
279      {
280         bmin[0] = bmin[1] = bmin[2] = bmax[0] = bmax[1] = bmax[2] = 0.0f;
281      }
282      /// Value constructor.
283      Tile(const Box3F &b, U32 _x, U32 _y, const F32 *min, const F32 *max)
284         : box(b), x(_x), y(_y)
285      {
286         rcVcopy(bmin, min);
287         rcVcopy(bmax, max);
288      }
289   };
290
291   /// Intermediate data for tile creation.
292   struct TileData {
293      RecastPolyList          geom;
294      rcHeightfield        *hf;
295      rcCompactHeightfield *chf;
296      rcContourSet         *cs;
297      rcPolyMesh           *pm;
298      rcPolyMeshDetail     *pmd;
299      TileData()
300      {
301         hf = NULL;
302         chf = NULL;
303         cs = NULL;
304         pm = NULL;
305         pmd = NULL;
306      }
307      void freeAll()
308      {
309         geom.clear();
310         rcFreeHeightField(hf);
311         rcFreeCompactHeightfield(chf);
312         rcFreeContourSet(cs);
313         rcFreePolyMesh(pm);
314         rcFreePolyMeshDetail(pmd);
315      }
316      ~TileData()
317      {
318         freeAll();
319      }
320   };
321
322   /// List of tiles.
323   Vector<Tile> mTiles;
324
325   /// List of tile intermediate data.
326   Vector<TileData> mTileData;
327
328   /// List of indices to the tile array which are dirty.
329   Vector<U32> mDirtyTiles;
330
331   /// Update tile dimensions.
332   void updateTiles(bool dirty = false);
333
334   /// Generates navmesh data for a single tile.
335   unsigned char *buildTileData(const Tile &tile, TileData &data, U32 &dataSize);
336
337   /// @}
338
339   /// @name Off-mesh links
340   /// @{
341
342   enum SelectState {
343      Unselected,
344      Hovered,
345      Selected
346   };
347
348   Vector<F32> mLinkVerts;            ///< Coordinates of each link vertex
349   Vector<bool> mLinksUnsynced;       ///< Are the editor links unsynced from the mesh?
350   Vector<F32> mLinkRads;             ///< Radius of each link
351   Vector<U8> mLinkDirs;              ///< Direction (one-way or bidirectional)
352   Vector<U8> mLinkAreas;             ///< Area ID
353   Vector<U16> mLinkFlags; ///< Flags
354   Vector<U32> mLinkIDs;              ///< ID number of each link
355   Vector<U8> mLinkSelectStates;      ///< Selection state of links
356   Vector<bool> mDeleteLinks;         ///< Link will be deleted next build.
357
358   U32 mCurLinkID;
359
360   void eraseLink(U32 idx);
361   void eraseLinks();
362   void setLinkCount(U32 c);
363
364   /// @}
365
366   /// @name Intermediate data
367   /// @{
368
369   /// Config struct.
370   rcConfig cfg;
371
372   /// Updates our config from console members.
373   void updateConfig();
374
375   dtNavMesh *nm;
376   rcContext *ctx;
377
378   /// @}
379
380   /// @name Cover
381   /// @{
382
383   struct CoverPointData {
384      MatrixF trans;
385      CoverPoint::Size size;
386      bool peek[3];
387   };
388
389   /// Attempt to place cover points along a given edge.
390   bool testEdgeCover(const Point3F &pos, const VectorF &dir, CoverPointData &data);
391
392   /// @}
393
394   /// Used to perform non-standard validation. detailSampleDist can be 0, or >= 0.9.
395   static bool setProtectedDetailSampleDist(void *obj, const char *index, const char *data);
396
397   /// Updates the client when we check the alwaysRender option.
398   static bool setProtectedAlwaysRender(void *obj, const char *index, const char *data);
399
400   /// @name Threaded updates
401   /// @{
402
403   /// A simple flag to say we are building.
404   bool mBuilding;
405
406   /// @}
407
408   /// @name Rendering
409   /// @{
410
411   duDebugDrawTorque mDbgDraw;
412
413   void renderToDrawer();
414
415   /// @}
416
417   /// Server-side set for all NavMesh objects.
418   static SimObjectPtr<SimSet> smServerSet;
419
420   /// Use this object to manage update events.
421   static SimObjectPtr<EventManager> smEventManager;
422};
423
424typedef NavMesh::WaterMethod NavMeshWaterMethod;
425DefineEnumType(NavMeshWaterMethod);
426
427#endif
428