Skip to content

Commit

Permalink
Changed to use Span<byte> and stackalloc for improved performance and…
Browse files Browse the repository at this point in the history
… memory management in `RcLayers.BuildHeightfieldLayers()`
  • Loading branch information
ikpil committed Jun 27, 2024
1 parent 2775152 commit ba68157
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 14 deletions.
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,8 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
- Changed `reg`, `area` arrays to byte arrays for uniformity and efficiency in `DtTileCacheContour`
- Changed `RcChunkyTriMesh` to separate the function and variable.
- Changed to consolidate vector-related functions into one place.
- Changed stack handling from List to a fixed-size array with manual index management for optimization in `RcLayers.BuildHeightfieldLayers`
- Changed stack handling from List to a fixed-size array with manual index management for optimization in `RcLayers.BuildHeightfieldLayers()`
- Changed to use Span<byte> and stackalloc for improved performance and memory management in `RcLayers.BuildHeightfieldLayers()`

### Removed
- Removed RcMeshDetails.VdistSq2(float[], float[])
Expand Down
24 changes: 11 additions & 13 deletions src/DotRecast.Recast/RcLayers.cs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ 3. This notice may not be removed or altered from any source distribution.

namespace DotRecast.Recast
{

using static RcRecast;

public static class RcLayers
Expand Down Expand Up @@ -61,7 +60,6 @@ private static bool OverlapRange(int amin, int amax, int bmin, int bmax)
/// @name Layer, Contour, Polymesh, and Detail Mesh Functions
/// @see rcHeightfieldLayer, rcContourSet, rcPolyMesh, rcPolyMeshDetail
/// @{

/// Builds a layer set from the specified compact heightfield.
/// @ingroup recast
/// @param[in,out] ctx The build context to use during the operation.
Expand All @@ -79,10 +77,10 @@ public static bool BuildHeightfieldLayers(RcContext ctx, RcCompactHeightfield ch

int w = chf.width;
int h = chf.height;
byte[] srcReg = new byte[chf.spanCount];
Array.Fill(srcReg, (byte)0xFF);

Span<byte> srcReg = stackalloc byte[chf.spanCount];
srcReg.Fill(0xFF);

int nsweeps = chf.width;
RcLayerSweepSpan[] sweeps = new RcLayerSweepSpan[nsweeps];
for (int i = 0; i < sweeps.Length; i++)
Expand All @@ -91,14 +89,14 @@ public static bool BuildHeightfieldLayers(RcContext ctx, RcCompactHeightfield ch
}

// Partition walkable area into monotone regions.
int[] prevCount = new int[256];
Span<int> prevCount = stackalloc int[256];
byte regId = 0;

// Sweep one line at a time.
for (int y = borderSize; y < h - borderSize; ++y)
{
// Collect spans from this row.
Array.Fill(prevCount, 0);
prevCount.Fill(0);
byte sweepId = 0;

for (int x = borderSize; x < w - borderSize; ++x)
Expand All @@ -110,9 +108,9 @@ public static bool BuildHeightfieldLayers(RcContext ctx, RcCompactHeightfield ch
ref RcCompactSpan s = ref chf.spans[i];
if (chf.areas[i] == RC_NULL_AREA)
continue;

byte sid = 0xFF;

// -x
if (GetCon(ref s, 0) != RC_NOT_CONNECTED)
{
Expand Down Expand Up @@ -292,7 +290,7 @@ public static bool BuildHeightfieldLayers(RcContext ctx, RcCompactHeightfield ch
RcLayerRegion reg = regs[stack[0]];
nstack--;
for (int j = 0; j < nstack; ++j)
stack[j] = stack[j+1];
stack[j] = stack[j + 1];

foreach (int nei in reg.neis)
{
Expand Down Expand Up @@ -457,7 +455,7 @@ public static bool BuildHeightfieldLayers(RcContext ctx, RcCompactHeightfield ch
bmin.Z += borderSize * chf.cs;
bmax.X -= borderSize * chf.cs;
bmax.Z -= borderSize * chf.cs;

lset = new RcHeightfieldLayerSet();
lset.layers = new RcHeightfieldLayer[layerId];
for (int i = 0; i < lset.layers.Length; i++)
Expand Down

0 comments on commit ba68157

Please sign in to comment.