Пример #1
0
    public BoxStackSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // ----- Add a stack of boxes.
      const int numberOfBoxes = 5;
      const float boxSize = 0.8f;
      BoxShape boxShape = new BoxShape(boxSize, boxSize, boxSize);

      // Optional: Use a small overlap between boxes to improve the stability.
      float overlap = Simulation.Settings.Constraints.AllowedPenetration * 0.5f;
      Vector3F position = new Vector3F(0, boxSize / 2 - overlap, 0);
      for (int i = 0; i < numberOfBoxes; i++)
      {
        RigidBody box = new RigidBody(boxShape)
        {
          Name = "Box" + i,
          Pose = new Pose(position),
        };
        Simulation.RigidBodies.Add(box);
        position.Y += boxSize - overlap;
      }
    }
Пример #2
0
        protected virtual void CloneCore(RigidBody source)
        {
            // Material and mass properties
              Material = source.Material;
              MassFrame = source.MassFrame.Clone();
              AutoUpdateMass = source.AutoUpdateMass;
              LockRotationX = source.LockRotationX;
              LockRotationY = source.LockRotationY;
              LockRotationZ = source.LockRotationZ;

              // Geometric object properties
              Pose = source.Pose;
              Shape = source.Shape.Clone();
              Scale = source.Scale;

              // Other properties
              CollisionObject.CollisionGroup = source.CollisionObject.CollisionGroup;
              CollisionObject.Type = source.CollisionObject.Type;
              CollisionObject.Enabled = source.CollisionObject.Enabled;
              CollisionResponseEnabled = source.CollisionResponseEnabled;
              MotionType = source.MotionType;
              Name = source.Name;
              UserData = source.UserData;
              BuoyancyData = source.BuoyancyData;
              CcdEnabled = source.CcdEnabled;
              LinearVelocity = source.LinearVelocity;
              AngularVelocity = source.AngularVelocity;
              CanSleep = source.CanSleep;
        }
Пример #3
0
    public RibbonSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      GraphicsScreen.DrawReticle = true;

      GameObjectService.Objects.Add(new GrabObject(Services));

      // Load a sphere model.
      _modelNode = ContentManager.Load<ModelNode>("Particles/Sphere").Clone();
      GraphicsScreen.Scene.Children.Add(_modelNode);

      // Add gravity and damping to the physics simulation.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Create a rigid body for the sphere.
      _rigidBody = new RigidBody(new SphereShape(0.5f))
      {
        Pose = new Pose(new Vector3F(-3, 0, 0)),
        LinearVelocity = new Vector3F(10, 10, -3f),
      };
      Simulation.RigidBodies.Add(_rigidBody);

      _particleSystem = RibbonEffect.Create(ContentManager);
      ParticleSystemService.ParticleSystems.Add(_particleSystem);
      _particleSystemNode = new ParticleSystemNode(_particleSystem);
      GraphicsScreen.Scene.Children.Add(_particleSystemNode);
    }
Пример #4
0
    public SphereStackSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // ----- Add a stack of spheres.
      const int numberOfSpheres = 10;
      const float sphereRadius = 0.4f;
      Shape sphereShape = new SphereShape(sphereRadius);

      // Optional: Use a small overlap between spheres to improve the stability.
      float overlap = Simulation.Settings.Constraints.AllowedPenetration * 0.5f;
      Vector3F position = new Vector3F(0, sphereRadius - overlap, 0);
      for (int i = 0; i < numberOfSpheres; i++)
      {
        RigidBody sphere = new RigidBody(sphereShape)
        {
          Name = "Sphere" + i,
          Pose = new Pose(position),
        };
        Simulation.RigidBodies.Add(sphere);
        position.Y += 2 * sphereRadius - overlap;
      }
    }
Пример #5
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      // Load model.
      var contentManager = _services.GetInstance<ContentManager>();
      _modelNode = contentManager.Load<ModelNode>("Ground/Ground").Clone();
      _modelNode.ScaleLocal = new Vector3F(0.5f);

      foreach (var node in _modelNode.GetSubtree())
      {
        // Disable the CastsShadows flag for ground meshes. No need to render
        // this model into the shadow map. (This also avoids any shadow acne on 
        // the ground model.)
        node.CastsShadows = false;

        // If models will never move, set the IsStatic flag. This gives the engine 
        // more room for optimizations. Additionally, some effects, like certain 
        // decals, may only affect static geometry.
        node.IsStatic = true;
      }

      // Add model node to scene graph.
      var scene = _services.GetInstance<IScene>();
      scene.Children.Add(_modelNode);

      // Create rigid body.
      _rigidBody = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        MotionType = MotionType.Static,
      };

      // Add rigid body to the physics simulation.
      var simulation = _services.GetInstance<Simulation>();
      simulation.RigidBodies.Add(_rigidBody);
    }
Пример #6
0
    private void InitializeSimulation(Simulation simulation, Vector3F offset)
    {
      // Add default force effects.
      simulation.ForceEffects.Add(new Gravity());
      simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",
        MotionType = MotionType.Static,
      };
      simulation.RigidBodies.Add(groundPlane);

      // Add a stack of boxes.
      const float boxSize = 0.8f;
      float overlap = simulation.Settings.Constraints.AllowedPenetration * 0.5f;
      float yPosition = boxSize / 2 - overlap;
      BoxShape boxShape = new BoxShape(boxSize, boxSize, boxSize);
      for (int i = 0; i < 15; i++)
      {
        RigidBody stackBox = new RigidBody(boxShape)
        {
          Name = "StackBox" + i,
          Pose = new Pose(new Vector3F(0, yPosition, 0) + offset),
        };
        simulation.RigidBodies.Add(stackBox);
        yPosition += boxSize - overlap;
      }
    }
Пример #7
0
    public ConvexHullSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",            // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Load model and add it to the graphics scene.
      _saucerModelNode = ContentManager.Load<ModelNode>("Saucer2/saucer").Clone();
      GraphicsScreen.Scene.Children.Add(_saucerModelNode);

      // Create rigid body for this model.
      // The tag contains the collision shape (created in the content processor).
      Shape saucerShape = (Shape)_saucerModelNode.UserData;
      _saucerBody = new RigidBody(saucerShape)
      {
        Pose = new Pose(new Vector3F(0, 2, 0), RandomHelper.Random.NextQuaternionF())
      };
      Simulation.RigidBodies.Add(_saucerBody);
    }
Пример #8
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      // ----- Create prototype of a lava ball:

      // Use a sphere for physics simulation.
      _bodyPrototype = new RigidBody(new SphereShape(0.5f));

      // Load the graphics model.
      var content = _services.GetInstance<ContentManager>();
      _modelPrototype = content.Load<ModelNode>("LavaBall/LavaBall").Clone();

      // Attach a point light to the model. The light projects the glowing lava 
      // veins (cube map texture) onto the environment.
      _pointLight = new PointLight
      {
        Color = new Vector3F(1, 1, 1),
        DiffuseIntensity = 2,
        SpecularIntensity = 2,
        Range = 1.5f,
        Attenuation = 0.5f,
        Texture = content.Load<TextureCube>("LavaBall/LavaCubeMap"),
      };
      var pointLightNode = new LightNode(_pointLight);
      _modelPrototype.Children.Add(pointLightNode);

      // Get the emissive color binding of the material because the emissive color
      // will be animated.
      // The model contains one mesh node with a single material.
      var meshNode = (MeshNode)_modelPrototype.Children[0];
      var mesh = meshNode.Mesh;
      var material = mesh.Materials[0];

      // The material contains several effect bindings. The "EmissiveColor" is applied
      // in the "Material" pass. 
      // (For reference see material definition file: Samples\Media\LavaBall\Lava.drmat)
      _emissiveColorBinding = (ConstParameterBinding<Vector3>)material["Material"].ParameterBindings["EmissiveColor"];

      // Use the animation service to animate glow intensity of the lava.
      var animationService = _services.GetInstance<IAnimationService>();

      // Create an AnimatableProperty<float>, which stores the animation value.
      _glowIntensity = new AnimatableProperty<float>();

      // Create sine animation and play the animation back-and-forth.
      var animation = new SingleFromToByAnimation
      {
        From = 0.3f,
        To = 3.0f,
        Duration = TimeSpan.FromSeconds(1),
        EasingFunction = new SineEase { Mode = EasingMode.EaseInOut },
      };
      var clip = new AnimationClip<float>
      {
        Animation = animation,
        Duration = TimeSpan.MaxValue,
        LoopBehavior = LoopBehavior.Oscillate
      };
      animationService.StartAnimation(clip, _glowIntensity).AutoRecycle();
    }
Пример #9
0
    // OnUnload() is called when the GameObject is removed from the IGameObjectService.
    protected override void OnUnload()
    {
      // Remove model and rigid body.
      _modelNode.Parent.Children.Remove(_modelNode);
      _modelNode.Dispose(false);
      _modelNode = null;

      _rigidBody.Simulation.RigidBodies.Remove(_rigidBody);
      _rigidBody = null;
    }
Пример #10
0
    private void CreateParticleSystem()
    {
      // Load a sphere model.
      var modelNode = ContentManager.Load<ModelNode>("Particles/Sphere");
      var meshNode = (MeshNode)modelNode.Children[0];

      // Add gravity and damping to the physics simulation.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Create two instances of the sphere model.
      _meshNode0 = meshNode.Clone();
      GraphicsScreen.Scene.Children.Add(_meshNode0);
      _meshNode1 = meshNode.Clone();
      GraphicsScreen.Scene.Children.Add(_meshNode1);

      // Create a rigid body for the left sphere.
      _rigidBody0 = new RigidBody(new SphereShape(0.5f))
      {
        Pose = new Pose(new Vector3F(-3, 4, 0)),
      };
      Simulation.RigidBodies.Add(_rigidBody0);

      // Create a rigid body for the right sphere. (Sharing the same shape, mass and material.)
      _rigidBody1 = new RigidBody(_rigidBody0.Shape, _rigidBody0.MassFrame, _rigidBody0.Material)
      {
        Pose = new Pose(new Vector3F(3, 4, 0)),
      };
      Simulation.RigidBodies.Add(_rigidBody1);

      // Extract basic triangle mesh from the sphere model.
      var triangleMesh = meshNode.Mesh.Submeshes[0].ToTriangleMesh();

      // Create a particle system for the left ball. This particle system uses
      // ReferenceFrame == ParticleReferenceFrame.World - which is the default for all 
      // particle systems. Particles are all relative to world space. The particle system pose 
      // determines the start positions and direction (when the StartPositionEffector and 
      // StartDirectionEffector are in use). Particles do not move with the particle system.
      _particleSystem0 = GlowingMeshEffect.Create(triangleMesh, ContentManager);
      _particleSystem0.ReferenceFrame = ParticleReferenceFrame.World;
      ParticleSystemService.ParticleSystems.Add(_particleSystem0);

      _particleSystemNode0 = new ParticleSystemNode(_particleSystem0);
      _meshNode0.Children = new SceneNodeCollection { _particleSystemNode0 };

      // Create a particle system for the right ball. This particle system uses
      // ReferenceFrame == ParticleReferenceFrame.Local. Particles are all relative to the 
      // particle system pose. Particles move with the particle system.
      _particleSystem1 = GlowingMeshEffect.Create(triangleMesh, ContentManager);
      _particleSystem1.ReferenceFrame = ParticleReferenceFrame.Local;
      ParticleSystemService.ParticleSystems.Add(_particleSystem1);

      _particleSystemNode1 = new ParticleSystemNode(_particleSystem1);
      _meshNode1.Children = new SceneNodeCollection { _particleSystemNode1 };
    }
Пример #11
0
        internal RigidBody(RigidBodyDescriptor descriptor)
        {
            WrappedRigidBody = new DR.RigidBody {AutoUpdateMass = true, MotionType = descriptor.MotionType.ToDigitalRune()};

            Configurator = new RigidBodyConfigurator(this);
            FixtureFactory = new RigidBodyFixtureFactory(this);
            Forces = new RigidBodyForces(this);
            Velocity = new RigidBodyVelocity(this);
            MassFrame = new RigidBodyMassFrame(this);
            Descriptor = descriptor;
        }
Пример #12
0
    public LockRotationSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Next, we add boxes and capsules in random positions and orientations.
      // For all bodies the flags LockRotationX/Y/Z are set. This will prevent all
      // rotation that would be caused by forces. (It is still allowed to manually 
      // change the rotation or to set an angular velocity.)

      BoxShape boxShape = new BoxShape(0.5f, 0.8f, 1.2f);
      for (int i = 0; i < 10; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-10, 10);
        position.Y = 5;
        QuaternionF orientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(boxShape)
        {
          Pose = new Pose(position, orientation),
          LockRotationX = true,
          LockRotationY = true,
          LockRotationZ = true,
        };
        Simulation.RigidBodies.Add(body);
      }

      CapsuleShape capsuleShape = new CapsuleShape(0.3f, 1.2f);
      for (int i = 0; i < 10; i++)
      {
        Vector3F randomPosition = RandomHelper.Random.NextVector3F(-10, 10);
        randomPosition.Y = 5;
        QuaternionF randomOrientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(capsuleShape)
        {
          Pose = new Pose(randomPosition, randomOrientation),
          LockRotationX = true,
          LockRotationY = true,
          LockRotationZ = true,
        };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #13
0
        // Creates a new rigid body and adds it to the simulation.
        private void AddBody(string name, Pose pose, Shape shape, MotionType motionType)
        {
            var rigidBody = new RigidBody(shape)
            {
                Name = name,
                Pose = pose,
                MotionType = motionType,
            };

            simulation.RigidBodies.Add(rigidBody);
        }
Пример #14
0
 public CompositeFixture(DR.RigidBody wrappedRigidBody, FixtureDescriptor descriptor)
 {
     _root     = true;
     _pose     = descriptor.Pose;
     _realPose = _pose;
     _wrappedCompositeMaterial = new CompositeMaterial();
     wrappedRigidBody.Material = _wrappedCompositeMaterial;
     _wrappedCompositeShape    = new CompositeShape();
     wrappedRigidBody.Shape    = _wrappedCompositeShape;
     UserData       = descriptor.UserData;
     FixtureFactory = new CompositeFixtureFixtureFactory(this);
 }
Пример #15
0
     SimpleFixture(DR.RigidBody wrappedRigidBody, FixtureDescriptor descriptor)
 {
     _wrappedRigidBody = wrappedRigidBody;
     _wrappedGeometricObject = new GeometricObject(new EmptyShape(), descriptor.Pose.ToDigitalRune());
     _wrappedRigidBody.Shape = new TransformedShape(_wrappedGeometricObject);
     _wrappedRigidBody.Material = new UniformMaterial();
     UserData = descriptor.UserData;
     _pose = descriptor.Pose;
     ShapeFactory = new SimpleFixtureShapeFactory(this);
     _root = true;
     MaterialFactory = new SimpleFixtureMaterialFactory(this);
 }
Пример #16
0
 SimpleFixture(DR.RigidBody wrappedRigidBody, FixtureDescriptor descriptor)
 {
     _wrappedRigidBody          = wrappedRigidBody;
     _wrappedGeometricObject    = new GeometricObject(new EmptyShape(), descriptor.Pose.ToDigitalRune());
     _wrappedRigidBody.Shape    = new TransformedShape(_wrappedGeometricObject);
     _wrappedRigidBody.Material = new UniformMaterial();
     UserData        = descriptor.UserData;
     _pose           = descriptor.Pose;
     ShapeFactory    = new SimpleFixtureShapeFactory(this);
     _root           = true;
     MaterialFactory = new SimpleFixtureMaterialFactory(this);
 }
Пример #17
0
    public ResponseFilterSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Only disable collision response if you need collision detection info but no collision
      // response. If you can disable collision detection too, use 
      //   Simulation.CollisionDomain.CollisionDetection.CollisionFilter 
      // instead - this is more efficient!
      // (In this sample, a custom filter implementation is used. DigitalRune.Physics provides
      // a standard filter implementation: DigitalRune.Physics.CollisionResponseFilter.)
      Simulation.ResponseFilter = new MyCollisionResponseFilter();

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // ----- Add boxes at random poses.
      BoxShape boxShape = new BoxShape(0.5f, 0.8f, 1.2f);
      for (int i = 0; i < 20; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-3, 3);
        position.Y = 5;
        QuaternionF orientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(boxShape)
        {
          Pose = new Pose(position, orientation),
        };
        Simulation.RigidBodies.Add(body);
      }

      // ----- Add capsules at random poses.
      CapsuleShape capsuleShape = new CapsuleShape(0.3f, 1.2f);
      for (int i = 0; i < 20; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-3, 3);
        position.Y = 5;
        QuaternionF orientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(capsuleShape)
        {
          Pose = new Pose(position, orientation),
        };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #18
0
        internal RigidBody(RigidBodyDescriptor descriptor)
        {
            WrappedRigidBody = new DR.RigidBody {
                AutoUpdateMass = true, MotionType = descriptor.MotionType.ToDigitalRune()
            };

            Configurator   = new RigidBodyConfigurator(this);
            FixtureFactory = new RigidBodyFixtureFactory(this);
            Forces         = new RigidBodyForces(this);
            Velocity       = new RigidBodyVelocity(this);
            MassFrame      = new RigidBodyMassFrame(this);
            Descriptor     = descriptor;
        }
Пример #19
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      var contentManager = _services.GetInstance<ContentManager>();
      
      // A rusty barrel with multiple levels of detail (LODs).
      _rigidBody = new RigidBody(new CylinderShape(0.35f, 1));
      _modelNode0 = contentManager.Load<ModelNode>("Barrel/Barrel").Clone();
      SampleHelper.EnablePerPixelLighting(_modelNode0);

      // Mark the LOD nodes with UserFlags = 1.
      _modelNode0.GetDescendants()
                 .OfType<LodGroupNode>()
                 .SelectMany(lodGroupNode => lodGroupNode.Levels)
                 .Select(level => level.Node)
                 .ForEach(node =>
                          {
                            node.UserFlags = 1;
                          });

      // Add a second model where each LOD has a different color.
      _modelNode1 = contentManager.Load<ModelNode>("Barrel/Barrel_Colored").Clone();
      SampleHelper.EnablePerPixelLighting(_modelNode1);

      // Mark the LOD nodes with UserFlags = 2.
      _modelNode1.GetDescendants()
                 .OfType<LodGroupNode>()
                 .SelectMany(lodGroupNode => lodGroupNode.Levels)
                 .Select(level => level.Node)
                 .ForEach(node =>
                         {
                           node.UserFlags = 2;
                         });


      // Set a random pose.
      var randomPosition = new Vector3F(
        RandomHelper.Random.NextFloat(-10, 10),
        RandomHelper.Random.NextFloat(2, 5),
        RandomHelper.Random.NextFloat(-10, 0));
      _rigidBody.Pose = new Pose(randomPosition, RandomHelper.Random.NextQuaternionF());
      _modelNode0.PoseWorld = _rigidBody.Pose;
      _modelNode1.PoseWorld = _rigidBody.Pose;

      // Add rigid body to physics simulation and models to scene.
      var simulation = _services.GetInstance<Simulation>();
      simulation.RigidBodies.Add(_rigidBody);

      var scene = _services.GetInstance<IScene>();
      scene.Children.Add(_modelNode0);
      scene.Children.Add(_modelNode1);
    }
Пример #20
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      var graphicsService = _services.GetInstance<IGraphicsService>();
      var gameObjectService = _services.GetInstance<IGameObjectService>();
      var content = _services.GetInstance<ContentManager>();

      // Check if the game object manager has another ProceduralObject instance.
      var otherProceduralObject = gameObjectService.Objects
                                                   .OfType<ProceduralObject>()
                                                   .FirstOrDefault(o => o != this);
      Mesh mesh;
      if (otherProceduralObject != null)
      {
        // This ProceduralObject is not the first. We re-use rigid body data and 
        // the mesh from the existing instance.
        var otherBody = otherProceduralObject._rigidBody;
        _rigidBody = new RigidBody(otherBody.Shape, otherBody.MassFrame, otherBody.Material);
        mesh = otherProceduralObject._meshNode.Mesh;
      }
      else
      {
        // This is the first ProceduralObject instance. 
        // Create a a new rigid body.
        var shape = new MinkowskiSumShape(new GeometricObject(new SphereShape(0.05f)), new GeometricObject(new BoxShape(0.5f, 0.5f, 0.5f)));
        _rigidBody = new RigidBody(shape);

        // Create a new mesh. See SampleHelper.CreateMesh for more details.
        mesh = SampleHelper.CreateMesh(content, graphicsService, _rigidBody.Shape);
        mesh.Name = "ProceduralObject";
      }

      // Create a scene graph node for the mesh.
      _meshNode = new MeshNode(mesh);

      // Set a random pose.
      var randomPosition = new Vector3F(
        RandomHelper.Random.NextFloat(-10, 10),
        RandomHelper.Random.NextFloat(2, 5),
        RandomHelper.Random.NextFloat(-20, 0));
      _rigidBody.Pose = new Pose(randomPosition, RandomHelper.Random.NextQuaternionF());
      _meshNode.PoseWorld = _rigidBody.Pose;

      // Add mesh node to scene graph.
      var scene = _services.GetInstance<IScene>();
      scene.Children.Add(_meshNode);

      // Add rigid body to the physics simulation.
      var simulation = _services.GetInstance<Simulation>();
      simulation.RigidBodies.Add(_rigidBody);
    }
Пример #21
0
    public ContinuousCollisionDetectionSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",            // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Add a thin wall.
      RigidBody body = new RigidBody(new BoxShape(10, 10, 0.1f))
      {
        MotionType = MotionType.Static,
        Pose = new Pose(new Vector3F(0, 5, -5))
      };
      Simulation.RigidBodies.Add(body);

      // ----- Add two fast bodies that move to the wall.
      // The first object does not use CCD. (Per default, RigidBody.CcdEnabled is false.)
      // The second object uses CCD.
      SphereShape bulletShape = new SphereShape(0.2f);
      body = new RigidBody(bulletShape)
      {
        Pose = new Pose(new Vector3F(-2, 5, 5.5f)),
        LinearVelocity = new Vector3F(0, 0, -100),
      };
      Simulation.RigidBodies.Add(body);

      body = new RigidBody(bulletShape)
      {
        Pose = new Pose(new Vector3F(2, 5, 5.5f)),
        LinearVelocity = new Vector3F(0, 0, -100),

        // Enable CCD for this body.
        CcdEnabled = true,
      };
      Simulation.RigidBodies.Add(body);

      // Note:
      // Global CCD settings can be changed in Simulation.Settings.Motion.
      // CCD can be globally enabled or disabled. 
      // Per default, Simulation.Settings.Motion.CcdEnabled is true. But RigidBody.CcdEnabled
      // is false. RigidBody.CcdEnabled should be set for critical game objects.
    }
Пример #22
0
    public CompositeMaterial2Sample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(new Vector3F(0, 1, 0.25f).Normalized, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };

      // Adjust the coefficients of friction of the ground plane.
      ((UniformMaterial)groundPlane.Material).DynamicFriction = 0.5f;
      ((UniformMaterial)groundPlane.Material).StaticFriction = 0.5f;
      Simulation.RigidBodies.Add(groundPlane);

      // Prepare two materials: a slippery material and a rough material.
      UniformMaterial slipperyMaterial = new UniformMaterial
      {
        DynamicFriction = 0.001f,
        StaticFriction = 0.001f,
      };
      UniformMaterial roughMaterial = new UniformMaterial
      {
        DynamicFriction = 1,
        StaticFriction = 1,
      };

      // Create a rigid body that consists of multiple shapes: Two boxes and a cylinder between them.
      CompositeShape compositeShape = new CompositeShape();
      compositeShape.Children.Add(new GeometricObject(new BoxShape(1f, 1f, 1f), new Pose(new Vector3F(1.5f, 0f, 0f))));
      compositeShape.Children.Add(new GeometricObject(new BoxShape(1f, 1, 1f), new Pose(new Vector3F(-1.5f, 0f, 0f))));
      compositeShape.Children.Add(new GeometricObject(new CylinderShape(0.1f, 2), new Pose(Matrix33F.CreateRotationZ(ConstantsF.PiOver2))));

      // A CompositeMaterial is used to assign a different material to each shape.
      CompositeMaterial compositeMaterial = new CompositeMaterial();
      compositeMaterial.Materials.Add(roughMaterial);     // Assign the rough material to the first box.
      compositeMaterial.Materials.Add(slipperyMaterial);  // Assign the slippery material to the second box.
      compositeMaterial.Materials.Add(null);              // Use whatever is default for the handle between the boxes.

      RigidBody body = new RigidBody(compositeShape, null, compositeMaterial)
      {
        Pose = new Pose(new Vector3F(0, 2.2f, -5)),
      };
      Simulation.RigidBodies.Add(body);
    }
Пример #23
0
    public WallSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // ----- Create a wall of boxes.
      const int wallHeight = 10;
      const int wallWidth = 10;
      const float boxWidth = 1.0f;
      const float boxDepth = 0.5f;
      const float boxHeight = 0.5f;
      BoxShape boxShape = new BoxShape(boxWidth, boxHeight, boxDepth);

      // Optional: Use a small overlap between boxes to improve the stability.
      float overlap = Simulation.Settings.Constraints.AllowedPenetration * 0.5f;

      float x;
      float y = boxHeight / 2 - overlap;
      float z = -5;

      for (int i = 0; i < wallHeight; i++)
      {
        for (int j = 0; j < wallWidth; j++)
        {
          // Tip: Leave a small gap between neighbor bricks. If the neighbors on the same
          // row do not touch, the simulation has less work to do!
          x = -boxWidth * wallWidth / 2 + j * (boxWidth + 0.02f) + (i % 2) * boxWidth / 2;
          RigidBody brick = new RigidBody(boxShape)
          {
            Name = "Brick" + i,
            Pose = new Pose(new Vector3F(x, y, z)),
          };
          Simulation.RigidBodies.Add(brick);
        }

        y += boxHeight - overlap;
      }
    }
Пример #24
0
    public ContentPipelineHeightFieldSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Load height field model and add it to the graphics scene.
      _heightFieldModelNode = ContentManager.Load<ModelNode>("HeightField/TerrainHeights").Clone();
      GraphicsScreen.Scene.Children.Add(_heightFieldModelNode);

      // The UserData contains the collision shape of type HeightField.
      HeightField heightField = (HeightField)_heightFieldModelNode.UserData;

      _heightFieldModelNode.PoseWorld = new Pose(new Vector3F(-heightField.WidthX / 2, 0, -heightField.WidthZ / 2));

      // Create rigid body.
      _heightFieldBody = new RigidBody(heightField, null, null)
      {
        MotionType = MotionType.Static,
        Pose = _heightFieldModelNode.PoseWorld,

        // The PhysicsSample class should not draw the height field. 
        UserData = "NoDraw",
      };
      Simulation.RigidBodies.Add(_heightFieldBody);

      // Distribute a few spheres and boxes across the landscape.
      SphereShape sphereShape = new SphereShape(0.5f);
      for (int i = 0; i < 30; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-30, 30);
        position.Y = 20;

        RigidBody body = new RigidBody(sphereShape) { Pose = new Pose(position) };
        Simulation.RigidBodies.Add(body);
      }

      BoxShape boxShape = new BoxShape(1, 1, 1);
      for (int i = 0; i < 30; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-30, 30);
        position.Y = 20;

        RigidBody body = new RigidBody(boxShape) { Pose = new Pose(position) };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #25
0
    public TechniqueBindingSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      SampleFramework.IsMouseVisible = false;

      _graphicsScreen = new DeferredGraphicsScreen(Services);
      _graphicsScreen.DrawReticle = true;
      GraphicsService.Screens.Insert(0, _graphicsScreen);

      Services.Register(typeof(DebugRenderer), null, _graphicsScreen.DebugRenderer);
      Services.Register(typeof(IScene), null, _graphicsScreen.Scene);

      // Add gravity and damping to the physics Simulation.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a custom game object which controls the camera.
      var cameraGameObject = new CameraObject(Services);
      GameObjectService.Objects.Add(cameraGameObject);
      _graphicsScreen.ActiveCameraNode = cameraGameObject.CameraNode;

      // More standard objects.
      GameObjectService.Objects.Add(new GrabObject(Services));
      GameObjectService.Objects.Add(new ObjectCreatorObject(Services));
      GameObjectService.Objects.Add(new StaticSkyObject(Services));
      GameObjectService.Objects.Add(new GroundObject(Services));

      // Tell the graphics service how to treat effect techniques which use
      // the "RepeatParameter" annotation.
      _repeatTechniqueInterpreter = new RepeatTechniqueInterpreter();
      GraphicsService.EffectInterpreters.Insert(0, _repeatTechniqueInterpreter);
      _repeatTechniqueBinder = new RepeatTechniqueBinder();
      GraphicsService.EffectBinders.Insert(0, _repeatTechniqueBinder);

      // Load model.
      _modelNode = ContentManager.Load<ModelNode>("Fur2/FurBall").Clone();
      _rigidBody = new RigidBody(new SphereShape(0.5f));

      // Set a random pose.
      _rigidBody.Pose = new Pose(new Vector3F(0, 1, 0), RandomHelper.Random.NextQuaternionF());
      _modelNode.PoseWorld = _rigidBody.Pose;

      // Add rigid body to physics simulation and model to scene.
      Simulation.RigidBodies.Add(_rigidBody);
      _graphicsScreen.Scene.Children.Add(_modelNode);
    }
Пример #26
0
    public KinematicSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",           // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Create the kinematic body. (Kinematic means that the velocity of the body is not 
      // the result of simulated forces and constraints. Instead the velocity of the body 
      // is directly controlled by the application.)
      _kinematicBody = new RigidBody(new ConeShape(0.3f, 1))
      {
        MotionType = MotionType.Kinematic
      };
      Simulation.RigidBodies.Add(_kinematicBody);

      // Create a cyclic path.
      CreatePath();

      // Add a number of random boxes.
      const int numberOfBoxes = 20;
      BoxShape boxShape = new BoxShape(1, 1, 1);
      for (int i = 0; i < numberOfBoxes; i++)
      {
        Vector3F randomPosition = RandomHelper.Random.NextVector3F(-5, 5);
        randomPosition.Y = 5;
        QuaternionF randomOrientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(boxShape)
        {
          Pose = new Pose(randomPosition, randomOrientation),
        };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #27
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      // Prepare n balls.
      const int n = 10;
      _balls = new RigidBody[n];
      var sphereShape = new SphereShape(0.25f);
      for (int i = 0; i < _balls.Length; i++)
      {
        _balls[i] = new RigidBody(sphereShape)  // Note: All rigid bodies share the same shape.
        {
          // Assign a name. (Just for debugging.)
          Name = "Ball" + i,

          // The balls are shot with a high velocity. We need to enable "Continuous Collision 
          // Detection" - otherwise, we could miss some collision.
          CcdEnabled = true,
        };
      }
    }
Пример #28
0
    public override void Apply(RigidBody body)
    {
      // Gravity forces act on the center of mass.
      Vector3F centerOfMass = body.PoseCenterOfMass.Position;

      // Normalize the vector.
      if (!centerOfMass.TryNormalize())
      {
        // Unable to normalize the vector, the body is already in the gravity origin.
        return;
      }

      // The gravity should act from the center of mass to the origin.
      Vector3F gravityDirection = -centerOfMass;

      // Add gravity force with an acceleration of 9.81 m/s².
      // (force = mass * acceleration)
      AddForce(body, body.MassFrame.Mass * gravityDirection * 9.81f);
    }
Пример #29
0
    public CustomGravitySample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new CustomGravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a static sphere that represents the planet.
      RigidBody planet = new RigidBody(new SphereShape(5))
      {
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(planet);

      // ----- Add a few cylinder and sphere bodies at random positions above the planet.
      Shape cylinderShape = new CylinderShape(0.3f, 1);
      for (int i = 0; i < 10; i++)
      {
        // A random position 10 m above the planet center.
        Vector3F randomPosition = RandomHelper.Random.NextVector3F(-1, 1);
        randomPosition.Length = 10;

        RigidBody body = new RigidBody(cylinderShape)
        {
          Pose = new Pose(randomPosition),
        };
        Simulation.RigidBodies.Add(body);
      }

      Shape sphereShape = new SphereShape(0.5f);
      for (int i = 0; i < 10; i++)
      {
        Vector3F randomPosition = RandomHelper.Random.NextVector3F(-1, 1);
        randomPosition.Length = 10;

        RigidBody body = new RigidBody(sphereShape)
        {
          Pose = new Pose(randomPosition),
        };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #30
0
        public override void Initialize()
        {
            // Prepare 10 balls.
              _balls = new RigidBody[10];
              Shape sphereShape = new SphereShape(0.2f);
              for (int i = 0; i < _balls.Length; i++)
              {
            _balls[i] = new RigidBody(sphereShape)      // Note: All rigid bodies share the same shape.
            {
              // Assign a name. (Just for debugging.)
              Name = "Ball" + i,

              // The balls are shot with a high velocity. We need to enable "Continuous Collision
              // Detection" - otherwise, we could miss some collision.
              CcdEnabled = true,
            };
              }

              base.Initialize();
        }
Пример #31
0
    public RagdollSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane", // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Add a number of ragdolls.
      for (int i = 0; i < 5; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-3, 3);
        position.Y = 1 + i;
        AddRagdoll(Simulation, 1, position, 0.0005f, true);
      }

      // Add some random, static boxes.
      BoxShape boxShape = new BoxShape(1, 1, 1);
      for (int i = 0; i < 10; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-5, 5);
        position.Y = 0.5f;
        QuaternionF orientation = RandomHelper.Random.NextQuaternionF();

        RigidBody body = new RigidBody(boxShape)
        {
          Pose = new Pose(position, orientation),
          MotionType = MotionType.Static
        };
        Simulation.RigidBodies.Add(body);
      }
    }
Пример #32
0
    public BreakableJointsSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity());
      Simulation.ForceEffects.Add(new Damping());

      // Add a ground plane.
      RigidBody groundPlane = new RigidBody(new PlaneShape(Vector3F.UnitY, 0))
      {
        Name = "GroundPlane",            // Names are not required but helpful for debugging.
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(groundPlane);

      // Add ragdolls. We use the Ragdoll-creation method of Sample21.
      for (int i = 0; i < 5; i++)
      {
        Vector3F position = RandomHelper.Random.NextVector3F(-3, 3);
        position.Y = 1 + i;
        RagdollSample.AddRagdoll(Simulation, 2f, position, 0.0001f, false);
      }
    }
Пример #33
0
    public RollingSphereSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      // To demonstrate the problems with triangle meshes we increase the gravity and let a
      // sphere roll over a curved surface.

      // Add basic force effects.
      Simulation.ForceEffects.Add(new Gravity { Acceleration = new Vector3F(0, -30, 0) });   // Higher gravity to make the problem more visible.
      Simulation.ForceEffects.Add(new Damping());

      // Use the custom contact filter to improve sphere contacts.
      _sphereContactFilter = new SphereContactFilter();
      Simulation.CollisionDomain.CollisionDetection.ContactFilter = _sphereContactFilter;

      // The triangle mesh could be loaded from a file, such as an XNA Model.
      // In this example will create a height field and convert the height field into a triangle mesh.
      var numberOfSamplesX = 60;
      var numberOfSamplesZ = 10;
      var samples = new float[numberOfSamplesX * numberOfSamplesZ];
      for (int z = 0; z < numberOfSamplesZ; z++)
        for (int x = 0; x < numberOfSamplesX; x++)
          samples[z * numberOfSamplesX + x] = (float)(Math.Sin(x / 6f) * 10f + 5f);

      var heightField = new HeightField(0, 0, 70, 30, samples, numberOfSamplesX, numberOfSamplesZ);

      // Convert the height field to a triangle mesh.
      ITriangleMesh mesh = heightField.GetMesh(0.01f, 3);

      // Create a shape for the triangle mesh.
      _triangleMeshShape = new TriangleMeshShape(mesh);

      // Enable contact welding. And set the welding limit to 1 for maximal effect.
      _triangleMeshShape.EnableContactWelding = true;
      _originalWeldingLimit = TriangleMeshAlgorithm.WeldingLimit;
      TriangleMeshAlgorithm.WeldingLimit = 1;

      // Optional: Assign a spatial partitioning scheme to the triangle mesh. (A spatial partition
      // adds an additional memory overhead, but it improves collision detection speed tremendously!)
      _triangleMeshShape.Partition = new CompressedAabbTree() { BottomUpBuildThreshold = 0 };

      // Create a static rigid body using the shape and add it to the simulation.
      // We explicitly specify a mass frame. We can use any mass frame for static bodies (because
      // static bodies are effectively treated as if they have infinite mass). If we do not specify 
      // a mass frame in the rigid body constructor, the constructor will automatically compute an 
      // approximate mass frame (which can take some time for large meshes).
      var ground = new RigidBody(_triangleMeshShape, new MassFrame(), null)
      {
        Pose = new Pose(new Vector3F(-34, 0, -40f)),
        MotionType = MotionType.Static,
      };
      Simulation.RigidBodies.Add(ground);

      SphereShape sphereShape = new SphereShape(0.5f);
      _sphere = new RigidBody(sphereShape);
      Simulation.RigidBodies.Add(_sphere);

      _enableSmoothMovement = true;
      _timeUntilReset = TimeSpan.Zero;
    }