|
|
using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Graphics; using System.Collections.Generic;
namespace SemiColinGames { static class Debug { struct DebugRect { public Rectangle Rect; public Color Color;
public DebugRect(Rectangle rect, Color color) { Rect = rect; Color = color; } }
struct DebugLine { public Point Start; public Point End; public Color Color;
public DebugLine(Point start, Point end, Color color) { Start = start; End = end; Color = color; } }
public static bool Enabled = true; // Lines in excess of MAX_LINES get dropped on the floor.
const int MAX_LINES = 1000; const int MAX_LINE_VERTICES = MAX_LINES * 2; // This is a LinkedList instead of a List because SetFpsText() adds to its front.
static readonly LinkedList<string> toasts = new LinkedList<string>(); static readonly List<DebugRect> rects = new List<DebugRect>(); static int lineIdx = 0; static readonly VertexPositionColor[] lineVertices = new VertexPositionColor[MAX_LINE_VERTICES]; static VertexBuffer vertexBuffer;
static Texture2D whiteTexture;
public static void Initialize(GraphicsDevice graphics, Texture2D white) { whiteTexture = white; vertexBuffer = new VertexBuffer( graphics, typeof(VertexPositionColor), MAX_LINE_VERTICES, BufferUsage.WriteOnly); }
public static void WriteLine(string s) { System.Diagnostics.Debug.WriteLine(s); }
public static void WriteLine(string s, params object[] args) { System.Diagnostics.Debug.WriteLine(s, args); }
public static void Clear(bool paused) { toasts.Clear(); if (!paused) { rects.Clear(); lineIdx = 0; } }
public static void AddToast(string s) { toasts.AddLast(s); }
// FPS text is always displayed as the first toast (if set).
public static void SetFpsText(string s) { toasts.AddFirst(s); }
public static void AddRect(Rectangle rect, Color color) { rects.Add(new DebugRect(rect, color)); }
public static void AddRect(AABB box, Color color) { Rectangle rect = new Rectangle( (int) (box.Position.X - box.HalfSize.X), (int) (box.Position.Y - box.HalfSize.Y), (int) (box.HalfSize.X * 2), (int) (box.HalfSize.Y * 2)); AddRect(rect, color); }
public static void AddLine(Point start, Point end, Color color) { if (lineIdx >= MAX_LINE_VERTICES) { return; } lineVertices[lineIdx] = new VertexPositionColor(new Vector3(start.X, start.Y, 0), color); lineVertices[lineIdx + 1] = new VertexPositionColor(new Vector3(end.X, end.Y, 0), color); lineIdx += 2; }
public static void AddLine(int p1x, int p1y, int p2x, int p2y, Color color) { AddLine(new Point(p1x, p1y), new Point(p2x, p2y), color); }
public static void AddLine(Vector2 start, Vector2 end, Color color) { AddLine(start.ToPoint(), end.ToPoint(), color); }
public static void DrawToasts(SpriteBatch spriteBatch, SpriteFont font) { if (!Enabled) { return; } int y = 10; foreach (var toast in toasts) { spriteBatch.DrawString(font, toast, new Vector2(10, y), Color.Teal); y += 30; } }
public static void Draw( SpriteBatch spriteBatch, GraphicsDevice graphics, BasicEffect lightingEffect) { if (!Enabled) { return; }
// Draw rects.
foreach (var debugRect in rects) { var rect = debugRect.Rect; var color = debugRect.Color; // top side
spriteBatch.Draw( whiteTexture, new Rectangle(rect.Left, rect.Top, rect.Width, 1), color); // bottom side
spriteBatch.Draw( whiteTexture, new Rectangle(rect.Left, rect.Bottom - 1, rect.Width, 1), color); // left side
spriteBatch.Draw( whiteTexture, new Rectangle(rect.Left, rect.Top, 1, rect.Height), color); // right side
spriteBatch.Draw( whiteTexture, new Rectangle(rect.Right - 1, rect.Top, 1, rect.Height), color); }
// Draw lines.
graphics.SetVertexBuffer(vertexBuffer); vertexBuffer.SetData(lineVertices); foreach (EffectPass pass in lightingEffect.CurrentTechnique.Passes) { pass.Apply(); graphics.DrawPrimitives(PrimitiveType.LineList, 0, lineIdx / 2); } } } }
|