Exemple #1
0
        internal override void UpdateFixture(bool updateShape = false)
        {
            // Loop shapes aren't allowed on nonstatic bodies.
            if (this.Parent != null && this.Parent.BodyType != BodyType.Static)
            {
                this.DestroyFixture(this.Parent.PhysicsBody, false);
                return;
            }

            base.UpdateFixture(updateShape);
            if (this.fixture == null)
            {
                return;
            }
            if (this.Parent == null)
            {
                return;
            }

            float scale = 1.0f;

            if (this.Parent.GameObj != null && this.Parent.GameObj.Transform != null)
            {
                scale = this.Parent.GameObj.Transform.Scale;
            }

            LoopShape poly = this.fixture.Shape as LoopShape;

            poly.Vertices = this.CreateVertices(scale);
        }
Exemple #2
0
        public void DrawShape(Fixture fixture, Transform xf, Color color)
        {
            switch (fixture.ShapeType)
            {
            case ShapeType.Circle:
            {
                CircleShape circle = (CircleShape)fixture.Shape;

                Vector2 center = MathUtils.Multiply(ref xf, circle.Position);
                float   radius = circle.Radius;
                Vector2 axis   = xf.R.Col1;

                DrawSolidCircle(center, radius, axis, color);
                //DrawCircle(center, radius, Color.White);
            }
            break;

            case ShapeType.Polygon:
            {
                PolygonShape poly        = (PolygonShape)fixture.Shape;
                int          vertexCount = poly.Vertices.Count;
                Debug.Assert(vertexCount <= Settings.MaxPolygonVertices);

                for (int i = 0; i < vertexCount; ++i)
                {
                    _tempVertices[i] = MathUtils.Multiply(ref xf, poly.Vertices[i]);
                }

                DrawSolidPolygon(_tempVertices, vertexCount, color);
            }
            break;


            case ShapeType.Edge:
            {
                EdgeShape edge = (EdgeShape)fixture.Shape;
                Vector2   v1   = MathUtils.Multiply(ref xf, edge.Vertex1);
                Vector2   v2   = MathUtils.Multiply(ref xf, edge.Vertex2);
                DrawSegment(v1, v2, color);
            }
            break;

            case ShapeType.Loop:
            {
                LoopShape loop  = (LoopShape)fixture.Shape;
                int       count = loop.Vertices.Count;

                Vector2 v1 = MathUtils.Multiply(ref xf, loop.Vertices[count - 1]);
                DrawCircle(v1, 0.05f, color);
                for (int i = 0; i < count; ++i)
                {
                    Vector2 v2 = MathUtils.Multiply(ref xf, loop.Vertices[i]);
                    DrawSegment(v1, v2, color);
                    v1 = v2;
                }
            }
            break;
            }
        }
Exemple #3
0
        /// <summary>
        /// Initialize the proxy using the given shape. The shape
        /// must remain in scope while the proxy is in use.
        /// </summary>
        /// <param name="shape">The shape.</param>
        /// <param name="index">The index.</param>
        public void Set(Shape shape, int index)
        {
            switch (shape.ShapeType)
            {
            case ShapeType.Circle:
            {
                CircleShape circle = (CircleShape)shape;
                Vertices = new Vertices(1);
                Vertices.Add(circle.Position);
                Radius = circle.Radius;
            }
            break;

            case ShapeType.Polygon:
            {
                PolygonShape polygon = (PolygonShape)shape;
                Vertices = polygon.Vertices;
                Radius   = polygon.Radius;
            }
            break;

            case ShapeType.Loop:
            {
                LoopShape loop = (LoopShape)shape;
                Debug.Assert(0 <= index && index < loop.Vertices.Count);

                Buffer[0] = loop.Vertices[index];
                if (index + 1 < loop.Vertices.Count)
                {
                    Buffer[1] = loop.Vertices[index + 1];
                }
                else
                {
                    Buffer[1] = loop.Vertices[0];
                }

                Vertices = new Vertices(2);
                Vertices.Add(Buffer[0]);
                Vertices.Add(Buffer[1]);
                Radius = loop.Radius;
            }
            break;

            case ShapeType.Edge:
            {
                EdgeShape edge = (EdgeShape)shape;
                Vertices = new Vertices(2);
                Vertices.Add(edge.Vertex1);
                Vertices.Add(edge.Vertex2);
                Radius = edge.Radius;
            }
            break;

            default:
                Debug.Assert(false);
                break;
            }
        }
Exemple #4
0
    void DrawShape(Fixture fixture, Box2D.Transform xf, Color color)
    {
        switch (fixture.ShapeType)
        {
        case ShapeType.Circle:
        {
            CircleShape circle = (CircleShape)fixture.GetShape();

            Vector2 center = MathUtils.Multiply(ref xf, circle._p);
            float   radius = circle._radius;
            Vector2 axis   = xf.R.col1;

            drawSolidCircle(center, radius, axis, color);
        }
        break;

        case ShapeType.Polygon:
        {
            PolygonShape          poly        = (PolygonShape)fixture.GetShape();
            int                   vertexCount = poly._vertexCount;
            FixedArray8 <Vector2> vertices    = new FixedArray8 <Vector2>();

            for (int i = 0; i < vertexCount; ++i)
            {
                vertices[i] = MathUtils.Multiply(ref xf, poly._vertices[i]);
            }

            drawSolidPolygon(ref vertices, vertexCount, color, true);
        }
        break;

        case ShapeType.Edge:
        {
            EdgeShape edge = (EdgeShape)fixture.GetShape();
            Vector2   v1   = MathUtils.Multiply(ref xf, edge._vertex1);
            Vector2   v2   = MathUtils.Multiply(ref xf, edge._vertex2);
            drawSegment(v1, v2, color);
        }
        break;

        case ShapeType.Loop:
        {
            LoopShape loop  = (LoopShape)fixture.GetShape();
            int       count = loop._count;

            Vector2 v1 = MathUtils.Multiply(ref xf, loop._vertices[count - 1]);
            for (int i = 0; i < count; ++i)
            {
                Vector2 v2 = MathUtils.Multiply(ref xf, loop._vertices[i]);
                drawSegment(v1, v2, color);
                v1 = v2;
            }
        }
        break;
        }
    }
        private static JObject SerializeLoopShape(LoopShape shape)
        {
            var jsonLoopShape = new JObject();

            jsonLoopShape.Add(new JProperty("vertices", ToJsonObject(shape.Vertices)));
            jsonLoopShape.Add(new JProperty("hasNextVertex", true));
            jsonLoopShape.Add(new JProperty("hasPrevVertex", true));
            jsonLoopShape.Add(new JProperty("nextVertex", ToJsonObject(shape.Vertices[1])));
            jsonLoopShape.Add(new JProperty("prevVertex", ToJsonObject(shape.Vertices[shape.Vertices.Count - 2])));
            return(jsonLoopShape);
        }
        /// <summary>
        /// Initialize the proxy using the given shape. The shape
        /// must remain in scope while the proxy is in use.
        /// </summary>
        /// <param name="shape">The shape.</param>
        /// <param name="index">The index.</param>
        public void Set(Shape shape, int index)
        {
            switch (shape.ShapeType)
            {
            case ShapeType.Circle:
            {
                CircleShape circle = (CircleShape)shape;
                Vertices.Clear();
                Vertices.Add(circle.Position);
                Radius = circle.Radius;
            }
            break;

            case ShapeType.Polygon:
            {
                PolygonShape polygon = (PolygonShape)shape;
                Vertices.Clear();
                for (int i = 0; i < polygon.Vertices.Count; i++)
                {
                    Vertices.Add(polygon.Vertices[i]);
                }
                Radius = polygon.Radius;
            }
            break;

            case ShapeType.Loop:
            {
                LoopShape loop = (LoopShape)shape;
                Debug.Assert(0 <= index && index < loop.Vertices.Count);
                Vertices.Clear();
                Vertices.Add(loop.Vertices[index]);
                Vertices.Add(index + 1 < loop.Vertices.Count ? loop.Vertices[index + 1] : loop.Vertices[0]);

                Radius = loop.Radius;
            }
            break;

            case ShapeType.Edge:
            {
                EdgeShape edge = (EdgeShape)shape;
                Vertices.Clear();
                Vertices.Add(edge.Vertex1);
                Vertices.Add(edge.Vertex2);
                Radius = edge.Radius;
            }
            break;

            default:
                Debug.Assert(false);
                break;
            }
        }
Exemple #7
0
        /// <summary>
        /// Evaluate this contact with your own manifold and transforms.
        /// </summary>
        /// <param name="manifold">The manifold.</param>
        /// <param name="transformA">The first transform.</param>
        /// <param name="transformB">The second transform.</param>
        private void Evaluate(ref Manifold manifold, ref Transform transformA, ref Transform transformB)
        {
            switch (_type)
            {
            case ContactType.Polygon:
                Collision.Collision.CollidePolygons(ref manifold,
                                                    (PolygonShape)FixtureA.Shape, ref transformA,
                                                    (PolygonShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.PolygonAndCircle:
                Collision.Collision.CollidePolygonAndCircle(ref manifold,
                                                            (PolygonShape)FixtureA.Shape, ref transformA,
                                                            (CircleShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.EdgeAndCircle:
                Collision.Collision.CollideEdgeAndCircle(ref manifold,
                                                         (EdgeShape)FixtureA.Shape, ref transformA,
                                                         (CircleShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.EdgeAndPolygon:
                Collision.Collision.CollideEdgeAndPolygon(ref manifold,
                                                          (EdgeShape)FixtureA.Shape, ref transformA,
                                                          (PolygonShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.LoopAndCircle:
                LoopShape loop = (LoopShape)FixtureA.Shape;
                loop.GetChildEdge(ref _edge, ChildIndexA);
                Collision.Collision.CollideEdgeAndCircle(ref manifold, _edge, ref transformA,
                                                         (CircleShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.LoopAndPolygon:
                LoopShape loop2 = (LoopShape)FixtureA.Shape;
                loop2.GetChildEdge(ref _edge, ChildIndexA);
                Collision.Collision.CollideEdgeAndPolygon(ref manifold, _edge, ref transformA,
                                                          (PolygonShape)FixtureB.Shape, ref transformB);
                break;

            case ContactType.Circle:
                Collision.Collision.CollideCircles(ref manifold,
                                                   (CircleShape)FixtureA.Shape, ref transformA,
                                                   (CircleShape)FixtureB.Shape, ref transformB);
                break;
            }
        }
Exemple #8
0
        //Contributed by Matthew Bettcher

        /// <summary>
        /// Convert a path into a set of edges and attaches them to the specified body.
        /// Note: use only for static edges.
        /// </summary>
        /// <param name="path">The path.</param>
        /// <param name="body">The body.</param>
        /// <param name="subdivisions">The subdivisions.</param>
        public static void ConvertPathToEdges(Path path, Body body, int subdivisions)
        {
            Vertices verts = path.GetVertices(subdivisions);

            if (path.Closed)
            {
                LoopShape loop = new LoopShape(verts);
                body.CreateFixture(loop);
            }
            else
            {
                for (int i = 1; i < verts.Count; i++)
                {
                    body.CreateFixture(new EdgeShape(verts[i], verts[i - 1]));
                }
            }
        }
Exemple #9
0
 public void DrawLineShape(Shape shape, Color color)
 {
     if (!_hasBegun)
     {
         throw new InvalidOperationException("Begin must be called before DrawLineShape can be called.");
     }
     if (shape.ShapeType != ShapeType.Edge &&
         shape.ShapeType != ShapeType.Loop)
     {
         throw new NotSupportedException("The specified shapeType is not supported by LineBatch.");
     }
     if (shape.ShapeType == ShapeType.Edge)
     {
         if (_lineVertsCount >= _lineVertices.Length)
         {
             Flush();
         }
         EdgeShape edge = (EdgeShape)shape;
         _lineVertices[_lineVertsCount].Position     = new Vector3(edge.Vertex1, 0f);
         _lineVertices[_lineVertsCount + 1].Position = new Vector3(edge.Vertex2, 0f);
         _lineVertices[_lineVertsCount].Color        = _lineVertices[_lineVertsCount + 1].Color = color;
         _lineVertsCount += 2;
     }
     else if (shape.ShapeType == ShapeType.Loop)
     {
         LoopShape loop = (LoopShape)shape;
         for (int i = 0; i < loop.Vertices.Count; ++i)
         {
             if (_lineVertsCount >= _lineVertices.Length)
             {
                 Flush();
             }
             _lineVertices[_lineVertsCount].Position     = new Vector3(loop.Vertices[i], 0f);
             _lineVertices[_lineVertsCount + 1].Position = new Vector3(loop.Vertices.NextVertex(i), 0f);
             _lineVertices[_lineVertsCount].Color        = _lineVertices[_lineVertsCount + 1].Color = color;
             _lineVertsCount += 2;
         }
     }
 }
        public static Fixture AttachLoopShape(Vertices vertices, Body body, object userData)
        {
            LoopShape shape = new LoopShape(vertices);

            return(body.CreateFixture(shape, userData));
        }
        public static Fixture CreateLoopShape(Vertices vertices, float density, Body body)
        {
            LoopShape shape = new LoopShape(vertices, density);

            return(body.CreateFixture(shape));
        }
Exemple #12
0
        private PinballTest()
        {
            // Ground body
            Body ground;
            {
                ground = BodyFactory.CreateBody(World);

                Vertices vertices = new Vertices(5);
                vertices.Add(new Vector2(0.0f, -2.0f));
                vertices.Add(new Vector2(8.0f, 6.0f));
                vertices.Add(new Vector2(8.0f, 20.0f));
                vertices.Add(new Vector2(-8.0f, 20.0f));
                vertices.Add(new Vector2(-8.0f, 6.0f));

                LoopShape loop = new LoopShape(vertices);
                ground.CreateFixture(loop);
            }

            // Flippers
            {
                Vector2 p1 = new Vector2(-2.0f, 0f);
                Vector2 p2 = new Vector2(2.0f, 0f);

                Body leftFlipper = BodyFactory.CreateBody(World, p1);
                leftFlipper.BodyType = BodyType.Dynamic;
                Body rightFlipper = BodyFactory.CreateBody(World, p2);
                rightFlipper.BodyType = BodyType.Dynamic;

                PolygonShape box = new PolygonShape(1);
                box.SetAsBox(1.75f, 0.1f);

                leftFlipper.CreateFixture(box);
                rightFlipper.CreateFixture(box);

                _leftJoint = new RevoluteJoint(ground, leftFlipper, p1, Vector2.Zero);
                _leftJoint.MaxMotorTorque = 1000.0f;
                _leftJoint.LimitEnabled   = true;
                _leftJoint.MotorEnabled   = true;
                _leftJoint.MotorSpeed     = 0.0f;
                _leftJoint.LowerLimit     = -30.0f * Settings.Pi / 180.0f;
                _leftJoint.UpperLimit     = 5.0f * Settings.Pi / 180.0f;
                World.AddJoint(_leftJoint);

                _rightJoint = new RevoluteJoint(ground, rightFlipper, p2, Vector2.Zero);
                _rightJoint.MaxMotorTorque = 1000.0f;
                _rightJoint.LimitEnabled   = true;
                _rightJoint.MotorEnabled   = true;
                _rightJoint.MotorSpeed     = 0.0f;
                _rightJoint.LowerLimit     = -5.0f * Settings.Pi / 180.0f;
                _rightJoint.UpperLimit     = 30.0f * Settings.Pi / 180.0f;
                World.AddJoint(_rightJoint);
            }

            // Circle character
            {
                _ball          = BodyFactory.CreateBody(World, new Vector2(1.0f, 15.0f));
                _ball.BodyType = BodyType.Dynamic;
                _ball.IsBullet = true;
                _ball.CreateFixture(new CircleShape(0.2f, 1.0f));
            }
        }
        public static Fixture CreateLoopShape(Vertices vertices, float density, Body body, Object userData)
        {
            LoopShape shape = new LoopShape(vertices, density);

            return(body.CreateFixture(shape, userData));
        }
        private CharacterCollisionTest()
        {
            //Ground body
            Body ground = BodyFactory.CreateEdge(World, new Vector2(-40.0f, 0.0f), new Vector2(40.0f, 0.0f));

            // Collinear edges
            EdgeShape shape = new EdgeShape(new Vector2(-8.0f, 1.0f), new Vector2(-6.0f, 1.0f));

            ground.CreateFixture(shape);
            shape = new EdgeShape(new Vector2(-6.0f, 1.0f), new Vector2(-4.0f, 1.0f));
            ground.CreateFixture(shape);
            shape = new EdgeShape(new Vector2(-4.0f, 1.0f), new Vector2(-2.0f, 1.0f));
            ground.CreateFixture(shape);

            // Square tiles
            PolygonShape tile = new PolygonShape(1);

            tile.SetAsBox(1.0f, 1.0f, new Vector2(4.0f, 3.0f), 0.0f);
            ground.CreateFixture(tile);
            tile.SetAsBox(1.0f, 1.0f, new Vector2(6.0f, 3.0f), 0.0f);
            ground.CreateFixture(tile);
            tile.SetAsBox(1.0f, 1.0f, new Vector2(8.0f, 3.0f), 0.0f);
            ground.CreateFixture(tile);

            // Square made from an edge loop.
            Vertices vertices = new Vertices(4);

            vertices.Add(new Vector2(-1.0f, 3.0f));
            vertices.Add(new Vector2(1.0f, 3.0f));
            vertices.Add(new Vector2(1.0f, 5.0f));
            vertices.Add(new Vector2(-1.0f, 5.0f));
            LoopShape loopShape = new LoopShape(vertices);

            ground.CreateFixture(loopShape);

            // Edge loop.
            vertices = new Vertices(10);
            vertices.Add(new Vector2(0.0f, 0.0f));
            vertices.Add(new Vector2(6.0f, 0.0f));
            vertices.Add(new Vector2(6.0f, 2.0f));
            vertices.Add(new Vector2(4.0f, 1.0f));
            vertices.Add(new Vector2(2.0f, 2.0f));
            vertices.Add(new Vector2(-2.0f, 2.0f));
            vertices.Add(new Vector2(-4.0f, 3.0f));
            vertices.Add(new Vector2(-6.0f, 2.0f));
            vertices.Add(new Vector2(-6.0f, 0.0f));

            BodyFactory.CreateLoopShape(World, vertices, new Vector2(-10, 4));

            // Square character
            Body squareCharacter = BodyFactory.CreateRectangle(World, 1, 1, 20);

            squareCharacter.Position        = new Vector2(-3.0f, 5.0f);
            squareCharacter.BodyType        = BodyType.Dynamic;
            squareCharacter.FixedRotation   = true;
            squareCharacter.SleepingAllowed = false;

            squareCharacter.OnCollision  += CharacterOnCollision;
            squareCharacter.OnSeparation += CharacterOnSeparation;

            // Square character 2
            Body squareCharacter2 = BodyFactory.CreateRectangle(World, 0.5f, 0.5f, 20);

            squareCharacter2.Position        = new Vector2(-5.0f, 5.0f);
            squareCharacter2.BodyType        = BodyType.Dynamic;
            squareCharacter2.FixedRotation   = true;
            squareCharacter2.SleepingAllowed = false;

            // Hexagon character
            float       angle = 0.0f;
            const float delta = Settings.Pi / 3.0f;

            vertices = new Vertices(6);

            for (int i = 0; i < 6; ++i)
            {
                vertices.Add(new Vector2(0.5f * (float)Math.Cos(angle), 0.5f * (float)Math.Sin(angle)));
                angle += delta;
            }

            Body hexCharacter = BodyFactory.CreatePolygon(World, vertices, 20);

            hexCharacter.Position        = new Vector2(-5.0f, 8.0f);
            hexCharacter.BodyType        = BodyType.Dynamic;
            hexCharacter.FixedRotation   = true;
            hexCharacter.SleepingAllowed = false;

            // Circle character
            Body circleCharacter = BodyFactory.CreateCircle(World, 0.5f, 20);

            circleCharacter.Position        = new Vector2(3.0f, 5.0f);
            circleCharacter.BodyType        = BodyType.Dynamic;
            circleCharacter.FixedRotation   = true;
            circleCharacter.SleepingAllowed = false;
        }
Exemple #15
0
        public CharacterCollision()
        {
            // Ground body
            {
                BodyDef bd     = new BodyDef();
                Body    ground = _world.CreateBody(bd);

                PolygonShape shape = new PolygonShape();
                shape.SetAsEdge(new Vector2(-20.0, 0.0), new Vector2(20.0, 0.0));
                ground.CreateFixture(shape, 0.0);
            }

            // Collinear edges
            {
                BodyDef bd     = new BodyDef();
                Body    ground = _world.CreateBody(bd);

                PolygonShape shape = new PolygonShape();
                shape.SetAsEdge(new Vector2(-8.0f, 1.0f), new Vector2(-6.0f, 1.0f));
                ground.CreateFixture(shape, 0.0f);
                shape.SetAsEdge(new Vector2(-6.0f, 1.0f), new Vector2(-4.0f, 1.0f));
                ground.CreateFixture(shape, 0.0f);
                shape.SetAsEdge(new Vector2(-4.0f, 1.0f), new Vector2(-2.0f, 1.0f));
                ground.CreateFixture(shape, 0.0f);
            }

            // Square tiles
            {
                BodyDef bd     = new BodyDef();
                Body    ground = _world.CreateBody(bd);

                PolygonShape shape = new PolygonShape();
                shape.SetAsBox(1.0f, 1.0f, new Vector2(4.0f, 3.0f), 0.0f);
                ground.CreateFixture(shape, 0.0f);
                shape.SetAsBox(1.0f, 1.0f, new Vector2(6.0f, 3.0f), 0.0f);
                ground.CreateFixture(shape, 0.0f);
                shape.SetAsBox(1.0f, 1.0f, new Vector2(8.0f, 3.0f), 0.0f);
                ground.CreateFixture(shape, 0.0f);
            }

            // Square made from edges notice how the edges are shrunk to account
            // for the polygon radius. This makes it so the square character does
            // not get snagged. However, ray casts can now go through the cracks.
            for (int i = 0; i < 4; i++)
            {
                BodyDef bd     = new BodyDef();
                Body    ground = _world.CreateBody(bd);
                ground.SetTransform(new Vector2(-2f * i, 0), 0);

                Vector2[] vs = new Vector2[4];
                vs[0] = new Vector2(-1.0f, 3.0f);
                vs[1] = new Vector2(1.0f, 3.0f);
                vs[2] = new Vector2(1.0f, 5.0f);
                vs[3] = new Vector2(-1.0f, 5.0f);
                LoopShape shape = new LoopShape();
                shape._count    = 4;
                shape._vertices = vs;
                ground.CreateFixture(shape, 0.0f);

                //PolygonShape shape = new PolygonShape();
                //double d = 2.0f * Settings.b2_polygonRadius;
                //shape.SetAsEdge(new Vector2(-1.0f + d, 3.0f), new Vector2(1.0f - d, 3.0f));
                //ground.CreateFixture(shape, 0.0f);
                //shape.SetAsEdge(new Vector2(1.0f, 3.0f + d), new Vector2(1.0f, 5.0f - d));
                //ground.CreateFixture(shape, 0.0f);
                //shape.SetAsEdge(new Vector2(1.0f - d, 5.0f), new Vector2(-1.0f + d, 5.0f));
                //ground.CreateFixture(shape, 0.0f);
                //shape.SetAsEdge(new Vector2(-1.0f, 5.0f - d), new Vector2(-1.0f, 3.0f + d));
                //ground.CreateFixture(shape, 0.0f);
            }

            // Square character
            {
                BodyDef bd = new BodyDef();
                bd.position      = new Vector2(-3.0f, 5.0f);
                bd.type          = BodyType.Dynamic;
                bd.fixedRotation = true;
                bd.allowSleep    = false;

                Body body = _world.CreateBody(bd);

                PolygonShape shape = new PolygonShape();
                shape.SetAsBox(0.5, 0.5);

                FixtureDef fd = new FixtureDef();
                fd.shape   = shape;
                fd.density = 20.0;
                body.CreateFixture(fd);
            }

#if false
            // Hexagon character
            {
                BodyDef bd = new BodyDef();
                bd.position      = new Vector2(-5.0f, 5.0f);
                bd.type          = BodyType.Dynamic;
                bd.fixedRotation = true;
                bd.allowSleep    = false;

                Body body = _world.CreateBody(bd);

                double    angle    = 0.0f;
                double    delta    = (double)Math.PI / 3.0f;
                Vector2[] vertices = new Vector2[6];
                for (int i = 0; i < 6; ++i)
                {
                    vertices[i] = new Vector2(0.5f * (double)Math.Cos(angle), 0.5f * (double)Math.Sin(angle));
                    angle      += delta;
                }

                PolygonShape shape = new PolygonShape();
                shape.Set(vertices, 6);

                FixtureDef fd = new FixtureDef();
                fd.shape   = shape;
                fd.density = 20.0f;
                body.CreateFixture(fd);
            }

            // Circle character
            {
                BodyDef bd = new BodyDef();
                bd.position      = new Vector2(3.0f, 5.0f);
                bd.type          = BodyType.Dynamic;
                bd.fixedRotation = true;
                bd.allowSleep    = false;

                Body body = _world.CreateBody(bd);

                CircleShape shape = new CircleShape();
                shape._radius = 0.5f;

                FixtureDef fd = new FixtureDef();
                fd.shape   = shape;
                fd.density = 20.0f;
                body.CreateFixture(fd);
            }
#endif
        }
        private void ParseFixture(JObject jsonFixture, Body body)
        {
            Shape shape = null;

            var circles  = (JObject)jsonFixture["circle"];
            var polygons = (JObject)jsonFixture["polygon"];
            var chains   = (JObject)jsonFixture["chain"];

            if (circles != null)
            {
                var   center = Vector2.Zero;
                float radius = 0;
                foreach (JProperty circleProperty in circles.Children())
                {
                    switch (circleProperty.Name)
                    {
                    case "center":
                        center = ParseVector2(circleProperty);
                        break;

                    case "radius":
                        radius = HexToFloat(circleProperty.Value.ToString());
                        break;
                    }
                }
                shape = new CircleShape(radius, 1);
                var circleShape = (CircleShape)shape;
                circleShape.Position = center;
            }
            else if (polygons != null)
            {
                Vertices vertices = null;
                foreach (var polygonProperty in polygons.Children().Cast <JProperty>().Where(polygonProperty => polygonProperty.Name == "vertices"))
                {
                    vertices = new Vertices(ParseVector2Array(polygonProperty));
                }
                if (vertices != null)
                {
                    shape = new PolygonShape(vertices, 1);
                }
            }
            else if (chains != null)
            {
                //shape = new
                Vertices vertices    = null;
                bool     isLoopShape = false;
                bool     hasNextVertex;
                bool     hasPrevVertex;
                Vector2  nextVertex = Vector2.Zero;
                Vector2  prevVertex = Vector2.Zero;

                foreach (JProperty chainProperty in chains.Children())
                {
                    switch (chainProperty.Name)
                    {
                    case "vertices":
                        vertices = new Vertices(ParseVector2Array(chainProperty));
                        break;

                    case "hasNextVertex":
                        isLoopShape   = true;
                        hasNextVertex = (bool)chainProperty.Value;
                        break;

                    case "hasPrevVertex":
                        hasPrevVertex = (bool)chainProperty.Value;
                        break;

                    case "nextVertex":
                        nextVertex = ParseVector2(chainProperty);
                        break;

                    case "prevVertex":
                        prevVertex = ParseVector2(chainProperty);
                        break;

                    default:
                        System.Diagnostics.Debug.WriteLine(chainProperty.Name + " not supported!");
                        break;
                    }
                }

                if (isLoopShape)
                {
                    var lastvertexIndex = vertices.Count - 1;
                    if (vertices[0] == vertices[lastvertexIndex])
                    {
                        vertices.RemoveAt(lastvertexIndex);
                    }
                    shape = new LoopShape(vertices);
                    //var loopShape = (LoopShape) shape;
                }
                else
                {
                    throw new NotImplementedException();
                    //shape = new EdgeShape(prevVertex, nextVertex);
                    //var edgeShape = (EdgeShape) shape;
                }
            }

            var fixture = body.CreateFixture(shape);

            foreach (JProperty fixtureProperty in jsonFixture.Children())
            {
                //Fixture properties
                switch (fixtureProperty.Name)
                {
                case "name":
                    var value = fixtureProperty.Value.ToString();
                    _namedFixtures.Add(fixture, value);
                    break;

                case "density":
                    shape.Density = HexToFloat(fixtureProperty.Value.ToString());
                    break;

                case "friction":
                    fixture.Friction = HexToFloat(fixtureProperty.Value.ToString());
                    break;

                case "restitution":
                    fixture.Restitution = HexToFloat(fixtureProperty.Value.ToString());
                    break;

                case "sensor":
                    fixture.IsSensor = (bool)fixtureProperty.Value;
                    break;

                case "circle":
                case "polygon":
                case "chain":
                    //case "filter-categoryBits":
                    //case "filter-maskBits":
                    //case "filter-groupIndex":
                    break;     //ignore

                default:
                    System.Diagnostics.Debug.WriteLine(fixtureProperty.Name + " not supported!");
                    break;
                }
            }
        }