/// <summary> /// Describes whether this instance test overlap /// </summary> /// <param name="b">The </param> /// <param name="p">The </param> /// <returns>The bool</returns> internal bool TestOverlap(BoundValues b, Proxy p) { for (int axis = 0; axis < 2; ++axis) { Bound[] bounds = Bounds[axis]; Box2DxDebug.Assert(p.LowerBounds[axis] < 2 * ProxyCount); Box2DxDebug.Assert(p.UpperBounds[axis] < 2 * ProxyCount); if (b.LowerValues[axis] > bounds[p.UpperBounds[axis]].Value) { return(false); } if (b.UpperValues[axis] < bounds[p.LowerBounds[axis]].Value) { return(false); } } return(true); }
// Call MoveProxy as many times as you like, then when you are done // call Commit to finalized the proxy pairs (for your time step). /// <summary> /// Moves the proxy using the specified proxy id /// </summary> /// <param name="proxyId">The proxy id</param> /// <param name="aabb">The aabb</param> public void MoveProxy(int proxyId, Aabb aabb) { if (proxyId == PairManager.NullProxy || Settings.MaxProxies <= proxyId) { Box2DxDebug.Assert(false); return; } if (aabb.IsValid == false) { Box2DxDebug.Assert(false); return; } int boundCount = 2 * ProxyCount; Proxy proxy1 = ProxyPool[proxyId]; // Get new bound values BoundValues newValues = new BoundValues(); ComputeBounds(out newValues.LowerValues, out newValues.UpperValues, aabb); // Get old bound values BoundValues oldValues = new BoundValues(); for (int axis = 0; axis < 2; ++axis) { oldValues.LowerValues[axis] = Bounds[axis][proxy1.LowerBounds[axis]].Value; oldValues.UpperValues[axis] = Bounds[axis][proxy1.UpperBounds[axis]].Value; } for (int axis = 0; axis < 2; ++axis) { Bound[] bounds = Bounds[axis]; int lowerIndex = proxy1.LowerBounds[axis]; int upperIndex = proxy1.UpperBounds[axis]; ushort lowerValue = newValues.LowerValues[axis]; ushort upperValue = newValues.UpperValues[axis]; int deltaLower = lowerValue - bounds[lowerIndex].Value; int deltaUpper = upperValue - bounds[upperIndex].Value; bounds[lowerIndex].Value = lowerValue; bounds[upperIndex].Value = upperValue; // // Expanding adds overlaps // // Should we move the lower bound down? if (deltaLower < 0) { int index = lowerIndex; while (index > 0 && lowerValue < bounds[index - 1].Value) { Bound bound = bounds[index]; Bound prevBound = bounds[index - 1]; int prevProxyId = prevBound.ProxyId; Proxy prevProxy = ProxyPool[prevBound.ProxyId]; ++prevBound.StabbingCount; if (prevBound.IsUpper) { if (TestOverlap(newValues, prevProxy)) { PairManager.AddBufferedPair(proxyId, prevProxyId); } ++prevProxy.UpperBounds[axis]; ++bound.StabbingCount; } else { ++prevProxy.LowerBounds[axis]; --bound.StabbingCount; } --proxy1.LowerBounds[axis]; Math.Swap(ref bounds[index], ref bounds[index - 1]); --index; } } // Should we move the upper bound up? if (deltaUpper > 0) { int index = upperIndex; while (index < boundCount - 1 && bounds[index + 1].Value <= upperValue) { Bound bound = bounds[index]; Bound nextBound = bounds[index + 1]; int nextProxyId = nextBound.ProxyId; Proxy nextProxy = ProxyPool[nextProxyId]; ++nextBound.StabbingCount; if (nextBound.IsLower) { if (TestOverlap(newValues, nextProxy)) { PairManager.AddBufferedPair(proxyId, nextProxyId); } --nextProxy.LowerBounds[axis]; ++bound.StabbingCount; } else { --nextProxy.UpperBounds[axis]; --bound.StabbingCount; } ++proxy1.UpperBounds[axis]; Math.Swap(ref bounds[index], ref bounds[index + 1]); ++index; } } // // Shrinking removes overlaps // // Should we move the lower bound up? if (deltaLower > 0) { int index = lowerIndex; while (index < boundCount - 1 && bounds[index + 1].Value <= lowerValue) { Bound bound = bounds[index]; Bound nextBound = bounds[index + 1]; int nextProxyId = nextBound.ProxyId; Proxy nextProxy = ProxyPool[nextProxyId]; --nextBound.StabbingCount; if (nextBound.IsUpper) { if (TestOverlap(oldValues, nextProxy)) { PairManager.RemoveBufferedPair(proxyId, nextProxyId); } --nextProxy.UpperBounds[axis]; --bound.StabbingCount; } else { --nextProxy.LowerBounds[axis]; ++bound.StabbingCount; } ++proxy1.LowerBounds[axis]; Math.Swap(ref bounds[index], ref bounds[index + 1]); ++index; } } // Should we move the upper bound down? if (deltaUpper < 0) { int index = upperIndex; while (index > 0 && upperValue < bounds[index - 1].Value) { Bound bound = bounds[index]; Bound prevBound = bounds[index - 1]; int prevProxyId = prevBound.ProxyId; Proxy prevProxy = ProxyPool[prevProxyId]; --prevBound.StabbingCount; if (prevBound.IsLower) { if (TestOverlap(oldValues, prevProxy)) { PairManager.RemoveBufferedPair(proxyId, prevProxyId); } ++prevProxy.LowerBounds[axis]; --bound.StabbingCount; } else { ++prevProxy.UpperBounds[axis]; ++bound.StabbingCount; } --proxy1.UpperBounds[axis]; Math.Swap(ref bounds[index], ref bounds[index - 1]); --index; } } } if (IsValidate) { Validate(); } }