using System;
using System.Collections.Generic;
using System.Text;
using Vortex.Utils;

namespace Vortex.Drawing.Performance {

	/// <summary>
	/// Performance monitor for Vortex.Drawing subsystem
	/// </summary>
	public class PerformanceMonitor : PerformanceMonitor<DeviceCounter, DeviceTimer> {

		/// <summary>
		/// Draws performance statistics specified canvas.
		/// </summary>
		/// <param name="canvas">The canvas.</param>
		public void Draw(Canvas2D canvas, Vector2 leftTopPoint, string titleString) {
			const float PADDING = 8.0f;
			ColorU bgColor = ColorU.Black, frameColor = ColorU.Lime, textColor = ColorU.LightGreen;

			PerformanceMonitor perfMonitor = new PerformanceMonitor();
			CopyTo(perfMonitor);
			perfMonitor.FlushTimers();

			System.Text.StringBuilder builder = new System.Text.StringBuilder();
			if (titleString != null) {
				builder.AppendFormat("{0}\n\n", titleString);
			}

			builder.AppendFormat("Draw time: {0:F2} ms\n", perfMonitor[DeviceTimer.Drawing].Milliseconds);
			builder.AppendFormat("Vertex transfer: {0:F2} ms\n", perfMonitor[DeviceTimer.BufferLock].Milliseconds);

			builder.AppendFormat("\nDynamic:\n");
			builder.AppendFormat("  Batches: {0}\n", perfMonitor[DeviceCounter.BatchesRendered]);
			builder.AppendFormat("  Primitives: {0}\n", perfMonitor[DeviceCounter.PrimitivesDrawn]);
			builder.AppendFormat("  Vertices: {0}\n", perfMonitor[DeviceCounter.VerticesDrawn]);
			builder.AppendFormat("  Indices: {0}\n", perfMonitor[DeviceCounter.IndicesDrawn]);
			builder.AppendFormat("  ~Primitives/Batch: {0}\n", perfMonitor[DeviceCounter.PrimitivesDrawn] / Math.Max(perfMonitor[DeviceCounter.BatchesRendered], 1));
			builder.AppendFormat("\nStates changed:\n");
			builder.AppendFormat("  Canvas Changed: {0}\n", perfMonitor[DeviceCounter.CanvasSwitches]);
			builder.AppendFormat("  Textures: {0}\n", perfMonitor[DeviceCounter.TexturesChanged]);			
			builder.AppendFormat("  Pixel Shaders: {0}\n", perfMonitor[DeviceCounter.PixelShaderChanged]);
			builder.AppendFormat("  Vertex Shaders: {0}\n", perfMonitor[DeviceCounter.VertexShaderChanged]);
			builder.AppendFormat("\nOther:\n");
			builder.AppendFormat("  Text Char Drawn: {0}\n", perfMonitor[DeviceCounter.TextCharDrawn]);

			string text = builder.ToString();

			//measure string
			Vector2 stringSize = Canvas2D.MeasureText(SpriteFont.SmallConsole, text);
			
			Rect textRect = Rect.FromBox(leftTopPoint + PADDING, stringSize);
			Rect bgRect = textRect.Inflate(new Vector2(PADDING));

			canvas.DrawFilledRect(bgRect, bgColor.MultiplyAlpha(0.65f));
			canvas.DrawRect(bgRect, frameColor.MultiplyAlpha(0.65f));
			canvas.DrawText(SpriteFont.SmallConsole, leftTopPoint + PADDING, text, textColor);
		}
	}
}
