예제 #1
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();
    }
예제 #2
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      var particleSystemService = _services.GetInstance<IParticleSystemService>();

      // The campfire consists of two particle systems (fire + smoke) and a light source.
      // 
      //   _campfire (SceneNode)
      //      |
      //      +-- _fireParticles (ParticleSystemNode)
      //      |
      //      +-- _smokeParticles (ParticleSystemNode)
      //      |
      //      +-- _light (LightNode)

      // Use a basic scene node as the root node for the campfire.
      _campfire = new SceneNode
      {
        Name = "Campfire",
        PoseLocal = new Pose(new Vector3F(0, 0, -1)),
        Children = new SceneNodeCollection()
      };

      // Add fire particles.
      var contentManager = _services.GetInstance<ContentManager>();
      var particleSystem = CreateFire(contentManager);
      particleSystemService.ParticleSystems.Add(particleSystem);
      _fireParticles = new ParticleSystemNode(particleSystem)
      {
        // The fire effect lies in the xy plane and shoots into the forward direction (= -z axis).
        // Therefore we rotate the particle system to shoot upwards.
        PoseLocal = new Pose(new Vector3F(0, 0.2f, 0), Matrix33F.CreateRotationX(ConstantsF.PiOver2))
      };
      _campfire.Children.Add(_fireParticles);

      // Add smoke particles.
      particleSystem = CreateSmoke(contentManager);
      particleSystemService.ParticleSystems.Add(particleSystem);
      _smokeParticles = new ParticleSystemNode(particleSystem)
      {
        PoseLocal = new Pose(new Vector3F(0, 0.2f, 0), Matrix33F.CreateRotationX(ConstantsF.PiOver2))
      };
      _campfire.Children.Add(_smokeParticles);

      // Add a point light that illuminates the environment.
      var light = new PointLight
      {
        Attenuation = 0.1f,
        Color = new Vector3F(1, 0.2f, 0),
        HdrScale = 20,
        Range = 4
      };
      _light = new LightNode(light)
      {
        // Optional: We can make this light cast shadows - but this will cost performance!
        //Shadow = new CubeMapShadow { PreferredSize = 64, FilterRadius = 2, JitterResolution = 2048 },
        PoseLocal = new Pose(new Vector3F(0, 1f, 0))
      };
      _campfire.Children.Add(_light);

      // Add campfire to scene.
      var scene = _services.GetInstance<IScene>();
      scene.Children.Add(_campfire);

      // Particle effects can be added multiple times to the scene (= "instancing").
      // Uncomment the following lines to add a few more instance to the scene.
      //for (int i = 0; i < 10; i++)
      //{
      //  var clone = _campfire.Clone();

      //  // Set random scale, position, orientation.
      //  clone.ScaleLocal = _random.NextVector3F(0.5f, 1.5f);
      //  var pose = _campfire.PoseWorld;
      //  pose.Position.X += _random.NextFloat(-10, 10);
      //  pose.Position.Z += _random.NextFloat(-10, 10);
      //  pose.Orientation = Matrix33F.CreateRotationY(_random.NextFloat(-ConstantsF.PiOver2, ConstantsF.PiOver2));
      //  clone.PoseLocal = pose;

      //  scene.Children.Add(clone);
      //}

      // Add GUI controls to the Options window.
      var sampleFramework = _services.GetInstance<SampleFramework>();
      var optionsPanel = sampleFramework.AddOptions("Game Objects");
      var panel = SampleHelper.AddGroupBox(optionsPanel, "CampfireObject");
      SampleHelper.AddCheckBox(
        panel,
        "Enable campfire",
        IsEnabled,
        isChecked => IsEnabled = isChecked);
    }
예제 #3
0
    public ShadowSample(Microsoft.Xna.Framework.Game game)
      : base(game)
    {
      SampleFramework.IsMouseVisible = false;
      _graphicsScreen = new DeferredGraphicsScreen(Services)
      {
        // For debugging: Disable materials and only show light buffer.
        DebugMode = DeferredGraphicsDebugMode.VisualizeDiffuseLightBuffer
      };
      _graphicsScreen.DrawReticle = true;
      GraphicsService.Screens.Insert(0, _graphicsScreen);

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

      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;

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

      CreateScene(Services, ContentManager, _graphicsScreen);

      // Disable existing lights.
      foreach (var lightNode in _graphicsScreen.Scene.GetDescendants().OfType<LightNode>())
        lightNode.IsEnabled = false;

      // Add a dim ambient light.
      _graphicsScreen.Scene.Children.Add(
        new LightNode(
          new AmbientLight
          {
            HemisphericAttenuation = 1,
            Intensity = 0.001f,
          }));

      // Add some test lights with shadows.
      _spotlight = new Spotlight { Range = 10, FalloffAngle = 0.8f, CutoffAngle = 1f };
      _standardShadow = new StandardShadow();
      _spotlightNode = new LightNode(_spotlight)
      {
        PoseWorld = new Pose(new Vector3F(0, 1f, -2)),
        Shadow = _standardShadow,
        IsEnabled = true,
      };
      _graphicsScreen.Scene.Children.Add(_spotlightNode);

      _cubeMapShadow = new CubeMapShadow();
      _pointLight = new PointLight { Range = 10, };
      _pointLightNode = new LightNode(_pointLight)
      {
        PoseWorld = new Pose(new Vector3F(0, 1f, -2)),
        Shadow = _cubeMapShadow,
        IsEnabled = false,
      };
      _graphicsScreen.Scene.Children.Add(_pointLightNode);

      CreateGuiControls();
    }
예제 #4
0
    // OnLoad() is called when the GameObject is added to the IGameObjectService.
    protected override void OnLoad()
    {
      var contentManager = _services.GetInstance<ContentManager>();
      
      if (_type == 1)
      {
        // A simple cube.
        RigidBody = new RigidBody(new BoxShape(1, 1, 1));
        ModelNode = contentManager.Load<ModelNode>("RustyCube/RustyCube").Clone();
      }
      else if (_type == 2)
      {
        // Another simple cube.
        RigidBody = new RigidBody(new BoxShape(1, 1, 1));
        ModelNode = contentManager.Load<ModelNode>("MetalGrateBox/MetalGrateBox").Clone();
      }
      else if (_type == 3)
      {
        // A TV-like box.
        RigidBody = new RigidBody(new BoxShape(1, 0.6f, 0.8f)) { UserData = "TV" };
        ModelNode = contentManager.Load<ModelNode>("TVBox/TVBox");

        if (ModelNode.Children.OfType<LightNode>().Count() == 0)
        {
          // This is the first time the "TVBox" is loaded.

          // Add a projector light to the model that projects the TV screen. The
          // TV screen is the emissive part of the TV mesh.
          var meshNode = ModelNode.Children.OfType<MeshNode>().First();
          var material = meshNode.Mesh.Materials.First(m => m.Name == "TestCard");

          // Get texture from material.
          // Note: In XNA the effect parameter type is Texture. In MonoGame it is Texture2D.
          Texture2D texture;
          EffectParameterBinding parameterBinding = material["Material"].ParameterBindings["EmissiveTexture"];
          if (parameterBinding is EffectParameterBinding<Texture>)
            texture = (Texture2D)((EffectParameterBinding<Texture>)parameterBinding).Value;
          else
            texture = ((EffectParameterBinding<Texture2D>)parameterBinding).Value;

          var projection = new PerspectiveProjection();
          projection.Near = 0.55f;
          projection.Far = 3.0f;
          projection.SetFieldOfView(MathHelper.ToRadians(60), 0.76f / 0.56f);

          var projectorLight = new ProjectorLight(texture, projection);
          projectorLight.Attenuation = 4;
          var projectorLightNode = new LightNode(projectorLight);
          projectorLightNode.LookAt(new Vector3F(0, 0.2f, 0), Vector3F.Zero, Vector3F.UnitZ);

          // Attach the projector light to the model.
          ModelNode.Children.Add(projectorLightNode);
        }

        ModelNode = ModelNode.Clone();
      }
      else if (_type == 4)
      {
        // A "magic" sphere with a colored point light.
        RigidBody = new RigidBody(new SphereShape(0.25f));
        ModelNode = contentManager.Load<ModelNode>("MagicSphere/MagicSphere");

        if (ModelNode.Children.OfType<LightNode>().Count() == 0)
        {
          // This is the first time the "MagicSphere" is loaded.

          // Change the size of the sphere.
          var meshNode = ModelNode.Children.OfType<MeshNode>().First();
          meshNode.ScaleLocal = new Vector3F(0.5f);

          // Disable shadows. (The sphere acts as a light source.)
          meshNode.CastsShadows = false;

          // Add a point light.
          var pointLight = new PointLight
          {
            Color = new Vector3F(1, 1, 1),
            DiffuseIntensity = 4,
            SpecularIntensity = 4,
            Range = 3,
            Attenuation = 1,
            Texture = contentManager.Load<TextureCube>("MagicSphere/ColorCube"),
          };
          var pointLightNode = new LightNode(pointLight)
          {
            // The point light uses shadow mapping to cast an omnidirectional shadow.
            Shadow = new CubeMapShadow
            {
              PreferredSize = 64,
            }
          };

          ModelNode.Children.Add(pointLightNode);
        }

        ModelNode = ModelNode.Clone();
      }
      else if (_type == 5)
      {
        // A sphere of glass (or "bubble").
        RigidBody = new RigidBody(new SphereShape(0.3f));
        ModelNode = contentManager.Load<ModelNode>("Bubble/Bubble").Clone();
        ModelNode.GetDescendants().OfType<MeshNode>().First().ScaleLocal = new Vector3F(0.3f);
      }
      else if (_type == 6)
      {
        // A rusty barrel with multiple levels of detail (LODs).
        RigidBody = new RigidBody(new CylinderShape(0.35f, 1));
        ModelNode = contentManager.Load<ModelNode>("Barrel/Barrel").Clone();
      }
      else
      {
        // A cube consisting of a frame and transparent sides.
        RigidBody = new RigidBody(new BoxShape(1, 1, 1));
        ModelNode = contentManager.Load<ModelNode>("GlassBox/GlassBox").Clone();
      }

      SampleHelper.EnablePerPixelLighting(ModelNode);

      // 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());
      ModelNode.PoseWorld = RigidBody.Pose;

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

      var scene = _services.GetInstance<IScene>();
      scene.Children.Add(ModelNode);
    }