public ColliderContact(Contact contact) { this.colliderA = contact.FixtureA.Body.UserData; this.colliderB = contact.FixtureB.Body.UserData; involvesATrigger = colliderA.isTrigger || colliderB.isTrigger; // Creates collisions Microsoft.Xna.Framework.Vector2 normal; FarseerPhysics.Common.FixedArray2<Microsoft.Xna.Framework.Vector2> points; contact.GetWorldManifold(out normal, out points); collisionBToA = new Collision() { collider = colliderB, relativeVelocity = ((colliderA.rigidbody != null) ? colliderA.rigidbody.velocity : Vector3.zero) - ((colliderB.rigidbody != null) ? colliderB.rigidbody.velocity : Vector3.zero), contacts = new ContactPoint[contact.Manifold.PointCount] }; collisionAToB = new Collision() { collider = colliderA, relativeVelocity = ((colliderB.rigidbody != null) ? colliderB.rigidbody.velocity : Vector3.zero) - ((colliderA.rigidbody != null) ? colliderA.rigidbody.velocity : Vector3.zero), contacts = new ContactPoint[contact.Manifold.PointCount] }; for (int j = 0; j < collisionBToA.contacts.Length; j++) { collisionBToA.contacts[j].thisCollider = colliderB; collisionBToA.contacts[j].otherCollider = colliderA; collisionBToA.contacts[j].point = VectorConverter.Convert(points[j], colliderB.to2dMode); collisionBToA.contacts[j].normal = VectorConverter.Convert(-normal, colliderB.to2dMode); collisionAToB.contacts[j].thisCollider = colliderA; collisionAToB.contacts[j].otherCollider = colliderB; collisionAToB.contacts[j].point = VectorConverter.Convert(points[j], colliderA.to2dMode); collisionAToB.contacts[j].normal = VectorConverter.Convert(normal, colliderA.to2dMode); } }
public Stay(Collision collisionAToB, Collision collisionBToA, GameObject gameObjectA, GameObject gameObjectB) { this.collisionAToB = collisionAToB; this.collisionBToA = collisionBToA; colliderToTriggerA = collisionAToB.collider; colliderToTriggerB = collisionBToA.collider; this.gameObjectA = gameObjectA; this.gameObjectB = gameObjectB; }
public void Update() { for (int i = 0; i < endContacts.Count; ++i) { Contact contact = endContacts[i]; Fixture fixtureA = contact.FixtureA; Fixture fixtureB = contact.FixtureB; if (fixtureA == null || fixtureB == null) { continue; } if (fixtureA.Body.BodyType == BodyType.Static && fixtureB.Body.BodyType == BodyType.Static) { continue; } Component compA = fixtureA.Body.UserData; Component compB = fixtureB.Body.UserData; if (compA == null || compB == null) { continue; } if (fixtureA.IsSensor || fixtureB.IsSensor) { RemoveStay(compA.collider, compB.collider); compA.gameObject.OnTriggerExit(compB.collider); compB.gameObject.OnTriggerExit(compA.collider); } else { if (compA.rigidbody == null && compB.rigidbody == null) { continue; } if (compA.rigidbody != null && compB.rigidbody != null && compA.rigidbody.isKinematic && compB.rigidbody.isKinematic) { continue; } RemoveStay(compA.collider, compB.collider); Microsoft.Xna.Framework.Vector2 normal; FarseerPhysics.Common.FixedArray2<Microsoft.Xna.Framework.Vector2> points; contact.GetWorldManifold(out normal, out points); Collision coll = new Collision() { collider = compB.collider, relativeVelocity = ((compA.rigidbody != null) ? compA.rigidbody.velocity : Vector3.zero) - ((compB.rigidbody != null) ? compB.rigidbody.velocity : Vector3.zero), contacts = new ContactPoint[2] }; for (int j = 0; j < 2; j++) { coll.contacts[j].thisCollider = compA.collider; coll.contacts[j].otherCollider = compB.collider; coll.contacts[j].point = VectorConverter.Convert(points[j], compA.collider.to2dMode); coll.contacts[j].normal = VectorConverter.Convert(normal, compA.collider.to2dMode); } compA.gameObject.OnCollisionExit(coll); coll.SetColliders(compB.collider, compA.collider); compB.gameObject.OnCollisionExit(coll); } } for (int i = staying.Count - 1; i >= 0; i--) { if (staysToRemove[i] || staying[i].colliderToTriggerA.gameObject == null || staying[i].colliderToTriggerB.gameObject == null || !staying[i].colliderToTriggerA.gameObject.active || !staying[i].colliderToTriggerB.gameObject.active) { staysToRemove[i] = false; staying.RemoveAt(i); continue; } else if (!staying[i].collision) { staying[i].gameObjectA.OnTriggerStay(staying[i].colliderToTriggerA); staying[i].gameObjectB.OnTriggerStay(staying[i].colliderToTriggerB); } else { staying[i].gameObjectA.OnCollisionStay(staying[i].collisionBToA); staying[i].gameObjectB.OnCollisionStay(staying[i].collisionAToB); } } for (int i = 0; i < beginContacts.Count; ++i) { Contact contact = beginContacts[i]; Fixture fixtureA = contact.FixtureA; Fixture fixtureB = contact.FixtureB; if (fixtureA == null || fixtureB == null) { continue; } #if DEBUG if (DebugSettings.LogCollisions) { Debug.Log(string.Format("Collision Begin: {0} <-> {1}", fixtureA.Body, fixtureB.Body)); } #endif if (fixtureA.Body.BodyType == BodyType.Static && fixtureB.Body.BodyType == BodyType.Static) { continue; } Component compA = fixtureA.Body.UserData; Component compB = fixtureB.Body.UserData; if (compA == null || compB == null) { continue; } if (fixtureA.IsSensor || fixtureB.IsSensor) { staying.Add(new Stay(compB.collider, compA.collider, compA.gameObject, compB.gameObject )); compA.gameObject.OnTriggerEnter(compB.collider); compB.gameObject.OnTriggerEnter(compA.collider); } else { if (compA.rigidbody == null && compB.rigidbody == null) { continue; } if (compA.rigidbody != null && compB.rigidbody != null && compA.rigidbody.isKinematic && compB.rigidbody.isKinematic) { continue; } Microsoft.Xna.Framework.Vector2 normal; FarseerPhysics.Common.FixedArray2<Microsoft.Xna.Framework.Vector2> points; contact.GetWorldManifold(out normal, out points); Collision collisionBToA = new Collision() { collider = compB.collider, relativeVelocity = ((compA.rigidbody != null) ? compA.rigidbody.velocity : Vector3.zero) - ((compB.rigidbody != null) ? compB.rigidbody.velocity : Vector3.zero), contacts = new ContactPoint[contact.Manifold.PointCount] }; Collision collisionAToB = new Collision() { collider = compA.collider, relativeVelocity = ((compB.rigidbody != null) ? compB.rigidbody.velocity : Vector3.zero) - ((compA.rigidbody != null) ? compA.rigidbody.velocity : Vector3.zero), contacts = new ContactPoint[contact.Manifold.PointCount] }; for (int j = 0; j < collisionBToA.contacts.Length; j++) { collisionBToA.contacts[j].thisCollider = compB.collider; collisionBToA.contacts[j].otherCollider = compA.collider; collisionBToA.contacts[j].point = VectorConverter.Convert(points[j], compB.collider.to2dMode); collisionBToA.contacts[j].normal = VectorConverter.Convert(-normal, compB.collider.to2dMode); collisionAToB.contacts[j].thisCollider = compA.collider; collisionAToB.contacts[j].otherCollider = compB.collider; collisionAToB.contacts[j].point = VectorConverter.Convert(points[j], compA.collider.to2dMode); collisionAToB.contacts[j].normal = VectorConverter.Convert(normal, compA.collider.to2dMode); } Stay s = new Stay(collisionAToB, collisionBToA, compA.gameObject, compB.gameObject); staying.Add(s); s.gameObjectA.OnCollisionEnter(s.collisionBToA); s.gameObjectB.OnCollisionEnter(s.collisionAToB); } } beginContacts.Clear(); endContacts.Clear(); }
public Stay(Collider colliderToTriggerA, Collider colliderToTriggerB, GameObject gameObjectA, GameObject gameObjectB) { this.colliderToTriggerA = colliderToTriggerA; this.colliderToTriggerB = colliderToTriggerB; this.gameObjectA = gameObjectA; this.gameObjectB = gameObjectB; collisionAToB = null; collisionBToA = null; }