예제 #1
0
        public static void FloodFillComponent(cpBody root, cpBody body)
        {
            // Kinematic bodies cannot be put to sleep and prevent bodies they are touching from sleeping.
            // Static bodies are effectively sleeping all the time.
            if (body.bodyType == cpBodyType.DYNAMIC)
            {
                cpBody other_root = cp.ComponentRoot(body);
                if (other_root == null)
                {
                    cp.componentAdd(root, body);
                    body.eachArbiter((arb, o) =>
                    {
                        FloodFillComponent(root, (body == arb.body_a ?
                                                  arb.body_b : arb.body_a));
                    }, null);

                    body.eachConstraint((constraint, o) =>
                    {
                        FloodFillComponent(root,
                                           (body == constraint.a ? constraint.b : constraint.a));
                    }, null);
                }
                else
                {
                    cp.AssertSoft(other_root == root, "Internal Error: Inconsistency dectected in the contact graph.");
                }
            }
        }
예제 #2
0
        public void DeactivateBody(cpBody body)
        {
            cp.AssertHard(body.bodyType == cpBodyType.DYNAMIC, "Internal error: Attempting to deactivate a non-dynamic body.");

            this.dynamicBodies.Remove(body);

            body.eachShape((shape, o) =>
            {
                this.dynamicShapes.Remove(shape.hashid);
                this.staticShapes.Insert(shape.hashid, shape);
            }, null);


            body.eachArbiter((arb, o) =>
            {
                var bodyA = arb.body_a;

                if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                {
                    this.UncacheArbiter(arb);
                }
            }, null);


            body.eachConstraint((constraint, o) =>
            {
                var bodyA = constraint.a;
                if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                {
                    this.constraints.Remove(constraint);
                }
            }, null);
        }
예제 #3
0
        public static void FloodFillComponent(cpBody root, cpBody body)
        {
            // Kinematic bodies cannot be put to sleep and prevent bodies they are touching from sleeping.
            // Static bodies are effectively sleeping all the time.
            if (body.bodyType == cpBodyType.DYNAMIC)
            {
                cpBody other_root = cp.ComponentRoot(body);
                if (other_root == null)
                {
                    cp.componentAdd(root, body);
                    body.eachArbiter((arb, o) =>
                    {
                        FloodFillComponent(root, (body == arb.body_a ?
                            arb.body_b : arb.body_a));

                    }, null);

                    body.eachConstraint((constraint, o) =>
                    {

                        FloodFillComponent(root,
                            (body == constraint.a ? constraint.b : constraint.a));

                    }, null);

                }
                else
                {
                    cp.AssertSoft(other_root == root, "Internal Error: Inconsistency dectected in the contact graph.");
                }
            }
        }
예제 #4
0
        public void ActivateBody(cpBody body)
        {
            cp.AssertHard(body.bodyType == cpBodyType.DYNAMIC, "Internal error: Attempting to deactivate a non-dynamic body.");

            if (this.IsLocked)
            {
                // cpSpaceActivateBody() is called again once the space is unlocked
                if (!this.rousedBodies.Contains(body))
                {
                    this.rousedBodies.Add(body);
                }
            }
            else
            {
                cp.AssertSoft(body.nodeRoot == null &&
                              body.nodeNext == null, "Internal error: Activating body non-NULL node pointers.");


                this.dynamicBodies.Add(body);

                body.eachShape((s, o) =>
                {
                    this.staticShapes.Remove(s.hashid);
                    this.dynamicShapes.Insert(s.hashid, s);
                }, null);


                body.eachArbiter((arb, o) =>
                {
                    cpBody bodyA = arb.body_a;

                    // Arbiters are shared between two bodies that are always woken up together.
                    // You only want to restore the arbiter once, so bodyA is arbitrarily chosen to own the arbiter.
                    // The edge case is when static bodies are involved as the static bodies never actually sleep.
                    // If the static body is bodyB then all is good. If the static body is bodyA, that can easily be checked.
                    if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                    {
                        cpShape a = arb.a, b = arb.b;
                        this.cachedArbiters.Add(cp.CP_HASH_PAIR(a.hashid, b.hashid), arb);

                        // Update the arbiter's state
                        arb.stamp   = this.stamp;
                        arb.handler = this.LookupHandler(a.type, b.type, defaultHandler);
                        this.arbiters.Add(arb);
                    }
                }, null);

                body.eachConstraint((constraint, o) =>
                {
                    var bodyA = constraint.a;
                    if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                    {
                        this.constraints.Add(constraint);
                    }
                }, null);
            }
        }
예제 #5
0
        public static bool QueryRejectConstraint(cpBody a, cpBody b)
        {
            bool returnValue = false;

            a.eachConstraint((constraint, o) =>
            {
                if (
                    !constraint.collideBodies && (
                        (constraint.a == a && constraint.b == b) ||
                        (constraint.a == b && constraint.b == a)
                        ))
                {
                    returnValue = true;
                }
            }, null);

            return(returnValue);
        }
예제 #6
0
        public void ActivateBody(cpBody body)
        {
            cp.AssertHard(body.bodyType == cpBodyType.DYNAMIC, "Internal error: Attempting to deactivate a non-dynamic body.");

            if (this.IsLocked)
            {
                // cpSpaceActivateBody() is called again once the space is unlocked
                if (!this.rousedBodies.Contains(body))
                    this.rousedBodies.Add(body);
            }
            else
            {

                cp.AssertSoft(body.nodeRoot == null &&
                    body.nodeNext == null, "Internal error: Activating body non-NULL node pointers.");

                this.dynamicBodies.Add(body);

                body.eachShape((s, o) =>
                {
                    this.staticShapes.Remove(s.hashid);
                    this.dynamicShapes.Insert(s.hashid, s);
                }, null);

                body.eachArbiter((arb, o) =>
                {
                    cpBody bodyA = arb.body_a;

                    // Arbiters are shared between two bodies that are always woken up together.
                    // You only want to restore the arbiter once, so bodyA is arbitrarily chosen to own the arbiter.
                    // The edge case is when static bodies are involved as the static bodies never actually sleep.
                    // If the static body is bodyB then all is good. If the static body is bodyA, that can easily be checked.
                    if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                    {
                        cpShape a = arb.a, b = arb.b;
                        this.cachedArbiters.Add(cp.CP_HASH_PAIR(a.hashid, b.hashid), arb);

                        // Update the arbiter's state
                        arb.stamp = this.stamp;
                        arb.handler = this.LookupHandler(a.type, b.type, defaultHandler);
                        this.arbiters.Add(arb);
                    }

                }, null);

                body.eachConstraint((constraint, o) =>
                {
                    var bodyA = constraint.a;
                    if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                        this.constraints.Add(constraint);

                }, null);

            }
        }
예제 #7
0
        public void DeactivateBody(cpBody body)
        {
            cp.AssertHard(body.bodyType == cpBodyType.DYNAMIC, "Internal error: Attempting to deactivate a non-dynamic body.");

            this.dynamicBodies.Remove(body);

            body.eachShape((shape, o) =>
                {
                    this.dynamicShapes.Remove(shape.hashid);
                    this.staticShapes.Insert(shape.hashid, shape);
                }, null);

            body.eachArbiter((arb, o) =>
            {

                var bodyA = arb.body_a;

                if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                {
                    this.UncacheArbiter(arb);
                }

            }, null);

            body.eachConstraint((constraint, o) =>
            {
                var bodyA = constraint.a;
                if (body == bodyA || bodyA.bodyType == cpBodyType.STATIC)
                    this.constraints.Remove(constraint);

            }, null);
        }