/// <summary> /// Draw the game for the specified _time. /// </summary> /// <param name="time">time since start of game (cf BallzGame draw).</param> public override void Draw(GameTime time) { using (new PerformanceReporter(Game)) { base.Draw(time); var worldState = Game.Match.World; WaterRenderer.PrepareDrawWater(Game.Match.World); //GraphicsDevice.SetRenderTarget(WorldRenderTarget); Game.Camera.UseBoundary = true; Game.Camera.BottomLeftBoundary = new Vector2(-100f, 0f); Game.Camera.TopRightBoundary = new Vector2(100f, 100f); if (Game.Match.UsePlayerTurns && Game.Match.ActivePlayer?.ActiveBall != null) { CurrentActiveBall = Game.Match.ActivePlayer?.ActiveBall; if (CurrentActiveBall != null && Game.Match.TurnState == TurnState.Running && Game.Match.ActivePlayer?.ActiveBall != CurrentActiveBall && Game.Match.ActivePlayer?.ActiveBall != null) { CurrentActiveBall = Game.Match.ActivePlayer.ActiveBall; Game.Camera.SwitchTarget(CurrentActiveBall.Position, time); } else if (Game.Match.FocussedEntity != null) { Game.Camera.SetTargetPosition((Vector2)Game.Match.FocussedEntity.Position, time); } } else { Game.Camera.SetView(Matrix.CreateOrthographicOffCenter(0, 40, 0, 40 / Game.GraphicsDevice.Viewport.AspectRatio, -20, 20)); } var shakeEffect = worldState.GraphicsEvents.FirstOrDefault(e => e is CameraShakeEffect) as CameraShakeEffect; if (shakeEffect != null) { var intensity = (1 - shakeEffect.GetProgress(Game.Match.GameTime)) * shakeEffect.Intensity; var offSetX = (float)(random.NextDouble() * 0.02 - 0.01) * intensity; var offSetY = (float)(random.NextDouble() * 0.02 - 0.01) * intensity; var view = Game.Camera.View; view.Translation += new Vector3(offSetX, offSetY, 0); Game.Camera.View = view; } DrawSky(); ////////////////////////////////////////////////////////////////////////////////////////////// // Draw Water ////////////////////////////////////////////////////////////////////////////////////////////// WaterRenderer.DrawWater(worldState); ////////////////////////////////////////////////////////////////////////////////// // Draw the Terrain ////////////////////////////////////////////////////////////////////////////////// BallEffect.View = Game.Camera.View; BallEffect.Projection = Game.Camera.Projection; var tris = worldState.StaticGeometry.GetTriangles(); VertexPositionColorTexture[] vpc = new VertexPositionColorTexture[tris.Count * 3]; int i = 0; float TerrainTextureScale = 0.015f; var terrainSize = new Vector2(worldState.StaticGeometry.width, worldState.StaticGeometry.height); foreach (var t in tris) { vpc[i + 0].Color = Color.Maroon; vpc[i + 0].Position = new Vector3(t.A.X, t.A.Y, -1); vpc[i + 0].TextureCoordinate = new Vector2(t.A.X, t.A.Y) / terrainSize; vpc[i + 1].Color = Color.Maroon; vpc[i + 1].Position = new Vector3(t.B.X, t.B.Y, -1); vpc[i + 1].TextureCoordinate = new Vector2(t.B.X, t.B.Y) / terrainSize; vpc[i + 2].Color = Color.Maroon; vpc[i + 2].Position = new Vector3(t.C.X, t.C.Y, -1); vpc[i + 2].TextureCoordinate = new Vector2(t.C.X, t.C.Y) / terrainSize; i += 3; } Matrix terrainWorld = Matrix.CreateScale(worldState.StaticGeometry.Scale); TerrainEffect.CurrentTechnique.Passes[0].Apply(); TerrainEffect.Parameters["ModelViewProjection"].SetValue(terrainWorld * Game.Camera.View * Game.Camera.Projection); TerrainEffect.Parameters["TerrainTypesTexture"].SetValue(worldState.StaticGeometry.GetTerrainTypeTexture()); TerrainEffect.Parameters["EarthTexture"].SetValue(EarthTexture); TerrainEffect.Parameters["SandTexture"].SetValue(SandTexture); TerrainEffect.Parameters["StoneTexture"].SetValue(StoneTexture); TerrainEffect.Parameters["TextureScale"].SetValue(TerrainTextureScale); //TerrainEffect.Parameters["TerrainSize"].SetValue(terrainSize); GraphicsDevice.DrawUserPrimitives <VertexPositionColorTexture>(PrimitiveType.TriangleList, vpc, 0, tris.Count); /////////////////////////////////////////////////////////////////////////////////// // Draw Ballz and shots /////////////////////////////////////////////////////////////////////////////////// var blending = new BlendState { AlphaSourceBlend = Blend.SourceAlpha, AlphaDestinationBlend = Blend.InverseSourceAlpha, ColorSourceBlend = Blend.SourceAlpha, ColorDestinationBlend = Blend.InverseSourceAlpha, }; SpriteBatch.Begin(blendState: blending); foreach (var entity in worldState.Entities) { if (entity.Disposed) { continue; } var ball = entity as Ball; if (ball != null) { DrawBall(ball); } var shot = entity as Shot; if (shot != null) { DrawShot(shot); } } foreach (var graphicsEvent in worldState.GraphicsEvents) { DrawGraphicsEvent(graphicsEvent); } SpriteBatch.End(); GraphicsDevice.SetRenderTarget(null); PostProcess(); DrawStatusOverlay(); } }