///<summary>
        /// Initializes the pair handler.
        ///</summary>
        ///<param name="entryA">First entry in the pair.</param>
        ///<param name="entryB">Second entry in the pair.</param>
        public override void Initialize(BroadPhaseEntry entryA, BroadPhaseEntry entryB)
        {

            terrain = entryA as Terrain;
            convex = entryB as ConvexCollidable;

            if (terrain == null || convex == null)
            {
                terrain = entryB as Terrain;
                convex = entryA as ConvexCollidable;

                if (terrain == null || convex == null)
                    throw new Exception("Inappropriate types used to initialize pair.");
            }

            //Contact normal goes from A to B.
            broadPhaseOverlap.entryA = convex;
            broadPhaseOverlap.entryB = terrain;

            UpdateMaterialProperties(convex.entity != null ? convex.entity.material : null, terrain.material);

            base.Initialize(entryA, entryB);




        }
Exemple #2
0
        public Map(Terrain terrain)
            : base(MobileFortressClient.Game)
        {
            Terrain = terrain;
            var map = Terrain.Shape.Heights;
            int width = map.GetLength(0);
            int x, y;

            vertexPNTs = new VertexMultitextured[width * width];

            ResetVertexBuffer();

            indices = new int[(width - 1) * (width - 1) * 6];
            int counter = 0;
            for (y = 0; y < width - 1; y++)
            {
                for (x = 0; x < width - 1; x++)
                {
                    int lowerLeft = x + y * width;
                    int lowerRight = (x + 1) + y * width;
                    int topLeft = x + (y + 1) * width;
                    int topRight = (x + 1) + (y + 1) * width;

                    indices[counter++] = topLeft;
                    indices[counter++] = lowerRight;
                    indices[counter++] = lowerLeft;

                    indices[counter++] = topLeft;
                    indices[counter++] = topRight;
                    indices[counter++] = lowerRight;
                }
            }
            MobileFortressClient.Game.Components.Add(this);
            CopyToBuffers();
        }
        ///<summary>
        /// Cleans up the pair handler.
        ///</summary>
        public override void CleanUp()
        {

            base.CleanUp();
            terrain = null;


        }
Exemple #4
0
        /// <summary>
        /// Constructs a new demo.
        /// </summary>
        /// <param name="game">Game owning this demo.</param>
        public TerrainDemo(DemosGame game)
            : base(game)
        {
            //x and y, in terms of heightmaps, refer to their local x and y coordinates.  In world space, they correspond to x and z.
            //Setup the heights of the terrain.
            //[The size here is limited by the Reach profile the demos use- the drawer draws the terrain as a big block and runs into primitive drawing limits.
            //The physics can support far larger terrains!]
            int xLength = 180;
            int zLength = 180;

            float xSpacing = 8f;
            float zSpacing = 8f;
            var heights = new float[xLength, zLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < zLength; j++)
                {
                    float x = i - xLength / 2;
                    float z = j - zLength / 2;
                    //heights[i,j] = (float)(x * y / 1000f);
                    heights[i, j] = (float)(10 * (Math.Sin(x / 8) + Math.Sin(z / 8)));
                    //heights[i,j] = 3 * (float)Math.Sin(x * y / 100f);
                    //heights[i,j] = (x * x * x * y - y * y * y * x) / 1000f;
                }
            }
            //Create the terrain.
            var terrain = new Terrain(heights, new AffineTransform(
                    new Vector3(xSpacing, 1, zSpacing),
                    Quaternion.Identity,
                    new Vector3(-xLength * xSpacing / 2, 0, -zLength * zSpacing / 2)));

            //terrain.Thickness = 5; //Uncomment this and shoot some things at the bottom of the terrain! They'll be sucked up through the ground.

            Space.Add(terrain);
            for (int i = 0; i < 3; i++)
            {
                for (int j = 0; j < 3; j++)
                {
                    for (int k = 0; k < 5; k++)
                    {
                        Space.Add(new Box(
                            new Vector3(0 + i * 4, 100 - j * 10, 0 + k * 4),
                            2 + i * j * k,
                            2 + i * j * k,
                            2 + i * j * k,
                            4 + 20 * i * j * k));
                    }
                }
            }

            game.ModelDrawer.Add(terrain);

            game.Camera.Position = new Vector3(0, 30, 20);
        }
        ///<summary>
        /// Initializes the pair handler.
        ///</summary>
        ///<param name="entryA">First entry in the pair.</param>
        ///<param name="entryB">Second entry in the pair.</param>
        public override void Initialize(BroadPhaseEntry entryA, BroadPhaseEntry entryB)
        {
            terrain = entryA as Terrain;
            if (terrain == null)
            {

                terrain = entryB as Terrain;
                if (terrain == null)
                {
                    throw new Exception("Inappropriate types used to initialize pair.");
                }
            }

            base.Initialize(entryA, entryB);
        }
        /// <summary>
        /// Constructs a new demo.
        /// </summary>
        /// <param name="game">Game owning this demo.</param>
        public AccumulationTestDemo(DemosGame game)
            : base(game)
        {
            //x and y, in terms of heightmaps, refer to their local x and y coordinates.  In world space, they correspond to x and z.
            //Setup the heights of the terrain.
            int xLength = 256;
            int zLength = 256;

            float xSpacing = .5f;
            float zSpacing = .5f;
            var heights = new float[xLength, zLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < zLength; j++)
                {
                    float x = i - xLength / 2;
                    float z = j - zLength / 2;
                    heights[i, j] = (float)(10 * (Math.Sin(x / 8) + Math.Sin(z / 8)));
                }
            }
            //Create the terrain.
            var terrain = new Terrain(heights, new AffineTransform(
                    new Vector3(xSpacing, 1, zSpacing),
                    Quaternion.Identity,
                    new Vector3(-xLength * xSpacing / 2, 0, -zLength * zSpacing / 2)));

            Space.Add(terrain);
            game.ModelDrawer.Add(terrain);

            eventHandler = (sender, other, pair) =>
            {

                var entityCollidable = other as EntityCollidable;
                if (entityCollidable == null || !entityCollidable.Entity.IsDynamic)
                {
                    sender.Events.RemoveAllEvents();
                    sender.Entity.LinearVelocity = new Vector3();
                    sender.Entity.AngularVelocity = new Vector3();
                    sender.Entity.BecomeKinematic();
                    sender.CollisionRules.Group = CollisionRules.DefaultDynamicCollisionGroup;
                }
            };

            game.Camera.Position = new Vector3(0, 30, 20);
        }
Exemple #7
0
        /// <summary>
        /// Constuct a TerrainPhysics entity.
        /// </summary>
        /// <param name="terrainName">The name of the terrain.</param>
        /// <param name="translation">The position of the terrain.</param>
        /// <param name="orientation">The orientation of the terrain.</param>
        /// <param name="scale">The amount to scale the terrain</param>
        public TerrainPhysics(String terrainName, Vector3 translation, Quaternion orientation, Vector3 scale)
        {
            float[,] heights = null;// AssetLibrary.LookupTerrainHeightMap(terrainName).GetHeights();
            StaticCollidable = new Terrain(
                heights,
                new AffineTransform(scale, orientation, translation - new Vector3(scale.X * .5f * heights.GetLength(0), 0f, scale.Z * .5f * heights.GetLength(1)))
            );

            StaticCollidable.CollisionRules.Group = TerrainPhysicsGroup;

            StaticCollidable.Tag = this;

            Position = translation;
            XNAOrientationMatrix = Matrix.CreateFromQuaternion(orientation);
            Scale = scale;

            mTerrainRenderable = new TerrainRenderable(terrainName);
        }
Exemple #8
0
        void CreateTerrain()
        {
            float peakValue = 0;

            for (int x = 0; x < map.GetLength(0); x++)
                for (int y = 0; y < map.GetLength(0); y++)
                    if (map[x, y] > peakValue) peakValue = map[x, y];

            float half = (map.GetLength(0) * lateralScale) / 2;

            AffineTransform transform = new AffineTransform(
                new Vector3(lateralScale, verticalScale, -lateralScale),
                Quaternion.Identity,
                new Vector3(-half, 0, half));

            Terrain = new Terrain(map, transform);
            Sector.Redria.Space.Add(Terrain);
        }
Exemple #9
0
        private void CreateStaticCollidable()
        {
            float[,] heights = AssetLibrary.LookupHeightMap(mName).Mesh.Heights;
            Vector3 collidableScale = new Vector3(Scale.X / (float)(heights.GetLength(0) - 1), Scale.Y, Scale.Z / (float)(heights.GetLength(1) - 1));

            StaticCollidable = new Terrain(heights, new BEPUphysics.MathExtensions.AffineTransform(collidableScale, OrientationQuaternion, Position));
            StaticCollidable.CollisionRules.Group = HeightMapPhysicsGroup;
            StaticCollidable.Tag = this;
        }
        ///<summary>
        /// Cleans up the pair handler.
        ///</summary>
        public override void CleanUp()
        {

            base.CleanUp();
            mesh = null;


        }
Exemple #11
0
        /// <summary>
        /// Constructs a new demo.
        /// </summary>
        /// <param name="game">Game owning this demo.</param>
        public TornadoDemo(DemosGame game)
            : base(game)
        {
            shape = new BoundingBoxForceFieldShape(new BoundingBox(new Vector3(-100, -20, -40), new Vector3(-20, 120, 40)));
            tornado = new Tornado(shape, (shape.BoundingBox.Min + shape.BoundingBox.Max) / 2, new Vector3(0, 1, 0),
                                  150, false, 50, 10, 200, 200, 80, 2000, 40, 10);
            tornado.ForceWakeUp = true; //The tornado will be moving, so it should wake up things that it comes into contact with.
            Space.Add(tornado);

            //Create the unfortunate box-like citizens about to be hit by the tornado.
            int numColumns = 10;
            int numRows = 10;
            int numHigh = 1;
            float separation = 1.5f;
            Entity toAdd;
            for (int i = 0; i < numRows; i++)
                for (int j = 0; j < numColumns; j++)
                    for (int k = 0; k < numHigh; k++)
                    {
                        toAdd = new Box(new Vector3(
                                            separation * i - numRows * separation / 2,
                                            5 + k * separation,
                                            separation * j - numColumns * separation / 2),
                                        1, 1, 1, 10);
                        Space.Add(toAdd);
                    }

            //x and y, in terms of heightmaps, refer to their local x and y coordinates.  In world space, they correspond to x and z.
            //Setup the heights of the terrain.
            //[The size here is limited by the Reach profile the demos use- the drawer draws the terrain as a big block and runs into primitive drawing limits.
            //The physics can support far larger terrains!]
            int xLength = 180;
            int zLength = 180;

            float xSpacing = 8f;
            float zSpacing = 8f;
            var heights = new float[xLength,zLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < zLength; j++)
                {
                    float x = i - xLength / 2;
                    float z = j - zLength / 2;
                    //heights[i,j] = (float)Math.Pow(1.2 * Math.Sqrt(x * x + y * y), 2);
                    //heights[i,j] = -1f / (x * x + y * y);
                    //heights[i,j] = (float)(x * y / 100f);
                    heights[i,j] = (float)(5 * (Math.Sin(x / 8f) + Math.Sin(z / 8f)));
                    //heights[i,j] = 3 * (float)Math.Sin(x * y / 100f);
                    //heights[i,j] = (x * x * x * y - y * y * y * x) / 1000f;
                }
            }

            //Create the terrain.
            var terrain = new Terrain(heights, new AffineTransform(
                new Vector3(xSpacing, 1, zSpacing),
                Quaternion.Identity,
                new Vector3(-xLength * xSpacing / 2, 0, -zLength * zSpacing / 2)));
            Space.Add(terrain);
            game.ModelDrawer.Add(terrain);
            game.Camera.Position = new Vector3(0, 5, 60);
        }
Exemple #12
0
        /// <summary>
        /// Constructs a new demo.
        /// </summary>
        /// <param name="game">Game owning this demo.</param>
        public ReverseTrikeDemo(DemosGame game)
            : base(game)
        {
            game.Camera.Position = new Vector3(0, 2, 15);
            game.Camera.Yaw = 0;
            game.Camera.Pitch = 0;

            Space.Add(new Box(new Vector3(0, -5, 0), 20, 1, 20));

            var body = new Box(new Vector3(0, 0, 0), 2, 1, 3, 10);
            body.CollisionInformation.LocalPosition = new Vector3(0, .8f, 0);
            Space.Add(body);

            #region First Wheel

            var wheel = new Cylinder(body.Position + new Vector3(-1.3f, 0, -1.5f), .2f, .5f, 4);
            wheel.Material = new Material(1.5f, 1.5f, 0);
            wheel.Orientation = Quaternion.CreateFromAxisAngle(Vector3.Forward, MathHelper.PiOver2);

            //Preventing the occasional pointless collision pair can speed things up.
            CollisionRules.AddRule(body, wheel, CollisionRule.NoBroadPhase);

            //Connect the wheel to the body.
            var ballSocketJoint = new BallSocketJoint(body, wheel, wheel.Position);
            var swivelHingeAngularJoint = new SwivelHingeAngularJoint(body, wheel, Vector3.Up, Vector3.Right);
            //Motorize the wheel.
            drivingMotor1 = new RevoluteMotor(body, wheel, Vector3.Left);
            drivingMotor1.Settings.VelocityMotor.Softness = .2f;
            //Let it roll when the user isn't giving specific commands.
            drivingMotor1.IsActive = false;
            steeringMotor1 = new RevoluteMotor(body, wheel, Vector3.Up);
            steeringMotor1.Settings.Mode = MotorMode.Servomechanism;
            //The constructor makes a guess about how to set up the constraint.
            //It can't always be right since it doesn't have all the information;
            //in this case, it chooses the basis and test axis incorrectly.
            //This leads to a 'flipping' behavior when the wheel is rolling
            //(the test axis is 'rolling' with the wheel, and passes over
            //a singularity which causes a flip).

            //To fix this, we configure the constraint directly.
            //The basis is aligned with how the wheel is set up; we choose 'up' as
            //the motorized axis, and right/forward to define the angle measurement plane.
            //The test axis is set to be perpendicular to the wheel's rotation so that
            //it only measures the steering angle.

            //If you're curious, the angle measurement is just a Math.Atan2.
            //The current world test axis is dotted against the two plane axes (Right and Forward here).
            //This gives an x and y value.  These can be plugged into Atan2 just like when
            //you compute an angle on a normal 2d graph.
            steeringMotor1.Basis.SetWorldAxes(Vector3.Up, Vector3.Right);
            steeringMotor1.TestAxis = Vector3.Right;

            //Add the wheel and connection to the space.
            Space.Add(wheel);
            Space.Add(ballSocketJoint);
            Space.Add(swivelHingeAngularJoint);
            Space.Add(drivingMotor1);
            Space.Add(steeringMotor1);

            #endregion

            #region Second Wheel

            wheel = new Cylinder(body.Position + new Vector3(1.3f, 0, -1.5f), .2f, .5f, 4);
            wheel.Material = new Material(1.5f, 1.5f, 0);
            wheel.Orientation = Quaternion.CreateFromAxisAngle(Vector3.Forward, MathHelper.PiOver2);

            //Preventing the occasional pointless collision pair can speed things up.
            CollisionRules.AddRule(body, wheel, CollisionRule.NoBroadPhase);

            //Connect the wheel to the body.
            ballSocketJoint = new BallSocketJoint(body, wheel, wheel.Position);
            swivelHingeAngularJoint = new SwivelHingeAngularJoint(body, wheel, Vector3.Up, Vector3.Right);
            //Motorize the wheel.
            drivingMotor2 = new RevoluteMotor(body, wheel, Vector3.Left);
            drivingMotor2.Settings.VelocityMotor.Softness = .2f;
            //Let it roll when the user isn't giving specific commands.
            drivingMotor2.IsActive = false;
            steeringMotor2 = new RevoluteMotor(body, wheel, Vector3.Up);
            steeringMotor2.Settings.Mode = MotorMode.Servomechanism;
            //Configure the motor.  See wheel 1 for more description.
            steeringMotor2.Basis.SetWorldAxes(Vector3.Up, Vector3.Right);
            steeringMotor2.TestAxis = Vector3.Right;

            //Add the wheel and connection to the space.
            Space.Add(wheel);
            Space.Add(ballSocketJoint);
            Space.Add(swivelHingeAngularJoint);
            Space.Add(drivingMotor2);
            Space.Add(steeringMotor2);

            #endregion

            #region Third Wheel

            wheel = new Cylinder(body.Position + new Vector3(0, -.3f, 1.5f), .2f, .5f, 4);
            wheel.Material = new Material(1.5f, 1.5f, 0);
            wheel.Orientation = Quaternion.CreateFromAxisAngle(Vector3.Forward, MathHelper.PiOver2);

            //Preventing the occasional pointless collision pair can speed things up.
            CollisionRules.AddRule(body, wheel, CollisionRule.NoBroadPhase);

            //Connect the wheel to the body.
            ballSocketJoint = new BallSocketJoint(body, wheel, wheel.Position);
            //Notice that the third wheel isn't a swivel hinge, it's just a revolute axis.
            //This lets it roll, but prevents flopping around like the wheels of a grocery cart.
            //Could have used a RevoluteJoint solver group here, but this shows it's possible to do
            //the same things without using the combo-constraints.
            var revoluteAngularJoint = new RevoluteAngularJoint(body, wheel, Vector3.Right);

            //Add the wheel and connection to the space.
            Space.Add(wheel);
            Space.Add(ballSocketJoint);
            Space.Add(revoluteAngularJoint);

            #endregion

            int xLength = 256;
            int zLength = 256;

            float xSpacing = 8f;
            float zSpacing = 8f;
            var heights = new float[xLength, zLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < zLength; j++)
                {
                    float x = i - xLength / 2;
                    float z = j - zLength / 2;
                    //heights[i,j] = (float)(x * y / 1000f);
                    heights[i, j] = (float)(10 * (Math.Sin(x / 8) + Math.Sin(z / 8)));
                    //heights[i,j] = 3 * (float)Math.Sin(x * y / 100f);
                    //heights[i,j] = (x * x * x * y - y * y * y * x) / 1000f;
                }
            }
            //Create the terrain.
            var terrain = new Terrain(heights, new AffineTransform(
                new Vector3(xSpacing, 1, zSpacing),
                Quaternion.Identity,
                new Vector3(-xLength * xSpacing / 2, -10, -zLength * zSpacing / 2)));
            Space.Add(terrain);

            game.ModelDrawer.Add(terrain);
        }
Exemple #13
0
        ///<summary>
        /// Initializes the manifold.
        ///</summary>
        ///<param name="newCollidableA">First collidable.</param>
        ///<param name="newCollidableB">Second collidable.</param>
        public override void Initialize(Collidable newCollidableA, Collidable newCollidableB)
        {
            convex = newCollidableA as ConvexCollidable;
            terrain = newCollidableB as Terrain;


            if (convex == null || terrain == null)
            {
                convex = newCollidableB as ConvexCollidable;
                terrain = newCollidableA as Terrain;
                if (convex == null || terrain == null)
                    throw new Exception("Inappropriate types used to initialize contact manifold.");
            }

        }
Exemple #14
0
 ///<summary>
 /// Cleans up the manifold.
 ///</summary>
 public override void CleanUp()
 {
     terrain = null;
     convex = null;
     base.CleanUp();
 }
        private void LoadHeightData(Texture2D heightMap)
        {
            terrainWidth = heightMap.Width;
            terrainHeight = heightMap.Height;

            Color[] heightMapColors = new Color[terrainWidth * terrainHeight];
            heightMap.GetData(heightMapColors);

            heightData = new float[terrainWidth, terrainHeight];
            var bepuHehighData = new float[terrainWidth, terrainHeight];
            for (int x = 0; x < terrainWidth; x++)
            {
                for (int y = 0; y < terrainHeight; y++)
                {
                    heightData[x, y] = heightMapColors[x + y * terrainWidth].R / 5.0f;
                }
            }

            int yy = 0;
            for (int x = 0; x < terrainWidth; x++)
            {
                for (int y = terrainHeight - 1; y >= 0 ; y--)
                {
                    bepuHehighData[x, y] = heightMapColors[x + yy * terrainWidth].R / 5.0f;
                    yy++;
                }
                yy = 0;
            }
            bepuTerrain = new BEPUphysics.Collidables.Terrain(bepuHehighData, new AffineTransform(
                    new Vector3(1, 1, 1)
                    , Quaternion.Identity
                    ,new Vector3(0, 0, -terrainHeight)
                    ));

             XNAGame.Instance.Space.Add(bepuTerrain);
             //XNAGame.Instance.ModelDrawer.Add(bepuTerrain);
        }
        /// <summary>
        /// Create a Terrain Physic Object
        /// </summary>
        /// <param name="gfactory">The gfactory.</param>
        /// <param name="heighmapName">Name of the heighmap texture</param>
        /// <param name="translation">The translation.</param>
        /// <param name="rotation">The rotation.</param>
        /// <param name="materialDesc">The material desc.</param>
        /// <param name="XSpacing">The X spacing.</param>
        /// <param name="ZSpacing">The Z spacing.</param>
        /// <param name="heightMultipler">Default 10 - controla a altura, menor mais alto</param>
        public TerrainObject(GraphicFactory gfactory, String heighmapName, Vector3 translation, Matrix? rotation = null, MaterialDescription materialDesc = null, float XSpacing = 1, float ZSpacing = 1, float heightMultipler = 10)
        {
            if (!rotation.HasValue)
                rotation = Matrix.Identity;

            if (materialDecription == null)
                materialDecription = MaterialDescription.DefaultBepuMaterial();


            //Used to calculate ther proportion of the xNormalized in the getHeightFast method
            xScale = XSpacing;
            zScale = ZSpacing;


            this.heightMultipler = heightMultipler;
            this.image = heighmapName;

            sourceImage = gfactory.GetTexture2D(image);
            int xLength = sourceImage.Width;
            int yLength = sourceImage.Height;

            terrainWidth = xLength;
            terrainHeight = yLength;


            this.rotation = rotation.Value;
            //this.scale = scale;

            Color[] colorData = new Color[xLength * yLength];
            sourceImage.GetData<Color>(colorData);

            var heightStore = new float[xLength, yLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < yLength; j++)
                {
                    Color color = colorData[j * xLength + i];
                    heightStore[i, j] = (color.R) / heightMultipler;

                    if (heightStore[i, j] > maxHeight)
                    {
                        maxHeight = heightStore[i, j];
                    }
                    if (heightStore[i, j] < minHeight)
                    {
                        minHeight = heightStore[i, j];
                    }

                }
            }
            //Create the terrain.
            BEPUphysics.CollisionShapes.TerrainShape shape = new BEPUphysics.CollisionShapes.TerrainShape(heightStore, BEPUphysics.CollisionShapes.QuadTriangleOrganization.BottomLeftUpperRight);

            terrain = new Terrain(shape, new BEPUphysics.MathExtensions.AffineTransform(new Vector3(XSpacing, 1, ZSpacing), Quaternion.CreateFromRotationMatrix(rotation.Value), new Vector3(-xLength * XSpacing / 2, 0, -yLength * ZSpacing / 2) + translation));
            terrain.ImproveBoundaryBehavior = true;

            SetMaterialDescription(materialDesc);

        }
Exemple #17
0
        /// <summary>
        /// Constructs a new demo.
        /// </summary>
        /// <param name="game">Game owning this demo.</param>
        public SuspensionCarDemo(DemosGame game)
            : base(game)
        {
            game.Camera.Position = new Vector3(0, 2, 15);
            game.Camera.Yaw = 0;
            game.Camera.Pitch = 0;

            Space.Add(new Box(new Vector3(0, -5, 0), 20, 1, 20));

            var body = new Box(new Vector3(0, 0, 0), 4, .5f, 5, 20);
            body.CollisionInformation.LocalPosition = new Vector3(0, .8f, 0);
            Space.Add(body);

            AddBackWheel(new Vector3(-1.8f, -.2f, 2.1f), body);
            AddBackWheel(new Vector3(1.8f, -.2f, 2.1f), body);
            var wheel1 = AddDriveWheel(new Vector3(-1.8f, -.2f, -2.1f), body, out drivingMotor1, out steeringMotor1);
            var wheel2 = AddDriveWheel(new Vector3(1.8f, -.2f, -2.1f), body, out drivingMotor2, out steeringMotor2);

            //Add a stabilizer so that the wheels can't point different directions.
            var steeringStabilizer = new RevoluteAngularJoint(wheel1, wheel2, Vector3.Right);
            Space.Add(steeringStabilizer);

            //x and y, in terms of heightmaps, refer to their local x and y coordinates.  In world space, they correspond to x and z.
            //Setup the heights of the terrain.
            int xLength = 256;
            int zLength = 256;

            float xSpacing = 8f;
            float zSpacing = 8f;
            var heights = new float[xLength, zLength];
            for (int i = 0; i < xLength; i++)
            {
                for (int j = 0; j < zLength; j++)
                {
                    float x = i - xLength / 2;
                    float z = j - zLength / 2;
                    //heights[i,j] = (float)(x * y / 1000f);
                    heights[i, j] = (float)(10 * (Math.Sin(x / 8) + Math.Sin(z / 8)));
                    //heights[i,j] = 3 * (float)Math.Sin(x * y / 100f);
                    //heights[i,j] = (x * x * x * y - y * y * y * x) / 1000f;
                }
            }
            //Create the terrain.
            var terrain = new Terrain(heights, new AffineTransform(
                    new Vector3(xSpacing, 1, zSpacing),
                    Quaternion.Identity,
                    new Vector3(-xLength * xSpacing / 2, -10, -zLength * zSpacing / 2)));

            //terrain.Thickness = 5; //Uncomment this and shoot some things at the bottom of the terrain! They'll be sucked up through the ground.

            Space.Add(terrain);

            game.ModelDrawer.Add(terrain);
        }
        public TerrainObject(GraphicFactory gfactory, Vector3 translation, Matrix rotation, float[,] heights, MaterialDescription materialDesc,BEPUphysics.CollisionShapes.QuadTriangleOrganization triangleorientation = BEPUphysics.CollisionShapes.QuadTriangleOrganization.BottomLeftUpperRight )
        {
            terrainWidth = heights.GetLength(0);
            terrainHeight = heights.GetLength(1);

            //Create the terrain.
            BEPUphysics.CollisionShapes.TerrainShape shape = new BEPUphysics.CollisionShapes.TerrainShape(heights, triangleorientation);

            terrain = new Terrain(shape, new BEPUphysics.MathExtensions.AffineTransform(Vector3.One, Quaternion.CreateFromRotationMatrix(rotation), translation));
            terrain.ImproveBoundaryBehavior = true;

            SetMaterialDescription(materialDesc);
        }