diff --git a/src/DotRecast.Recast.Demo/Draw/RecastDebugDraw.cs b/src/DotRecast.Recast.Demo/Draw/RecastDebugDraw.cs index 43c7523..82bf288 100644 --- a/src/DotRecast.Recast.Demo/Draw/RecastDebugDraw.cs +++ b/src/DotRecast.Recast.Demo/Draw/RecastDebugDraw.cs @@ -486,11 +486,11 @@ public class RecastDebugDraw : DebugDraw { float fx = chf.bmin.X + x * cs; float fz = chf.bmin.Z + y * cs; - ref readonly RcCompactCell c = ref chf.cells[x + y * chf.width]; + ref RcCompactCell c = ref chf.cells[x + y * chf.width]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int area = chf.areas[i]; int color; @@ -859,11 +859,11 @@ public class RecastDebugDraw : DebugDraw { float fx = chf.bmin.X + x * cs; float fz = chf.bmin.Z + y * cs; - ref readonly RcCompactCell c = ref chf.cells[x + y * chf.width]; + ref RcCompactCell c = ref chf.cells[x + y * chf.width]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; float fy = chf.bmin.Y + (s.y) * ch; int color; if (s.reg != 0) @@ -912,11 +912,11 @@ public class RecastDebugDraw : DebugDraw { float fx = chf.bmin.X + x * cs; float fz = chf.bmin.Z + y * cs; - ref readonly RcCompactCell c = ref chf.cells[x + y * chf.width]; + ref RcCompactCell c = ref chf.cells[x + y * chf.width]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; float fy = chf.bmin.Y + (s.y + 1) * ch; char cd = (char)(chf.dist[i] * dscale); int color = DuRGBA(cd, cd, cd, 255); diff --git a/src/DotRecast.Recast/RcAreas.cs b/src/DotRecast.Recast/RcAreas.cs index 6597383..05d8e2c 100644 --- a/src/DotRecast.Recast/RcAreas.cs +++ b/src/DotRecast.Recast/RcAreas.cs @@ -60,7 +60,7 @@ namespace DotRecast.Recast { for (int x = 0; x < xSize; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; for (int spanIndex = cell.index, maxSpanIndex = cell.index + cell.count; spanIndex < maxSpanIndex; ++spanIndex) { if (compactHeightfield.areas[spanIndex] == RC_NULL_AREA) @@ -69,13 +69,13 @@ namespace DotRecast.Recast } else { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; // Check that there is a non-null adjacent span in each of the 4 cardinal directions. int neighborCount = 0; for (int direction = 0; direction < 4; ++direction) { - int neighborConnection = GetCon(span, direction); + int neighborConnection = GetCon(ref span, direction); if (neighborConnection == RC_NOT_CONNECTED) { break; @@ -83,7 +83,7 @@ namespace DotRecast.Recast int neighborX = x + GetDirOffsetX(direction); int neighborZ = z + GetDirOffsetY(direction); - int neighborSpanIndex = compactHeightfield.cells[neighborX + neighborZ * zStride].index + GetCon(span, direction); + int neighborSpanIndex = compactHeightfield.cells[neighborX + neighborZ * zStride].index + GetCon(ref span, direction); if (compactHeightfield.areas[neighborSpanIndex] == RC_NULL_AREA) { break; @@ -109,19 +109,19 @@ namespace DotRecast.Recast { for (int x = 0; x < xSize; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; for (int spanIndex = cell.index; spanIndex < maxSpanIndex; ++spanIndex) { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; - if (GetCon(span, 0) != RC_NOT_CONNECTED) + if (GetCon(ref span, 0) != RC_NOT_CONNECTED) { // (-1,0) int aX = x + GetDirOffsetX(0); int aY = z + GetDirOffsetY(0); - int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(span, 0); - RcCompactSpan aSpan = compactHeightfield.spans[aIndex]; + int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(ref span, 0); + ref RcCompactSpan aSpan = ref compactHeightfield.spans[aIndex]; newDistance = Math.Min(distanceToBoundary[aIndex] + 2, 255); if (newDistance < distanceToBoundary[spanIndex]) { @@ -129,11 +129,11 @@ namespace DotRecast.Recast } // (-1,-1) - if (GetCon(aSpan, 3) != RC_NOT_CONNECTED) + if (GetCon(ref aSpan, 3) != RC_NOT_CONNECTED) { int bX = aX + GetDirOffsetX(3); int bY = aY + GetDirOffsetY(3); - int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(aSpan, 3); + int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(ref aSpan, 3); newDistance = Math.Min(distanceToBoundary[bIndex] + 3, 255); if (newDistance < distanceToBoundary[spanIndex]) { @@ -142,13 +142,13 @@ namespace DotRecast.Recast } } - if (GetCon(span, 3) != RC_NOT_CONNECTED) + if (GetCon(ref span, 3) != RC_NOT_CONNECTED) { // (0,-1) int aX = x + GetDirOffsetX(3); int aY = z + GetDirOffsetY(3); - int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(span, 3); - RcCompactSpan aSpan = compactHeightfield.spans[aIndex]; + int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(ref span, 3); + ref RcCompactSpan aSpan = ref compactHeightfield.spans[aIndex]; newDistance = Math.Min(distanceToBoundary[aIndex] + 2, 255); if (newDistance < distanceToBoundary[spanIndex]) { @@ -156,11 +156,11 @@ namespace DotRecast.Recast } // (1,-1) - if (GetCon(aSpan, 2) != RC_NOT_CONNECTED) + if (GetCon(ref aSpan, 2) != RC_NOT_CONNECTED) { int bX = aX + GetDirOffsetX(2); int bY = aY + GetDirOffsetY(2); - int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(aSpan, 2); + int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(ref aSpan, 2); newDistance = Math.Min(distanceToBoundary[bIndex] + 3, 255); if (newDistance < distanceToBoundary[spanIndex]) { @@ -177,19 +177,19 @@ namespace DotRecast.Recast { for (int x = xSize - 1; x >= 0; --x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; for (int i = cell.index; i < maxSpanIndex; ++i) { - RcCompactSpan span = compactHeightfield.spans[i]; + ref RcCompactSpan span = ref compactHeightfield.spans[i]; - if (GetCon(span, 2) != RC_NOT_CONNECTED) + if (GetCon(ref span, 2) != RC_NOT_CONNECTED) { // (1,0) int aX = x + GetDirOffsetX(2); int aY = z + GetDirOffsetY(2); - int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(span, 2); - RcCompactSpan aSpan = compactHeightfield.spans[aIndex]; + int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(ref span, 2); + ref RcCompactSpan aSpan = ref compactHeightfield.spans[aIndex]; newDistance = Math.Min(distanceToBoundary[aIndex] + 2, 255); if (newDistance < distanceToBoundary[i]) { @@ -197,11 +197,11 @@ namespace DotRecast.Recast } // (1,1) - if (GetCon(aSpan, 1) != RC_NOT_CONNECTED) + if (GetCon(ref aSpan, 1) != RC_NOT_CONNECTED) { int bX = aX + GetDirOffsetX(1); int bY = aY + GetDirOffsetY(1); - int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(aSpan, 1); + int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(ref aSpan, 1); newDistance = Math.Min(distanceToBoundary[bIndex] + 3, 255); if (newDistance < distanceToBoundary[i]) { @@ -210,13 +210,13 @@ namespace DotRecast.Recast } } - if (GetCon(span, 1) != RC_NOT_CONNECTED) + if (GetCon(ref span, 1) != RC_NOT_CONNECTED) { // (0,1) int aX = x + GetDirOffsetX(1); int aY = z + GetDirOffsetY(1); - int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(span, 1); - RcCompactSpan aSpan = compactHeightfield.spans[aIndex]; + int aIndex = compactHeightfield.cells[aX + aY * xSize].index + GetCon(ref span, 1); + ref RcCompactSpan aSpan = ref compactHeightfield.spans[aIndex]; newDistance = Math.Min(distanceToBoundary[aIndex] + 2, 255); if (newDistance < distanceToBoundary[i]) { @@ -224,11 +224,11 @@ namespace DotRecast.Recast } // (-1,1) - if (GetCon(aSpan, 0) != RC_NOT_CONNECTED) + if (GetCon(ref aSpan, 0) != RC_NOT_CONNECTED) { int bX = aX + GetDirOffsetX(0); int bY = aY + GetDirOffsetY(0); - int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(aSpan, 0); + int bIndex = compactHeightfield.cells[bX + bY * xSize].index + GetCon(ref aSpan, 0); newDistance = Math.Min(distanceToBoundary[bIndex] + 3, 255); if (newDistance < distanceToBoundary[i]) { @@ -275,11 +275,11 @@ namespace DotRecast.Recast { for (int x = 0; x < xSize; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; for (int spanIndex = cell.index; spanIndex < maxSpanIndex; ++spanIndex) { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; if (compactHeightfield.areas[spanIndex] == RC_NULL_AREA) { areas[spanIndex] = compactHeightfield.areas[spanIndex]; @@ -294,27 +294,27 @@ namespace DotRecast.Recast for (int dir = 0; dir < 4; ++dir) { - if (GetCon(span, dir) == RC_NOT_CONNECTED) + if (GetCon(ref span, dir) == RC_NOT_CONNECTED) { continue; } int aX = x + GetDirOffsetX(dir); int aZ = z + GetDirOffsetY(dir); - int aIndex = compactHeightfield.cells[aX + aZ * zStride].index + GetCon(span, dir); + int aIndex = compactHeightfield.cells[aX + aZ * zStride].index + GetCon(ref span, dir); if (compactHeightfield.areas[aIndex] != RC_NULL_AREA) { neighborAreas[dir * 2 + 0] = compactHeightfield.areas[aIndex]; } - RcCompactSpan aSpan = compactHeightfield.spans[aIndex]; + ref RcCompactSpan aSpan = ref compactHeightfield.spans[aIndex]; int dir2 = (dir + 1) & 0x3; - int neighborConnection2 = GetCon(aSpan, dir2); + int neighborConnection2 = GetCon(ref aSpan, dir2); if (neighborConnection2 != RC_NOT_CONNECTED) { int bX = aX + GetDirOffsetX(dir2); int bZ = aZ + GetDirOffsetY(dir2); - int bIndex = compactHeightfield.cells[bX + bZ * zStride].index + GetCon(aSpan, dir2); + int bIndex = compactHeightfield.cells[bX + bZ * zStride].index + GetCon(ref aSpan, dir2); if (compactHeightfield.areas[bIndex] != RC_NULL_AREA) { neighborAreas[dir * 2 + 1] = compactHeightfield.areas[bIndex]; @@ -404,11 +404,11 @@ namespace DotRecast.Recast { for (int x = minX; x <= maxX; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; for (int spanIndex = cell.index; spanIndex < maxSpanIndex; ++spanIndex) { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; // Skip if the span is outside the box extents. if (span.y < minY || span.y > maxY) @@ -523,11 +523,11 @@ namespace DotRecast.Recast { for (int x = minx; x <= maxx; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; for (int spanIndex = cell.index; spanIndex < maxSpanIndex; ++spanIndex) { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; // Skip if span is removed. if (compactHeightfield.areas[spanIndex] == RC_NULL_AREA) @@ -644,7 +644,7 @@ namespace DotRecast.Recast { for (int x = minx; x <= maxx; ++x) { - ref readonly RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; + ref RcCompactCell cell = ref compactHeightfield.cells[x + z * zStride]; int maxSpanIndex = cell.index + cell.count; float cellX = compactHeightfield.bmin.X + ((float)x + 0.5f) * compactHeightfield.cs; @@ -661,7 +661,7 @@ namespace DotRecast.Recast // Mark all overlapping spans for (int spanIndex = cell.index; spanIndex < maxSpanIndex; ++spanIndex) { - RcCompactSpan span = compactHeightfield.spans[spanIndex]; + ref RcCompactSpan span = ref compactHeightfield.spans[spanIndex]; // Skip if span is removed. if (compactHeightfield.areas[spanIndex] == RC_NULL_AREA) diff --git a/src/DotRecast.Recast/RcCommons.cs b/src/DotRecast.Recast/RcCommons.cs index 93ba642..f35b4f0 100644 --- a/src/DotRecast.Recast/RcCommons.cs +++ b/src/DotRecast.Recast/RcCommons.cs @@ -36,7 +36,7 @@ namespace DotRecast.Recast /// @param[in] span The span to update. /// @param[in] direction The direction to set. [Limits: 0 <= value < 4] /// @param[in] neighborIndex The index of the neighbor span. - public static void SetCon(RcCompactSpan span, int direction, int neighborIndex) + public static void SetCon(RcCompactSpanBuilder span, int direction, int neighborIndex) { int shift = direction * 6; int con = span.con; @@ -47,7 +47,7 @@ namespace DotRecast.Recast /// @param[in] span The span to check. /// @param[in] direction The direction to check. [Limits: 0 <= value < 4] /// @return The neighbor connection data for the specified direction, or #RC_NOT_CONNECTED if there is no connection. - public static int GetCon(RcCompactSpan s, int dir) + public static int GetCon(ref RcCompactSpan s, int dir) { int shift = dir * 6; return (s.con >> shift) & 0x3f; diff --git a/src/DotRecast.Recast/RcCompactSpan.cs b/src/DotRecast.Recast/RcCompactSpan.cs index de1e55d..7f61001 100644 --- a/src/DotRecast.Recast/RcCompactSpan.cs +++ b/src/DotRecast.Recast/RcCompactSpan.cs @@ -21,18 +21,26 @@ freely, subject to the following restrictions: namespace DotRecast.Recast { /** Represents a span of unobstructed space within a compact heightfield. */ - public class RcCompactSpan + public readonly struct RcCompactSpan { /** The lower extent of the span. (Measured from the heightfield's base.) */ - public int y; + public readonly int y; /** The id of the region the span belongs to. (Or zero if not in a region.) */ - public int reg; + public readonly int reg; /** Packed neighbor connection data. */ - public int con; + public readonly int con; /** The height of the span. (Measured from #y.) */ - public int h; + public readonly int h; + + public RcCompactSpan(RcCompactSpanBuilder span) + { + y = span.y; + reg = span.reg; + con = span.con; + h = span.h; + } } } \ No newline at end of file diff --git a/src/DotRecast.Recast/RcCompactSpanBuilder.cs b/src/DotRecast.Recast/RcCompactSpanBuilder.cs new file mode 100644 index 0000000..c4ee9bb --- /dev/null +++ b/src/DotRecast.Recast/RcCompactSpanBuilder.cs @@ -0,0 +1,35 @@ +namespace DotRecast.Recast +{ + public class RcCompactSpanBuilder + { + public int y; + public int reg; + public int con; + public int h; + + public static RcCompactSpanBuilder NewBuilder(ref RcCompactSpan span) + { + var builder = new RcCompactSpanBuilder(); + builder.y = span.y; + builder.reg = span.reg; + builder.con = span.con; + builder.h = span.h; + return builder; + } + + public RcCompactSpanBuilder() + { + } + + public RcCompactSpanBuilder WithReg(int reg) + { + this.reg = reg; + return this; + } + + public RcCompactSpan Build() + { + return new RcCompactSpan(this); + } + } +} \ No newline at end of file diff --git a/src/DotRecast.Recast/RcCompacts.cs b/src/DotRecast.Recast/RcCompacts.cs index 426b511..9aa84e1 100644 --- a/src/DotRecast.Recast/RcCompacts.cs +++ b/src/DotRecast.Recast/RcCompacts.cs @@ -18,6 +18,7 @@ freely, subject to the following restrictions: */ using System; +using System.Linq; using DotRecast.Core; using static DotRecast.Recast.RcConstants; @@ -65,13 +66,13 @@ namespace DotRecast.Recast chf.cs = hf.cs; chf.ch = hf.ch; chf.cells = new RcCompactCell[w * h]; - chf.spans = new RcCompactSpan[spanCount]; + //chf.spans = new RcCompactSpan[spanCount]; chf.areas = new int[spanCount]; - for (int i = 0; i < chf.spans.Length; i++) - { - chf.spans[i] = new RcCompactSpan(); - } + var chfSpans = Enumerable + .Range(0, spanCount) + .Select(x => new RcCompactSpanBuilder()) + .ToArray(); // Fill in cells and spans. int idx = 0; @@ -92,8 +93,8 @@ namespace DotRecast.Recast { int bot = s.smax; int top = s.next != null ? (int)s.next.smin : MAX_HEIGHT; - chf.spans[idx].y = Math.Clamp(bot, 0, MAX_HEIGHT); - chf.spans[idx].h = Math.Clamp(top - bot, 0, MAX_HEIGHT); + chfSpans[idx].y = Math.Clamp(bot, 0, MAX_HEIGHT); + chfSpans[idx].h = Math.Clamp(top - bot, 0, MAX_HEIGHT); chf.areas[idx] = s.area; idx++; tmpCount++; @@ -112,10 +113,10 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpanBuilder s = ref chfSpans[i]; for (int dir = 0; dir < 4; ++dir) { @@ -128,10 +129,10 @@ namespace DotRecast.Recast // Iterate over all neighbour spans and check if any of the is // accessible from current cell. - ref readonly RcCompactCell nc = ref chf.cells[nx + ny * w]; + ref RcCompactCell nc = ref chf.cells[nx + ny * w]; for (int k = nc.index, nk = nc.index + nc.count; k < nk; ++k) { - RcCompactSpan ns = chf.spans[k]; + ref RcCompactSpanBuilder ns = ref chfSpans[k]; int bot = Math.Max(s.y, ns.y); int top = Math.Min(s.y + s.h, ns.y + ns.h); @@ -162,6 +163,8 @@ namespace DotRecast.Recast + " (max: " + MAX_LAYERS + ")"); } + chf.spans = chfSpans.Select(x => x.Build()).ToArray(); + return chf; } diff --git a/src/DotRecast.Recast/RcContours.cs b/src/DotRecast.Recast/RcContours.cs index af5bb56..0891087 100644 --- a/src/DotRecast.Recast/RcContours.cs +++ b/src/DotRecast.Recast/RcContours.cs @@ -33,7 +33,7 @@ namespace DotRecast.Recast { isBorderVertex = false; - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int ch = s.y; int dirp = (dir + 1) & 0x3; @@ -46,39 +46,39 @@ namespace DotRecast.Recast // border vertices which are in between two areas to be removed. regs[0] = chf.spans[i].reg | (chf.areas[i] << 16); - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dir); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dir); + ref RcCompactSpan @as = ref chf.spans[ai]; ch = Math.Max(ch, @as.y); regs[1] = chf.spans[ai].reg | (chf.areas[ai] << 16); - if (GetCon(@as, dirp) != RC_NOT_CONNECTED) + if (GetCon(ref @as, dirp) != RC_NOT_CONNECTED) { int ax2 = ax + GetDirOffsetX(dirp); int ay2 = ay + GetDirOffsetY(dirp); - int ai2 = chf.cells[ax2 + ay2 * chf.width].index + GetCon(@as, dirp); - RcCompactSpan as2 = chf.spans[ai2]; + int ai2 = chf.cells[ax2 + ay2 * chf.width].index + GetCon(ref @as, dirp); + ref RcCompactSpan as2 = ref chf.spans[ai2]; ch = Math.Max(ch, as2.y); regs[2] = chf.spans[ai2].reg | (chf.areas[ai2] << 16); } } - if (GetCon(s, dirp) != RC_NOT_CONNECTED) + if (GetCon(ref s, dirp) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dirp); int ay = y + GetDirOffsetY(dirp); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dirp); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dirp); + ref RcCompactSpan @as = ref chf.spans[ai]; ch = Math.Max(ch, @as.y); regs[3] = chf.spans[ai].reg | (chf.areas[ai] << 16); - if (GetCon(@as, dir) != RC_NOT_CONNECTED) + if (GetCon(ref @as, dir) != RC_NOT_CONNECTED) { int ax2 = ax + GetDirOffsetX(dir); int ay2 = ay + GetDirOffsetY(dir); - int ai2 = chf.cells[ax2 + ay2 * chf.width].index + GetCon(@as, dir); - RcCompactSpan as2 = chf.spans[ai2]; + int ai2 = chf.cells[ax2 + ay2 * chf.width].index + GetCon(ref @as, dir); + ref RcCompactSpan as2 = ref chf.spans[ai2]; ch = Math.Max(ch, as2.y); regs[2] = chf.spans[ai2].reg | (chf.areas[ai2] << 16); } @@ -146,12 +146,12 @@ namespace DotRecast.Recast } int r = 0; - RcCompactSpan s = chf.spans[i]; - if (GetCon(s, dir) != RC_NOT_CONNECTED) + ref RcCompactSpan s = ref chf.spans[i]; + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dir); r = chf.spans[ai].reg; if (area != chf.areas[ai]) isAreaBorder = true; @@ -174,11 +174,11 @@ namespace DotRecast.Recast int ni = -1; int nx = x + GetDirOffsetX(dir); int ny = y + GetDirOffsetY(dir); - RcCompactSpan s = chf.spans[i]; - if (GetCon(s, dir) != RC_NOT_CONNECTED) + ref RcCompactSpan s = ref chf.spans[i]; + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { - ref readonly RcCompactCell nc = ref chf.cells[nx + ny * chf.width]; - ni = nc.index + GetCon(s, dir); + ref RcCompactCell nc = ref chf.cells[nx + ny * chf.width]; + ni = nc.index + GetCon(ref s, dir); } if (ni == -1) @@ -753,11 +753,11 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { int res = 0; - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (chf.spans[i].reg == 0 || (chf.spans[i].reg & RC_BORDER_REG) != 0) { flags[i] = 0; @@ -767,11 +767,11 @@ namespace DotRecast.Recast for (int dir = 0; dir < 4; ++dir) { int r = 0; - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); r = chf.spans[ai].reg; } @@ -793,7 +793,7 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { if (flags[i] == 0 || flags[i] == 0xf) diff --git a/src/DotRecast.Recast/RcLayers.cs b/src/DotRecast.Recast/RcLayers.cs index dd6ee8e..244b140 100644 --- a/src/DotRecast.Recast/RcLayers.cs +++ b/src/DotRecast.Recast/RcLayers.cs @@ -80,21 +80,21 @@ namespace DotRecast.Recast for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (chf.areas[i] == RC_NULL_AREA) continue; int sid = 0xFF; // -x - if (GetCon(s, 0) != RC_NOT_CONNECTED) + if (GetCon(ref s, 0) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(0); int ay = y + GetDirOffsetY(0); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 0); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 0); if (chf.areas[ai] != RC_NULL_AREA && srcReg[ai] != 0xff) sid = srcReg[ai]; } @@ -107,11 +107,11 @@ namespace DotRecast.Recast } // -y - if (GetCon(s, 3) != RC_NOT_CONNECTED) + if (GetCon(ref s, 3) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(3); int ay = y + GetDirOffsetY(3); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 3); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 3); int nr = srcReg[ai]; if (nr != 0xff) { @@ -165,7 +165,7 @@ namespace DotRecast.Recast // Remap local sweep ids to region ids. for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { if (srcReg[i] != 0xff) @@ -189,13 +189,13 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; lregs.Clear(); for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int ri = srcReg[i]; if (ri == 0xff) continue; @@ -209,11 +209,11 @@ namespace DotRecast.Recast // Update neighbours for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); int rai = srcReg[ai]; if (rai != 0xff && rai != ri) AddUnique(regs[ri].neis, rai); @@ -475,10 +475,10 @@ namespace DotRecast.Recast { int cx = borderSize + x; int cy = borderSize + y; - ref readonly RcCompactCell c = ref chf.cells[cx + cy * w]; + ref RcCompactCell c = ref chf.cells[cx + cy * w]; for (int j = c.index, nj = c.index + c.count; j < nj; ++j) { - RcCompactSpan s = chf.spans[j]; + ref RcCompactSpan s = ref chf.spans[j]; // Skip unassigned regions. if (srcReg[j] == 0xff) continue; @@ -503,11 +503,11 @@ namespace DotRecast.Recast char con = (char)0; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = cx + GetDirOffsetX(dir); int ay = cy + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); int alid = srcReg[ai] != 0xff ? regs[srcReg[ai]].layerId : 0xff; // Portal mask if (chf.areas[ai] != RC_NULL_AREA && lid != alid) @@ -515,7 +515,7 @@ namespace DotRecast.Recast portal |= (char)(1 << dir); // Update height so that it matches on both // sides of the portal. - RcCompactSpan @as = chf.spans[ai]; + ref RcCompactSpan @as = ref chf.spans[ai]; if (@as.y > hmin) layer.heights[idx] = Math.Max(layer.heights[idx], (char)(@as.y - hmin)); } diff --git a/src/DotRecast.Recast/RcMeshDetails.cs b/src/DotRecast.Recast/RcMeshDetails.cs index 1c12486..bf24782 100644 --- a/src/DotRecast.Recast/RcMeshDetails.cs +++ b/src/DotRecast.Recast/RcMeshDetails.cs @@ -1131,10 +1131,10 @@ namespace DotRecast.Recast continue; } - ref readonly RcCompactCell c = ref chf.cells[(ax + bs) + (az + bs) * chf.width]; + ref RcCompactCell c = ref chf.cells[(ax + bs) + (az + bs) * chf.width]; for (int i = c.index, ni = c.index + c.count; i < ni && dmin > 0; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int d = Math.Abs(ay - s.y); if (d < dmin) { @@ -1210,12 +1210,12 @@ namespace DotRecast.Recast dirs[3] = dirs[directDir]; dirs[directDir] = tmp; - RcCompactSpan cs = chf.spans[ci]; + ref RcCompactSpan cs = ref chf.spans[ci]; for (int i = 0; i < 4; ++i) { int dir = dirs[i]; - if (GetCon(cs, dir) == RC_NOT_CONNECTED) + if (GetCon(ref cs, dir) == RC_NOT_CONNECTED) { continue; } @@ -1239,7 +1239,7 @@ namespace DotRecast.Recast array.Add(newX); array.Add(newY); - array.Add(chf.cells[(newX + bs) + (newY + bs) * chf.width].index + GetCon(cs, dir)); + array.Add(chf.cells[(newX + bs) + (newY + bs) * chf.width].index + GetCon(ref cs, dir)); } tmp = dirs[3]; @@ -1253,7 +1253,7 @@ namespace DotRecast.Recast array.Add(cy + bs); array.Add(ci); Array.Fill(hp.data, RC_UNSET_HEIGHT, 0, (hp.width * hp.height) - (0)); - RcCompactSpan cs2 = chf.spans[ci]; + ref RcCompactSpan cs2 = ref chf.spans[ci]; hp.data[cx - hp.xmin + (cy - hp.ymin) * hp.width] = cs2.y; } @@ -1290,10 +1290,10 @@ namespace DotRecast.Recast for (int hx = 0; hx < hp.width; hx++) { int x = hp.xmin + hx + bs; - ref readonly RcCompactCell c = ref chf.cells[x + y * chf.width]; + ref RcCompactCell c = ref chf.cells[x + y * chf.width]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (s.reg == region) { // Store height @@ -1304,12 +1304,12 @@ namespace DotRecast.Recast bool border = false; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dir); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dir); + ref RcCompactSpan @as = ref chf.spans[ai]; if (@as.reg != region) { border = true; @@ -1355,10 +1355,10 @@ namespace DotRecast.Recast queue = queue.GetRange(RETRACT_SIZE * 3, queue.Count - (RETRACT_SIZE * 3)); } - RcCompactSpan cs = chf.spans[ci]; + ref RcCompactSpan cs = ref chf.spans[ci]; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(cs, dir) == RC_NOT_CONNECTED) + if (GetCon(ref cs, dir) == RC_NOT_CONNECTED) { continue; } @@ -1378,8 +1378,8 @@ namespace DotRecast.Recast continue; } - int ai = chf.cells[ax + ay * chf.width].index + GetCon(cs, dir); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref cs, dir); + ref RcCompactSpan @as = ref chf.spans[ai]; hp.data[hx + hy * hp.width] = @as.y; Push3(queue, ax, ay, ai); diff --git a/src/DotRecast.Recast/RcRegions.cs b/src/DotRecast.Recast/RcRegions.cs index a8dd76d..3970f5c 100644 --- a/src/DotRecast.Recast/RcRegions.cs +++ b/src/DotRecast.Recast/RcRegions.cs @@ -49,20 +49,20 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int area = chf.areas[i]; int nc = 0; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); if (area == chf.areas[ai]) { nc++; @@ -83,29 +83,29 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; - if (GetCon(s, 0) != RC_NOT_CONNECTED) + if (GetCon(ref s, 0) != RC_NOT_CONNECTED) { // (-1,0) int ax = x + GetDirOffsetX(0); int ay = y + GetDirOffsetY(0); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 0); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 0); + ref RcCompactSpan @as = ref chf.spans[ai]; if (src[ai] + 2 < src[i]) { src[i] = src[ai] + 2; } // (-1,-1) - if (GetCon(@as, 3) != RC_NOT_CONNECTED) + if (GetCon(ref @as, 3) != RC_NOT_CONNECTED) { int aax = ax + GetDirOffsetX(3); int aay = ay + GetDirOffsetY(3); - int aai = chf.cells[aax + aay * w].index + GetCon(@as, 3); + int aai = chf.cells[aax + aay * w].index + GetCon(ref @as, 3); if (src[aai] + 3 < src[i]) { src[i] = src[aai] + 3; @@ -113,24 +113,24 @@ namespace DotRecast.Recast } } - if (GetCon(s, 3) != RC_NOT_CONNECTED) + if (GetCon(ref s, 3) != RC_NOT_CONNECTED) { // (0,-1) int ax = x + GetDirOffsetX(3); int ay = y + GetDirOffsetY(3); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 3); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 3); + ref RcCompactSpan @as = ref chf.spans[ai]; if (src[ai] + 2 < src[i]) { src[i] = src[ai] + 2; } // (1,-1) - if (GetCon(@as, 2) != RC_NOT_CONNECTED) + if (GetCon(ref @as, 2) != RC_NOT_CONNECTED) { int aax = ax + GetDirOffsetX(2); int aay = ay + GetDirOffsetY(2); - int aai = chf.cells[aax + aay * w].index + GetCon(@as, 2); + int aai = chf.cells[aax + aay * w].index + GetCon(ref @as, 2); if (src[aai] + 3 < src[i]) { src[i] = src[aai] + 3; @@ -146,29 +146,29 @@ namespace DotRecast.Recast { for (int x = w - 1; x >= 0; --x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; - if (GetCon(s, 2) != RC_NOT_CONNECTED) + if (GetCon(ref s, 2) != RC_NOT_CONNECTED) { // (1,0) int ax = x + GetDirOffsetX(2); int ay = y + GetDirOffsetY(2); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 2); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 2); + ref RcCompactSpan @as = ref chf.spans[ai]; if (src[ai] + 2 < src[i]) { src[i] = src[ai] + 2; } // (1,1) - if (GetCon(@as, 1) != RC_NOT_CONNECTED) + if (GetCon(ref @as, 1) != RC_NOT_CONNECTED) { int aax = ax + GetDirOffsetX(1); int aay = ay + GetDirOffsetY(1); - int aai = chf.cells[aax + aay * w].index + GetCon(@as, 1); + int aai = chf.cells[aax + aay * w].index + GetCon(ref @as, 1); if (src[aai] + 3 < src[i]) { src[i] = src[aai] + 3; @@ -176,24 +176,24 @@ namespace DotRecast.Recast } } - if (GetCon(s, 1) != RC_NOT_CONNECTED) + if (GetCon(ref s, 1) != RC_NOT_CONNECTED) { // (0,1) int ax = x + GetDirOffsetX(1); int ay = y + GetDirOffsetY(1); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 1); - RcCompactSpan @as = chf.spans[ai]; + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 1); + ref RcCompactSpan @as = ref chf.spans[ai]; if (src[ai] + 2 < src[i]) { src[i] = src[ai] + 2; } // (-1,1) - if (GetCon(@as, 0) != RC_NOT_CONNECTED) + if (GetCon(ref @as, 0) != RC_NOT_CONNECTED) { int aax = ax + GetDirOffsetX(0); int aay = ay + GetDirOffsetY(0); - int aai = chf.cells[aax + aay * w].index + GetCon(@as, 0); + int aai = chf.cells[aax + aay * w].index + GetCon(ref @as, 0); if (src[aai] + 3 < src[i]) { src[i] = src[aai] + 3; @@ -225,10 +225,10 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int cd = src[i]; if (cd <= thr) { @@ -239,20 +239,20 @@ namespace DotRecast.Recast int d = cd; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); d += src[ai]; - RcCompactSpan @as = chf.spans[ai]; + ref RcCompactSpan @as = ref chf.spans[ai]; int dir2 = (dir + 1) & 0x3; - if (GetCon(@as, dir2) != RC_NOT_CONNECTED) + if (GetCon(ref @as, dir2) != RC_NOT_CONNECTED) { int ax2 = ax + GetDirOffsetX(dir2); int ay2 = ay + GetDirOffsetY(dir2); - int ai2 = chf.cells[ax2 + ay2 * w].index + GetCon(@as, dir2); + int ai2 = chf.cells[ax2 + ay2 * w].index + GetCon(ref @as, dir2); d += src[ai2]; } else @@ -304,18 +304,18 @@ namespace DotRecast.Recast stack.RemoveAt(stack.Count - 1); - RcCompactSpan cs = chf.spans[ci]; + ref RcCompactSpan cs = ref chf.spans[ci]; // Check if any of the neighbours already have a valid region set. int ar = 0; for (int dir = 0; dir < 4; ++dir) { // 8 connected - if (GetCon(cs, dir) != RC_NOT_CONNECTED) + if (GetCon(ref cs, dir) != RC_NOT_CONNECTED) { int ax = cx + GetDirOffsetX(dir); int ay = cy + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(cs, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref cs, dir); if (chf.areas[ai] != area) { continue; @@ -333,14 +333,14 @@ namespace DotRecast.Recast break; } - RcCompactSpan @as = chf.spans[ai]; + ref RcCompactSpan @as = ref chf.spans[ai]; int dir2 = (dir + 1) & 0x3; - if (GetCon(@as, dir2) != RC_NOT_CONNECTED) + if (GetCon(ref @as, dir2) != RC_NOT_CONNECTED) { int ax2 = ax + GetDirOffsetX(dir2); int ay2 = ay + GetDirOffsetY(dir2); - int ai2 = chf.cells[ax2 + ay2 * w].index + GetCon(@as, dir2); + int ai2 = chf.cells[ax2 + ay2 * w].index + GetCon(ref @as, dir2); if (chf.areas[ai2] != area) { continue; @@ -367,11 +367,11 @@ namespace DotRecast.Recast // Expand neighbours. for (int dir = 0; dir < 4; ++dir) { - if (GetCon(cs, dir) != RC_NOT_CONNECTED) + if (GetCon(ref cs, dir) != RC_NOT_CONNECTED) { int ax = cx + GetDirOffsetX(dir); int ay = cy + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(cs, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref cs, dir); if (chf.areas[ai] != area) { continue; @@ -406,7 +406,7 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { if (chf.dist[i] >= level && srcReg[i] == 0 && chf.areas[i] != RC_NULL_AREA) @@ -453,17 +453,17 @@ namespace DotRecast.Recast int r = srcReg[i]; int d2 = 0xffff; int area = chf.areas[i]; - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) == RC_NOT_CONNECTED) + if (GetCon(ref s, dir) == RC_NOT_CONNECTED) { continue; } int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); if (chf.areas[ai] != area) { continue; @@ -535,7 +535,7 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { if (chf.areas[i] == RC_NULL_AREA || srcReg[i] != 0) @@ -739,13 +739,13 @@ namespace DotRecast.Recast private static bool IsSolidEdge(RcCompactHeightfield chf, int[] srcReg, int x, int y, int i, int dir) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int r = 0; - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dir); r = srcReg[ai]; } @@ -763,13 +763,13 @@ namespace DotRecast.Recast int startDir = dir; int starti = i; - RcCompactSpan ss = chf.spans[i]; + ref RcCompactSpan ss = ref chf.spans[i]; int curReg = 0; - if (GetCon(ss, dir) != RC_NOT_CONNECTED) + if (GetCon(ref ss, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(ss, dir); + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref ss, dir); curReg = srcReg[ai]; } @@ -778,17 +778,17 @@ namespace DotRecast.Recast int iter = 0; while (++iter < 40000) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (IsSolidEdge(chf, srcReg, x, y, i, dir)) { // Choose the edge corner int r = 0; - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * chf.width].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * chf.width].index + GetCon(ref s, dir); r = srcReg[ai]; } @@ -805,10 +805,10 @@ namespace DotRecast.Recast int ni = -1; int nx = x + GetDirOffsetX(dir); int ny = y + GetDirOffsetY(dir); - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { - ref readonly RcCompactCell nc = ref chf.cells[nx + ny * chf.width]; - ni = nc.index + GetCon(s, dir); + ref RcCompactCell nc = ref chf.cells[nx + ny * chf.width]; + ni = nc.index + GetCon(ref s, dir); } if (ni == -1) @@ -867,7 +867,7 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { int r = srcReg[i]; @@ -1190,13 +1190,13 @@ namespace DotRecast.Recast { for (int x = 0; x < w; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; lregs.Clear(); for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; int ri = srcReg[i]; if (ri == 0 || ri >= nreg) { @@ -1215,11 +1215,11 @@ namespace DotRecast.Recast // Update neighbours for (int dir = 0; dir < 4; ++dir) { - if (GetCon(s, dir) != RC_NOT_CONNECTED) + if (GetCon(ref s, dir) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(dir); int ay = y + GetDirOffsetY(dir); - int ai = chf.cells[ax + ay * w].index + GetCon(s, dir); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, dir); int rai = srcReg[ai]; if (rai > 0 && rai < nreg && rai != ri) { @@ -1445,7 +1445,7 @@ namespace DotRecast.Recast { for (int x = minx; x < maxx; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { if (chf.areas[i] != RC_NULL_AREA) @@ -1531,11 +1531,11 @@ namespace DotRecast.Recast for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (chf.areas[i] == RC_NULL_AREA) { continue; @@ -1543,11 +1543,11 @@ namespace DotRecast.Recast // -x int previd = 0; - if (GetCon(s, 0) != RC_NOT_CONNECTED) + if (GetCon(ref s, 0) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(0); int ay = y + GetDirOffsetY(0); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 0); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 0); if ((srcReg[ai] & RC_BORDER_REG) == 0 && chf.areas[i] == chf.areas[ai]) { previd = srcReg[ai]; @@ -1563,11 +1563,11 @@ namespace DotRecast.Recast } // -y - if (GetCon(s, 3) != RC_NOT_CONNECTED) + if (GetCon(ref s, 3) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(3); int ay = y + GetDirOffsetY(3); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 3); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 3); if (srcReg[ai] != 0 && (srcReg[ai] & RC_BORDER_REG) == 0 && chf.areas[i] == chf.areas[ai]) { int nr = srcReg[ai]; @@ -1609,7 +1609,7 @@ namespace DotRecast.Recast // Remap IDs for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { @@ -1632,7 +1632,10 @@ namespace DotRecast.Recast // Store the result out. for (int i = 0; i < chf.spanCount; ++i) { - chf.spans[i].reg = srcReg[i]; + chf.spans[i] = RcCompactSpanBuilder + .NewBuilder(ref chf.spans[i]) + .WithReg(srcReg[i]) + .Build(); } } @@ -1774,7 +1777,10 @@ namespace DotRecast.Recast // Write the result out. for (int i = 0; i < chf.spanCount; ++i) { - chf.spans[i].reg = srcReg[i]; + chf.spans[i] = RcCompactSpanBuilder + .NewBuilder(ref chf.spans[i]) + .WithReg(srcReg[i]) + .Build(); } } @@ -1831,11 +1837,11 @@ namespace DotRecast.Recast for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { - RcCompactSpan s = chf.spans[i]; + ref RcCompactSpan s = ref chf.spans[i]; if (chf.areas[i] == RC_NULL_AREA) { continue; @@ -1843,11 +1849,11 @@ namespace DotRecast.Recast // -x int previd = 0; - if (GetCon(s, 0) != RC_NOT_CONNECTED) + if (GetCon(ref s, 0) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(0); int ay = y + GetDirOffsetY(0); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 0); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 0); if ((srcReg[ai] & RC_BORDER_REG) == 0 && chf.areas[i] == chf.areas[ai]) { previd = srcReg[ai]; @@ -1863,11 +1869,11 @@ namespace DotRecast.Recast } // -y - if (GetCon(s, 3) != RC_NOT_CONNECTED) + if (GetCon(ref s, 3) != RC_NOT_CONNECTED) { int ax = x + GetDirOffsetX(3); int ay = y + GetDirOffsetY(3); - int ai = chf.cells[ax + ay * w].index + GetCon(s, 3); + int ai = chf.cells[ax + ay * w].index + GetCon(ref s, 3); if (srcReg[ai] != 0 && (srcReg[ai] & RC_BORDER_REG) == 0 && chf.areas[i] == chf.areas[ai]) { int nr = srcReg[ai]; @@ -1909,7 +1915,7 @@ namespace DotRecast.Recast // Remap IDs for (int x = borderSize; x < w - borderSize; ++x) { - ref readonly RcCompactCell c = ref chf.cells[x + y * w]; + ref RcCompactCell c = ref chf.cells[x + y * w]; for (int i = c.index, ni = c.index + c.count; i < ni; ++i) { @@ -1932,7 +1938,10 @@ namespace DotRecast.Recast // Store the result out. for (int i = 0; i < chf.spanCount; ++i) { - chf.spans[i].reg = srcReg[i]; + chf.spans[i] = RcCompactSpanBuilder + .NewBuilder(ref chf.spans[i]) + .WithReg(srcReg[i]) + .Build(); } } }