} // end of PlayCollision() /// <summary> /// Play audio for actor/terrrain collision /// </summary> /// <param name="actor"></param> /// <param name="material">Material index.</param> public static void PlayCollision(GameThing actor, ushort material) { // Get the proper collision sound from the material index. if (!TerrainMaterial.IsValid(material, false, false)) { //Debug.Assert(false, "Why do we have an invalid material here?"); // Why? Well because we sometimes clear the material in the feeler // collision testing. So it's no longer a valid way to tell what // terrain we're over. In general, it works when we're on the ground // but not when jumping. Argh. collisionMetalSoft.Play(actor); return; } PlayActorCollision(actor); CollisionSound cs = TerrainMaterial.Get(material).CollisionSound; switch (cs) { case CollisionSound.plasticHard: collisionPlasticHard.Play(actor); break; case CollisionSound.plasticSoft: collisionPlasticSoft.Play(actor); break; case CollisionSound.metalHard: collisionMetalHard.Play(actor); break; case CollisionSound.metalSoft: collisionMetalSoft.Play(actor); break; case CollisionSound.rover: collisionRover.Play(actor); break; case CollisionSound.dirt: collisionDirt.Play(actor); break; case CollisionSound.grass: collisionGrass.Play(actor); break; case CollisionSound.rock: collisionRock.Play(actor); break; default: break; } } // end of PlayCollision()
} // end of HandleTouchInput() public override void Render(Camera camera) { // Don't bother if offscreen. Vector3 position = worldMatrix.Translation; float radius = 2.0f; Frustum.CullResult cullResult = camera.Frustum.CullTest(position, radius); if (cullResult == Frustum.CullResult.TotallyOutside) { return; } GraphicsDevice device = BokuGame.bokuGame.GraphicsDevice; Terrain terrain = BokuGame.bokuGame.inGame.Terrain; int materialIndex = Terrain.UISlotToMatIndex(uiSlot); Effect effect = terrain.EffectColor; EffectTechnique technique = TerrainMaterial.Get(materialIndex).TechniqueColor(TerrainMaterial.EffectTechs.TerrainColorPass); effect.CurrentTechnique = technique; // We need to push the near plane out more than is normal for UI // so that the material cubes don't render behind the terrain. Camera cam = camera; cam.NearClip = 6.0f; Matrix twistMatrix = Matrix.CreateRotationZ(worldMatrix.Translation.X + 0.5f); float scale = MathHelper.Clamp(2.0f / ((float)Math.Abs(worldMatrix.Translation.X) + 1.0f), 0.1f, 1.0f); Matrix scaleMatrix = Matrix.CreateScale(scale); Matrix world = twistMatrix * scaleMatrix * worldMatrix; Vector3 trans = world.Translation; trans.X *= scale + 0.5f; world.Translation = trans; hitWorld = world; // Compensate for verts being [0..1] instead of [-0.5..0.5] as we'd prefer. // They must be in [0..1] because UV mapping is implicit in local position. Matrix preTrans = Matrix.Identity; preTrans.Translation = new Vector3(-0.5f, -0.5f, -0.5f); world = preTrans * world; Matrix worldViewProjMatrix = world * cam.ViewProjectionMatrix; terrain.ParameterColor(Terrain.EffectParams.WorldMatrix).SetValue(worldMatrix); terrain.ParameterColor(Terrain.EffectParams.WorldViewProjMatrix).SetValue(worldViewProjMatrix); terrain.ParameterColor(Terrain.EffectParams.WarpCenter).SetValue(Vector4.Zero); terrain.ParameterEdit(Terrain.EffectParams.WorldMatrix).SetValue(worldMatrix); terrain.ParameterEdit(Terrain.EffectParams.WorldViewProjMatrix).SetValue(worldViewProjMatrix); terrain.ParameterEdit(Terrain.EffectParams.WarpCenter).SetValue(Vector4.Zero); #if NETFX_CORE // Note: Indexing into shaders doesn't work with MG. Apparently it // was some hack done in XNA related to the Effect code they used. // Anyway, instead of using this indexing we need to pick and set // the right technique which we do further down from here. #else if (BokuSettings.Settings.PreferReach) { //Select the VS based on the number of point-lights var lightNum = Boku.Fx.Luz.Count; if (lightNum > 6) { terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(4); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(4); } else if (lightNum > 4) { terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(3); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(3); } else if (lightNum > 2) { terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(2); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(2); } else if (lightNum > 0) { terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(1); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(1); } else { terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(0); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(0); } //Select the PS terrain.ParameterColor(Terrain.EffectParams.PSIndex).SetValue(0); terrain.ParameterEdit(Terrain.EffectParams.PSIndex).SetValue(0); } else // Shader Model v3 { //SM3 only uses one VS terrain.ParameterColor(Terrain.EffectParams.VSIndex).SetValue(5); terrain.ParameterEdit(Terrain.EffectParams.VSIndex).SetValue(5); //Select the PS terrain.ParameterColor(Terrain.EffectParams.PSIndex).SetValue(2); terrain.ParameterEdit(Terrain.EffectParams.PSIndex).SetValue(2); } #endif if (MaterialPicker.FabricMode) { var cubeSize = 1f; terrain.ParameterColor(Terrain.EffectParams.InvCubeSize).SetValue(new Vector3(cubeSize, 1.0f / cubeSize, cubeSize * 0.5f)); terrain.ParameterEdit(Terrain.EffectParams.InvCubeSize).SetValue(new Vector3(cubeSize, 1.0f / cubeSize, cubeSize * 0.5f)); #region Fabric device.SetVertexBuffer(vBuff_FA); device.Indices = iBuff_FA; terrain.SetGlobalParams_FA(); terrain.SetMaterialParams_FA((ushort)materialIndex, true); TerrainMaterial mat = TerrainMaterial.Get(materialIndex); #if NETFX_CORE int lightNum = Boku.Fx.Luz.Count; if (lightNum > 6) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L10_FA_SM2"]; } else if (lightNum > 4) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L6_FA_SM2"]; } else if (lightNum > 2) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L4_FA_SM2"]; } else if (lightNum > 0) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L2_FA_SM2"]; } else { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L0_FA_SM2"]; } #else effect.CurrentTechnique = mat.TechniqueColor(TerrainMaterial.EffectTechs_FA.TerrainColorPass_FA); #endif foreach (EffectPass pass in effect.CurrentTechnique.Passes) { pass.Apply(); device.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, 37, 0, 56); } #endregion } else { #region Cube var cubeSize = 1.0f; terrain.ParameterColor(Terrain.EffectParams.InvCubeSize).SetValue(new Vector3(cubeSize, 1.0f / cubeSize, cubeSize * 0.5f)); terrain.ParameterEdit(Terrain.EffectParams.InvCubeSize).SetValue(new Vector3(cubeSize, 1.0f / cubeSize, cubeSize * 0.5f)); Tile.CheckIndices(new Point(32, 32)); if (Terrain.RenderMethod == Terrain.RenderMethods.FewerDraws) { device.SetVertexBuffer(vBuff); device.Indices = Tile.IndexBuffer_FD(); terrain.SetGlobalParams_FD(); terrain.SetMaterialParams_FD((ushort)materialIndex, true); } TerrainMaterial mat = TerrainMaterial.Get(materialIndex); #if NETFX_CORE int lightNum = Boku.Fx.Luz.Count; if (lightNum > 6) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L10_FD_SM2"]; } else if (lightNum > 4) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L6_FD_SM2"]; } else if (lightNum > 2) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L4_FD_SM2"]; } else if (lightNum > 0) { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L2_FD_SM2"]; } else { effect.CurrentTechnique = effect.Techniques["TerrainColorPass_L0_FD_SM2"]; } #else effect.CurrentTechnique = mat.TechniqueColor(TerrainMaterial.EffectTechs.TerrainColorPass); #endif foreach (EffectPass pass in effect.CurrentTechnique.Passes) { if (Terrain.RenderMethod == Terrain.RenderMethods.FewerDraws) { terrain.SetTopParams_FD((ushort)materialIndex, true); pass.Apply(); device.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, 4, 0, 2); //20 verts, 10 triangles terrain.SetSideParams_FD((ushort)materialIndex, true); pass.Apply(); device.DrawIndexedPrimitives(PrimitiveType.TriangleList, 4, 0, 16, 0, 8); //20 verts, 10 triangles } } #endregion } RenderLabel(camera, world); } // end of UIGridMaterialElement Render()