forked from bit/DotRecastNetSim
change FindCorners
This commit is contained in:
parent
6433ce8d95
commit
9c42e58e86
|
@ -942,7 +942,7 @@ namespace DotRecast.Detour.Crowd
|
|||
}
|
||||
|
||||
// Find corners for steering
|
||||
ag.corners = ag.corridor.FindCorners(DT_CROWDAGENT_MAX_CORNERS, _navQuery, _filters[ag.option.queryFilterType]);
|
||||
ag.corridor.FindCorners(ref ag.corners, DT_CROWDAGENT_MAX_CORNERS, _navQuery, _filters[ag.option.queryFilterType]);
|
||||
|
||||
// Check to see if the corner after the next corner is directly visible,
|
||||
// and short cut to there.
|
||||
|
|
|
@ -234,16 +234,14 @@ namespace DotRecast.Detour.Crowd
|
|||
* @param[in] navquery The query object used to build the corridor.
|
||||
* @return Corners
|
||||
*/
|
||||
public List<StraightPathItem> FindCorners(int maxCorners, DtNavMeshQuery navquery, IDtQueryFilter filter)
|
||||
public int FindCorners(ref List<StraightPathItem> corners, int maxCorners, DtNavMeshQuery navquery, IDtQueryFilter filter)
|
||||
{
|
||||
List<StraightPathItem> path = new List<StraightPathItem>();
|
||||
Result<List<StraightPathItem>> result = navquery.FindStraightPath(m_pos, m_target, m_path, maxCorners, 0);
|
||||
var result = navquery.FindStraightPath(m_pos, m_target, m_path, ref corners, maxCorners, 0);
|
||||
if (result.Succeeded())
|
||||
{
|
||||
path = result.result;
|
||||
// Prune points in the beginning of the path which are too close.
|
||||
int start = 0;
|
||||
foreach (StraightPathItem spi in path)
|
||||
foreach (StraightPathItem spi in corners)
|
||||
{
|
||||
if ((spi.GetFlags() & DtNavMeshQuery.DT_STRAIGHTPATH_OFFMESH_CONNECTION) != 0
|
||||
|| RcVec3f.Dist2DSqr(spi.GetPos(), m_pos) > MIN_TARGET_DIST)
|
||||
|
@ -254,11 +252,11 @@ namespace DotRecast.Detour.Crowd
|
|||
start++;
|
||||
}
|
||||
|
||||
int end = path.Count;
|
||||
int end = corners.Count;
|
||||
// Prune points after an off-mesh connection.
|
||||
for (int i = start; i < path.Count; i++)
|
||||
for (int i = start; i < corners.Count; i++)
|
||||
{
|
||||
StraightPathItem spi = path[i];
|
||||
StraightPathItem spi = corners[i];
|
||||
if ((spi.GetFlags() & DtNavMeshQuery.DT_STRAIGHTPATH_OFFMESH_CONNECTION) != 0)
|
||||
{
|
||||
end = i + 1;
|
||||
|
@ -266,10 +264,10 @@ namespace DotRecast.Detour.Crowd
|
|||
}
|
||||
}
|
||||
|
||||
path = path.GetRange(start, end - start);
|
||||
corners = corners.GetRange(start, end - start);
|
||||
}
|
||||
|
||||
return path;
|
||||
return corners.Count;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -1422,7 +1422,7 @@ namespace DotRecast.Detour
|
|||
return Results.Of(status, path);
|
||||
}
|
||||
|
||||
protected DtStatus AppendVertex(RcVec3f pos, int flags, long refs, List<StraightPathItem> straightPath,
|
||||
protected DtStatus AppendVertex(RcVec3f pos, int flags, long refs, ref List<StraightPathItem> straightPath,
|
||||
int maxStraightPath)
|
||||
{
|
||||
if (straightPath.Count > 0 && DetourCommon.VEqual(straightPath[straightPath.Count - 1].pos, pos))
|
||||
|
@ -1450,7 +1450,7 @@ namespace DotRecast.Detour
|
|||
}
|
||||
|
||||
protected DtStatus AppendPortals(int startIdx, int endIdx, RcVec3f endPos, List<long> path,
|
||||
List<StraightPathItem> straightPath, int maxStraightPath, int options)
|
||||
ref List<StraightPathItem> straightPath, int maxStraightPath, int options)
|
||||
{
|
||||
var startPos = straightPath[straightPath.Count - 1].pos;
|
||||
// Append or update last vertex
|
||||
|
@ -1491,7 +1491,7 @@ namespace DotRecast.Detour
|
|||
if (DetourCommon.IntersectSegSeg2D(startPos, endPos, left, right, out var _, out var t))
|
||||
{
|
||||
var pt = RcVec3f.Lerp(left, right, t);
|
||||
stat = AppendVertex(pt, 0, path[i + 1], straightPath, maxStraightPath);
|
||||
stat = AppendVertex(pt, 0, path[i + 1], ref straightPath, maxStraightPath);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return stat;
|
||||
|
@ -1503,7 +1503,6 @@ namespace DotRecast.Detour
|
|||
}
|
||||
|
||||
/// @par
|
||||
/// Finds the straight path from the start to the end position within the polygon corridor.
|
||||
///
|
||||
/// This method peforms what is often called 'string pulling'.
|
||||
///
|
||||
|
@ -1520,41 +1519,45 @@ namespace DotRecast.Detour
|
|||
/// they will be filled as far as possible from the start toward the end
|
||||
/// position.
|
||||
///
|
||||
/// Finds the straight path from the start to the end position within the polygon corridor.
|
||||
/// @param[in] startPos Path start position. [(x, y, z)]
|
||||
/// @param[in] endPos Path end position. [(x, y, z)]
|
||||
/// @param[in] path An array of polygon references that represent the path corridor.
|
||||
/// @param[in] pathSize The number of polygons in the @p path array.
|
||||
/// @param[out] straightPath Points describing the straight path. [(x, y, z) * @p straightPathCount].
|
||||
/// @param[in] maxStraightPath The maximum number of points the straight path arrays can hold. [Limit: > 0]
|
||||
/// @param[in] options Query options. (see: #dtStraightPathOptions)
|
||||
/// @returns The status flags for the query.
|
||||
public virtual Result<List<StraightPathItem>> FindStraightPath(RcVec3f startPos, RcVec3f endPos, List<long> path,
|
||||
public virtual DtStatus FindStraightPath(RcVec3f startPos, RcVec3f endPos, List<long> path,
|
||||
ref List<StraightPathItem> straightPath,
|
||||
int maxStraightPath, int options)
|
||||
{
|
||||
List<StraightPathItem> straightPath = new List<StraightPathItem>();
|
||||
straightPath.Clear();
|
||||
|
||||
if (!RcVec3f.IsFinite(startPos) || !RcVec3f.IsFinite(endPos)
|
||||
|| null == path || 0 == path.Count || path[0] == 0 || maxStraightPath <= 0)
|
||||
{
|
||||
return Results.InvalidParam<List<StraightPathItem>>();
|
||||
return DtStatus.DT_FAILURE | DtStatus.DT_INVALID_PARAM;
|
||||
}
|
||||
|
||||
// TODO: Should this be callers responsibility?
|
||||
var closestStartPosRes = ClosestPointOnPolyBoundary(path[0], startPos, out var closestStartPos);
|
||||
if (closestStartPosRes.Failed())
|
||||
{
|
||||
return Results.InvalidParam<List<StraightPathItem>>("Cannot find start position");
|
||||
return DtStatus.DT_FAILURE | DtStatus.DT_INVALID_PARAM;
|
||||
}
|
||||
|
||||
var closestEndPosRes = ClosestPointOnPolyBoundary(path[path.Count - 1], endPos, out var closestEndPos);
|
||||
if (closestEndPosRes.Failed())
|
||||
{
|
||||
return Results.InvalidParam<List<StraightPathItem>>("Cannot find end position");
|
||||
return DtStatus.DT_FAILURE | DtStatus.DT_INVALID_PARAM;
|
||||
}
|
||||
|
||||
// Add start point.
|
||||
DtStatus stat = AppendVertex(closestStartPos, DT_STRAIGHTPATH_START, path[0], straightPath, maxStraightPath);
|
||||
DtStatus stat = AppendVertex(closestStartPos, DT_STRAIGHTPATH_START, path[0], ref straightPath, maxStraightPath);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
|
||||
if (path.Count > 1)
|
||||
|
@ -1591,19 +1594,20 @@ namespace DotRecast.Detour
|
|||
var cpStatus = ClosestPointOnPolyBoundary(path[i], endPos, out closestEndPos);
|
||||
if (cpStatus.Failed())
|
||||
{
|
||||
return Results.InvalidParam<List<StraightPathItem>>();
|
||||
return DtStatus.DT_FAILURE | DtStatus.DT_INVALID_PARAM;
|
||||
}
|
||||
|
||||
// Append portals along the current straight path segment.
|
||||
if ((options & (DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS)) != 0)
|
||||
{
|
||||
// Ignore status return value as we're just about to return anyway.
|
||||
AppendPortals(apexIndex, i, closestEndPos, path, straightPath, maxStraightPath, options);
|
||||
AppendPortals(apexIndex, i, closestEndPos, path, ref straightPath, maxStraightPath, options);
|
||||
}
|
||||
|
||||
// Ignore status return value as we're just about to return anyway.
|
||||
AppendVertex(closestEndPos, 0, path[i], straightPath, maxStraightPath);
|
||||
return Results.Success(straightPath);
|
||||
AppendVertex(closestEndPos, 0, path[i], ref straightPath, maxStraightPath);
|
||||
|
||||
return DtStatus.DT_FAILURE | DtStatus.DT_INVALID_PARAM | (straightPath.Count >= maxStraightPath ? DtStatus.DT_BUFFER_TOO_SMALL : DtStatus.DT_STATUS_NOTHING);
|
||||
}
|
||||
|
||||
// If starting really close the portal, advance.
|
||||
|
@ -1639,11 +1643,10 @@ namespace DotRecast.Detour
|
|||
// Append portals along the current straight path segment.
|
||||
if ((options & (DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS)) != 0)
|
||||
{
|
||||
stat = AppendPortals(apexIndex, leftIndex, portalLeft, path, straightPath, maxStraightPath,
|
||||
options);
|
||||
stat = AppendPortals(apexIndex, leftIndex, portalLeft, path, ref straightPath, maxStraightPath, options);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1663,10 +1666,10 @@ namespace DotRecast.Detour
|
|||
long refs = leftPolyRef;
|
||||
|
||||
// Append or update vertex
|
||||
stat = AppendVertex(portalApex, flags, refs, straightPath, maxStraightPath);
|
||||
stat = AppendVertex(portalApex, flags, refs, ref straightPath, maxStraightPath);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
|
||||
portalLeft = portalApex;
|
||||
|
@ -1696,11 +1699,10 @@ namespace DotRecast.Detour
|
|||
// Append portals along the current straight path segment.
|
||||
if ((options & (DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS)) != 0)
|
||||
{
|
||||
stat = AppendPortals(apexIndex, rightIndex, portalRight, path, straightPath,
|
||||
maxStraightPath, options);
|
||||
stat = AppendPortals(apexIndex, rightIndex, portalRight, path, ref straightPath, maxStraightPath, options);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1720,10 +1722,10 @@ namespace DotRecast.Detour
|
|||
long refs = rightPolyRef;
|
||||
|
||||
// Append or update vertex
|
||||
stat = AppendVertex(portalApex, flags, refs, straightPath, maxStraightPath);
|
||||
stat = AppendVertex(portalApex, flags, refs, ref straightPath, maxStraightPath);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
|
||||
portalLeft = portalApex;
|
||||
|
@ -1742,18 +1744,17 @@ namespace DotRecast.Detour
|
|||
// Append portals along the current straight path segment.
|
||||
if ((options & (DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS)) != 0)
|
||||
{
|
||||
stat = AppendPortals(apexIndex, path.Count - 1, closestEndPos, path, straightPath, maxStraightPath,
|
||||
options);
|
||||
stat = AppendPortals(apexIndex, path.Count - 1, closestEndPos, path, ref straightPath, maxStraightPath, options);
|
||||
if (!stat.InProgress())
|
||||
{
|
||||
return Results.Success(straightPath);
|
||||
return stat;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Ignore status return value as we're just about to return anyway.
|
||||
AppendVertex(closestEndPos, DT_STRAIGHTPATH_END, 0, straightPath, maxStraightPath);
|
||||
return Results.Success(straightPath);
|
||||
AppendVertex(closestEndPos, DT_STRAIGHTPATH_END, 0, ref straightPath, maxStraightPath);
|
||||
return DtStatus.DT_SUCCSESS | (straightPath.Count >= maxStraightPath ? DtStatus.DT_BUFFER_TOO_SMALL : DtStatus.DT_STATUS_NOTHING);
|
||||
}
|
||||
|
||||
/// @par
|
||||
|
|
|
@ -31,6 +31,7 @@ namespace DotRecast.Detour
|
|||
|
||||
// Detail information for status.
|
||||
public static readonly DtStatus DT_STATUS_DETAIL_MASK = new DtStatus(0x0ffffff);
|
||||
public static readonly DtStatus DT_STATUS_NOTHING = new DtStatus(0); // nothing
|
||||
public static readonly DtStatus DT_WRONG_MAGIC = new DtStatus(1 << 0); // Input data is not recognized.
|
||||
public static readonly DtStatus DT_WRONG_VERSION = new DtStatus(1 << 1); // Input data is in wrong version.
|
||||
public static readonly DtStatus DT_OUT_OF_MEMORY = new DtStatus(1 << 2); // Operation ran out of memory.
|
||||
|
|
|
@ -34,13 +34,13 @@ namespace DotRecast.Detour
|
|||
float minTargetDist, List<long> path)
|
||||
{
|
||||
// Find steer target.
|
||||
Result<List<StraightPathItem>> result = navQuery.FindStraightPath(startPos, endPos, path, MAX_STEER_POINTS, 0);
|
||||
var straightPath = new List<StraightPathItem>();
|
||||
var result = navQuery.FindStraightPath(startPos, endPos, path, ref straightPath, MAX_STEER_POINTS, 0);
|
||||
if (result.Failed())
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
List<StraightPathItem> straightPath = result.result;
|
||||
float[] steerPoints = new float[straightPath.Count * 3];
|
||||
for (int i = 0; i < straightPath.Count; i++)
|
||||
{
|
||||
|
|
|
@ -345,8 +345,7 @@ public class TestNavmeshTool : IRcTool
|
|||
}
|
||||
}
|
||||
|
||||
m_straightPath = m_navQuery.FindStraightPath(m_spos, epos, m_polys, MAX_POLYS,
|
||||
m_straightPathOptions).result;
|
||||
m_navQuery.FindStraightPath(m_spos, epos, m_polys, ref m_straightPath, MAX_POLYS, m_straightPathOptions);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -999,14 +998,7 @@ public class TestNavmeshTool : IRcTool
|
|||
}
|
||||
}
|
||||
|
||||
{
|
||||
Result<List<StraightPathItem>> result = m_navQuery.FindStraightPath(m_spos, epos, m_polys,
|
||||
MAX_POLYS, DtNavMeshQuery.DT_STRAIGHTPATH_ALL_CROSSINGS);
|
||||
if (result.Succeeded())
|
||||
{
|
||||
m_straightPath = result.result;
|
||||
}
|
||||
}
|
||||
m_navQuery.FindStraightPath(m_spos, epos, m_polys, ref m_straightPath, MAX_POLYS, DtNavMeshQuery.DT_STRAIGHTPATH_ALL_CROSSINGS);
|
||||
}
|
||||
|
||||
m_pathFindStatus = DtStatus.DT_FAILURE;
|
||||
|
|
|
@ -44,16 +44,24 @@ public class PathCorridorTest
|
|||
straightPath.Add(new StraightPathItem(RcVec3f.Of(12, 20, 30.00002f), 0, 0));
|
||||
straightPath.Add(new StraightPathItem(RcVec3f.Of(11f, 21, 32f), 0, 0));
|
||||
straightPath.Add(new StraightPathItem(RcVec3f.Of(11f, 21, 32f), 0, 0));
|
||||
Result<List<StraightPathItem>> result = Results.Success(straightPath);
|
||||
var mockQuery = new Mock<DtNavMeshQuery>(It.IsAny<DtNavMesh>());
|
||||
mockQuery.Setup(q => q.FindStraightPath(
|
||||
It.IsAny<RcVec3f>(),
|
||||
It.IsAny<RcVec3f>(),
|
||||
It.IsAny<List<long>>(),
|
||||
ref It.Ref<List<StraightPathItem>>.IsAny,
|
||||
It.IsAny<int>(),
|
||||
It.IsAny<int>())
|
||||
).Returns(result);
|
||||
List<StraightPathItem> path = corridor.FindCorners(int.MaxValue, mockQuery.Object, filter);
|
||||
)
|
||||
.Callback((RcVec3f startPos, RcVec3f endPos, List<long> path,
|
||||
ref List<StraightPathItem> refStraightPath, int maxStraightPath, int options) =>
|
||||
{
|
||||
refStraightPath = straightPath;
|
||||
})
|
||||
.Returns(() => DtStatus.DT_SUCCSESS);
|
||||
|
||||
var path = new List<StraightPathItem>();
|
||||
corridor.FindCorners(ref path, int.MaxValue, mockQuery.Object, filter);
|
||||
Assert.That(path.Count, Is.EqualTo(4));
|
||||
Assert.That(path, Is.EqualTo(straightPath));
|
||||
}
|
||||
|
@ -67,18 +75,24 @@ public class PathCorridorTest
|
|||
straightPath.Add(new StraightPathItem(RcVec3f.Of(11f, 21, 32f), 0, 0));
|
||||
straightPath.Add(new StraightPathItem(RcVec3f.Of(12f, 22, 33f), DtNavMeshQuery.DT_STRAIGHTPATH_OFFMESH_CONNECTION, 0)); // offmesh
|
||||
straightPath.Add(new StraightPathItem(RcVec3f.Of(11f, 21, 32f), DtNavMeshQuery.DT_STRAIGHTPATH_OFFMESH_CONNECTION, 0)); // offmesh
|
||||
Result<List<StraightPathItem>> result = Results.Success(straightPath);
|
||||
|
||||
var mockQuery = new Mock<DtNavMeshQuery>(It.IsAny<DtNavMesh>());
|
||||
var s = mockQuery.Setup(q => q.FindStraightPath(
|
||||
mockQuery.Setup(q => q.FindStraightPath(
|
||||
It.IsAny<RcVec3f>(),
|
||||
It.IsAny<RcVec3f>(),
|
||||
It.IsAny<List<long>>(),
|
||||
ref It.Ref<List<StraightPathItem>>.IsAny,
|
||||
It.IsAny<int>(),
|
||||
It.IsAny<int>())
|
||||
).Returns(result);
|
||||
).Callback((RcVec3f startPos, RcVec3f endPos, List<long> path,
|
||||
ref List<StraightPathItem> refStraightPath, int maxStraightPath, int options) =>
|
||||
{
|
||||
refStraightPath = straightPath;
|
||||
})
|
||||
.Returns(() => DtStatus.DT_SUCCSESS);
|
||||
|
||||
List<StraightPathItem> path = corridor.FindCorners(int.MaxValue, mockQuery.Object, filter);
|
||||
var path = new List<StraightPathItem>();
|
||||
corridor.FindCorners(ref path, int.MaxValue, mockQuery.Object, filter);
|
||||
Assert.That(path.Count, Is.EqualTo(2));
|
||||
Assert.That(path, Is.EqualTo(new List<StraightPathItem> { straightPath[2], straightPath[3] }));
|
||||
}
|
||||
|
|
|
@ -188,9 +188,8 @@ public class FindPathTest : AbstractDetourTest
|
|||
var startPos = startPoss[i];
|
||||
var endPos = endPoss[i];
|
||||
Result<List<long>> path = query.FindPath(startRef, endRef, startPos, endPos, filter);
|
||||
Result<List<StraightPathItem>> result = query.FindStraightPath(startPos, endPos, path.result,
|
||||
int.MaxValue, 0);
|
||||
List<StraightPathItem> straightPath = result.result;
|
||||
var straightPath = new List<StraightPathItem>();
|
||||
query.FindStraightPath(startPos, endPos, path.result, ref straightPath, int.MaxValue, 0);
|
||||
Assert.That(straightPath.Count, Is.EqualTo(STRAIGHT_PATHS[i].Length));
|
||||
for (int j = 0; j < STRAIGHT_PATHS[i].Length; j++)
|
||||
{
|
||||
|
|
|
@ -55,7 +55,9 @@ public class TileCacheFindPathTest : AbstractTileCacheTest
|
|||
Result<List<long>> path = query.FindPath(startRef, endRef, startPos, endPos, filter);
|
||||
int maxStraightPath = 256;
|
||||
int options = 0;
|
||||
Result<List<StraightPathItem>> pathStr = query.FindStraightPath(startPos, endPos, path.result, maxStraightPath, options);
|
||||
Assert.That(pathStr.result.Count, Is.EqualTo(8));
|
||||
|
||||
var pathStr = new List<StraightPathItem>();
|
||||
query.FindStraightPath(startPos, endPos, path.result, ref pathStr, maxStraightPath, options);
|
||||
Assert.That(pathStr.Count, Is.EqualTo(8));
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue