forked from mirror/DotRecast
fix bug where return value of dynamic update result is reversed
This commit is contained in:
parent
668ebd0128
commit
26a1dfddeb
|
@ -3,5 +3,7 @@
|
|||
public interface IRcRand
|
||||
{
|
||||
float Next();
|
||||
double NextDouble();
|
||||
int NextInt32();
|
||||
}
|
||||
}
|
|
@ -6,9 +6,13 @@ namespace DotRecast.Core
|
|||
{
|
||||
private readonly Random _r;
|
||||
|
||||
public RcRand()
|
||||
public RcRand() : this(new Random())
|
||||
{
|
||||
_r = new Random();
|
||||
}
|
||||
|
||||
public RcRand(Random r)
|
||||
{
|
||||
_r = r;
|
||||
}
|
||||
|
||||
public RcRand(long seed)
|
||||
|
@ -21,6 +25,11 @@ namespace DotRecast.Core
|
|||
return (float)_r.NextDouble();
|
||||
}
|
||||
|
||||
public double NextDouble()
|
||||
{
|
||||
return _r.NextDouble();
|
||||
}
|
||||
|
||||
public int NextInt32()
|
||||
{
|
||||
return _r.Next();
|
||||
|
|
|
@ -40,7 +40,7 @@ namespace DotRecast.Detour.Dynamic
|
|||
private readonly BlockingCollection<IDtDaynmicTileJob> updateQueue = new BlockingCollection<IDtDaynmicTileJob>();
|
||||
private readonly RcAtomicLong currentColliderId = new RcAtomicLong(0);
|
||||
private DtNavMesh _navMesh;
|
||||
private bool dirty = true;
|
||||
private bool _dirty = true;
|
||||
|
||||
public DtDynamicNavMesh(DtVoxelFile voxelFile)
|
||||
{
|
||||
|
@ -105,29 +105,6 @@ namespace DotRecast.Detour.Dynamic
|
|||
updateQueue.Add(new DtDynamicTileColliderRemovalJob(colliderId, GetTilesByCollider(colliderId)));
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform full build of the nav mesh
|
||||
*/
|
||||
public void Build()
|
||||
{
|
||||
ProcessQueue();
|
||||
Rebuild(_tiles.Values);
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform incremental update of the nav mesh
|
||||
*/
|
||||
public bool Update()
|
||||
{
|
||||
return Rebuild(ProcessQueue());
|
||||
}
|
||||
|
||||
private bool Rebuild(ICollection<DtDynamicTile> stream)
|
||||
{
|
||||
foreach (var dynamicTile in stream)
|
||||
Rebuild(dynamicTile);
|
||||
return UpdateNavMesh();
|
||||
}
|
||||
|
||||
private HashSet<DtDynamicTile> ProcessQueue()
|
||||
{
|
||||
|
@ -159,27 +136,49 @@ namespace DotRecast.Detour.Dynamic
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform full build concurrently using the given {@link ExecutorService}
|
||||
*/
|
||||
public Task<bool> Build(TaskFactory executor)
|
||||
// Perform full build of the navmesh
|
||||
public void Build()
|
||||
{
|
||||
ProcessQueue();
|
||||
Rebuild(_tiles.Values);
|
||||
}
|
||||
|
||||
// Perform full build concurrently using the given {@link ExecutorService}
|
||||
public bool Build(TaskFactory executor)
|
||||
{
|
||||
ProcessQueue();
|
||||
return Rebuild(_tiles.Values, executor);
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform incremental update concurrently using the given {@link ExecutorService}
|
||||
*/
|
||||
public Task<bool> Update(TaskFactory executor)
|
||||
|
||||
// Perform incremental update of the navmesh
|
||||
public bool Update()
|
||||
{
|
||||
return Rebuild(ProcessQueue());
|
||||
}
|
||||
|
||||
// Perform incremental update concurrently using the given {@link ExecutorService}
|
||||
public bool Update(TaskFactory executor)
|
||||
{
|
||||
return Rebuild(ProcessQueue(), executor);
|
||||
}
|
||||
|
||||
private Task<bool> Rebuild(ICollection<DtDynamicTile> tiles, TaskFactory executor)
|
||||
private bool Rebuild(ICollection<DtDynamicTile> tiles)
|
||||
{
|
||||
var tasks = tiles.Select(tile => executor.StartNew(() => Rebuild(tile))).ToArray();
|
||||
return Task.WhenAll(tasks).ContinueWith(k => UpdateNavMesh());
|
||||
foreach (var tile in tiles)
|
||||
Rebuild(tile);
|
||||
|
||||
return UpdateNavMesh();
|
||||
}
|
||||
|
||||
private bool Rebuild(ICollection<DtDynamicTile> tiles, TaskFactory executor)
|
||||
{
|
||||
var tasks = tiles
|
||||
.Select(tile => executor.StartNew(() => Rebuild(tile)))
|
||||
.ToArray();
|
||||
|
||||
Task.WaitAll(tasks);
|
||||
return UpdateNavMesh();
|
||||
}
|
||||
|
||||
private ICollection<DtDynamicTile> GetTiles(float[] bounds)
|
||||
|
@ -218,19 +217,19 @@ namespace DotRecast.Detour.Dynamic
|
|||
{
|
||||
DtNavMeshCreateParams option = new DtNavMeshCreateParams();
|
||||
option.walkableHeight = config.walkableHeight;
|
||||
dirty = dirty | tile.Build(builder, config, _context);
|
||||
_dirty = _dirty | tile.Build(builder, config, _context);
|
||||
}
|
||||
|
||||
private bool UpdateNavMesh()
|
||||
{
|
||||
if (dirty)
|
||||
if (_dirty)
|
||||
{
|
||||
DtNavMesh navMesh = new DtNavMesh(navMeshParams, MAX_VERTS_PER_POLY);
|
||||
foreach (var t in _tiles.Values)
|
||||
t.AddTo(navMesh);
|
||||
|
||||
this._navMesh = navMesh;
|
||||
dirty = false;
|
||||
_navMesh = navMesh;
|
||||
_dirty = false;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -91,7 +91,7 @@ public class DynamicUpdateSampleTool : ISampleTool
|
|||
var bridgeGeom = DemoInputGeomProvider.LoadFile("bridge.obj");
|
||||
var houseGeom = DemoInputGeomProvider.LoadFile("house.obj");
|
||||
var convexGeom = DemoInputGeomProvider.LoadFile("convex.obj");
|
||||
_tool = new(Random.Shared, bridgeGeom, houseGeom, convexGeom);
|
||||
_tool = new(new RcRand(Random.Shared), bridgeGeom, houseGeom, convexGeom);
|
||||
executor = Task.Factory;
|
||||
}
|
||||
|
||||
|
@ -406,7 +406,7 @@ public class DynamicUpdateSampleTool : ISampleTool
|
|||
long t = RcFrequency.Ticks;
|
||||
try
|
||||
{
|
||||
bool updated = _tool.UpdateDynaMesh(executor);
|
||||
bool updated = _tool.Update(executor);
|
||||
if (updated)
|
||||
{
|
||||
buildTime = (RcFrequency.Ticks - t) / TimeSpan.TicksPerMillisecond;
|
||||
|
@ -450,7 +450,7 @@ public class DynamicUpdateSampleTool : ISampleTool
|
|||
long t = RcFrequency.Ticks;
|
||||
try
|
||||
{
|
||||
var _ = dynaMesh.Build(executor).Result;
|
||||
var _ = dynaMesh.Build(executor);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
|
|
|
@ -18,12 +18,12 @@ namespace DotRecast.Recast.Toolset.Tools
|
|||
private DtDynamicNavMesh dynaMesh;
|
||||
private readonly Dictionary<long, RcGizmo> colliderGizmos;
|
||||
|
||||
private readonly Random random;
|
||||
private readonly IRcRand random;
|
||||
private readonly DemoInputGeomProvider bridgeGeom;
|
||||
private readonly DemoInputGeomProvider houseGeom;
|
||||
private readonly DemoInputGeomProvider convexGeom;
|
||||
|
||||
public RcDynamicUpdateTool(Random rand, DemoInputGeomProvider bridgeGeom, DemoInputGeomProvider houseGeom, DemoInputGeomProvider convexGeom)
|
||||
public RcDynamicUpdateTool(IRcRand rand, DemoInputGeomProvider bridgeGeom, DemoInputGeomProvider houseGeom, DemoInputGeomProvider convexGeom)
|
||||
{
|
||||
this.colliderGizmos = new Dictionary<long, RcGizmo>();
|
||||
this.random = rand;
|
||||
|
@ -339,20 +339,14 @@ namespace DotRecast.Recast.Toolset.Tools
|
|||
return resultvector;
|
||||
}
|
||||
|
||||
public bool UpdateDynaMesh(TaskFactory executor)
|
||||
public bool Update(TaskFactory executor)
|
||||
{
|
||||
if (dynaMesh == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
bool updated = dynaMesh.Update(executor).Result;
|
||||
if (updated)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
return dynaMesh.Update(executor);
|
||||
}
|
||||
|
||||
public bool Raycast(RcVec3f spos, RcVec3f epos, out float hitPos, out RcVec3f raycastHitPos)
|
||||
|
|
|
@ -10,7 +10,6 @@ using NUnit.Framework;
|
|||
|
||||
namespace DotRecast.Detour.Dynamic.Test;
|
||||
|
||||
|
||||
public class DynamicNavMeshTest
|
||||
{
|
||||
private static readonly RcVec3f START_POS = new RcVec3f(70.87453f, 0.0010070801f, 86.69021f);
|
||||
|
@ -32,9 +31,7 @@ public class DynamicNavMeshTest
|
|||
// create dynamic navmesh
|
||||
DtDynamicNavMesh mesh = new DtDynamicNavMesh(f);
|
||||
// build navmesh asynchronously using multiple threads
|
||||
Task<bool> future = mesh.Build(Task.Factory);
|
||||
// wait for build to complete
|
||||
bool _ = future.Result;
|
||||
mesh.Build(Task.Factory);
|
||||
|
||||
// create new query
|
||||
DtNavMeshQuery query = new DtNavMeshQuery(mesh.NavMesh());
|
||||
|
@ -54,9 +51,8 @@ public class DynamicNavMeshTest
|
|||
long colliderId = mesh.AddCollider(colldier);
|
||||
|
||||
// update navmesh asynchronously
|
||||
future = mesh.Update(Task.Factory);
|
||||
// wait for update to complete
|
||||
_ = future.Result;
|
||||
mesh.Update(Task.Factory);
|
||||
|
||||
// create new query
|
||||
query = new DtNavMeshQuery(mesh.NavMesh());
|
||||
|
||||
|
@ -70,9 +66,7 @@ public class DynamicNavMeshTest
|
|||
// remove obstacle
|
||||
mesh.RemoveCollider(colliderId);
|
||||
// update navmesh asynchronously
|
||||
future = mesh.Update(Task.Factory);
|
||||
// wait for update to complete
|
||||
_ = future.Result;
|
||||
mesh.Update(Task.Factory);
|
||||
// create new query
|
||||
query = new DtNavMeshQuery(mesh.NavMesh());
|
||||
|
||||
|
|
|
@ -31,7 +31,6 @@ using NUnit.Framework;
|
|||
|
||||
namespace DotRecast.Detour.Dynamic.Test;
|
||||
|
||||
|
||||
public class VoxelQueryTest
|
||||
{
|
||||
private const int TILE_WIDTH = 100;
|
||||
|
@ -101,12 +100,12 @@ public class VoxelQueryTest
|
|||
// load voxels from file
|
||||
DtVoxelFileReader reader = new DtVoxelFileReader(DtVoxelTileLZ4ForTestCompressor.Shared);
|
||||
DtVoxelFile f = reader.Read(br);
|
||||
|
||||
// create dynamic navmesh
|
||||
var mesh = new DtDynamicNavMesh(f);
|
||||
|
||||
// build navmesh asynchronously using multiple threads
|
||||
Task<bool> future = mesh.Build(Task.Factory);
|
||||
// wait for build to complete
|
||||
var _ = future.Result;
|
||||
mesh.Build(Task.Factory);
|
||||
return mesh;
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue