void Collision_optimized(float timeStep)
{
lock(_contactcountLock)
m_global_contactcount = 0;
//Clear out all the colliding attributes before we begin to collide anyone
foreach (ODECharacter chr in _characters)
{
chr.IsColliding = false;
chr.IsTruelyColliding = false;
}
List<IntPtr> shells = _characters.Where(chr => chr != null && chr.Shell != IntPtr.Zero && chr.Body != IntPtr.Zero).Select<ODECharacter, IntPtr>(chr => chr.Shell).ToList();
lock (_activeprimsLock)
{
List<ODEPrim> removeprims = null;
foreach (ODEPrim chr in _activeprims)
{
//Fix colliding atributes!
chr.IsColliding = false;
chr.LinkSetIsColliding = false;
}
if (space != IntPtr.Zero)
{
List<ODEPrim> primsToCollide = new List<ODEPrim>(_activeprims.Where(
prm => prm != null && prm.Body != IntPtr.Zero && d.BodyIsEnabled(prm.Body) &&
!prm.m_disabled && !prm.m_frozen && prm.prim_geom != IntPtr.Zero));
shells.AddRange(primsToCollide.ConvertAll<IntPtr>(prm => prm.prim_geom));
foreach (IntPtr shell in shells)
{
try
{
if (ContinueCollisionProcessing)
d.SpaceCollide2(space, shell, IntPtr.Zero, nearCallback);
else
{
//Do a step so that we can do the rest of the contacts, since
// otherwise, we get prim explosions inworld
lock(_contactcountLock)
m_global_contactcount = 0;
d.WorldQuickStep(world, ODE_STEPSIZE);
d.JointGroupEmpty(contactgroup);
d.SpaceCollide2(space, shell, IntPtr.Zero, nearCallback);
}
}
catch (AccessViolationException)
{
MainConsole.Instance.Warn("[ODE Physics]: Unable to space collide");
}
}
/*if (shells.Count > 0)
{
List<UnmanagedODE.ContactGeom> contacts = UnmanagedODE.UnmanagedODEPhysics.CollisionLoop(space, shells);
}*/
foreach (ODEPrim prm in
_activeprims.Where(prm => prm != null && (prm.m_frozen || prm.prim_geom == IntPtr.Zero)))
{
if (removeprims == null)
removeprims = new List<ODEPrim>();
removeprims.Add(prm);
if (prm.prim_geom == IntPtr.Zero)
MainConsole.Instance.Debug("[ODE Physics]: unable to collide test active prim against space. The space was zero, the geom was zero or " +
"it was in the process of being removed. Removed it from the active prim list. This needs to be fixed!");
}
if (removeprims != null)
{
foreach (ODEPrim chr in removeprims)
_activeprims.Remove(chr);
}
}
}
if (m_filterCollisions)
_perloopContact.Clear();
}