Skip to content

Commit

Permalink
CoreTests: Added Test_MinimapNodeFinder
Browse files Browse the repository at this point in the history
  • Loading branch information
Xian55 committed Dec 10, 2022
1 parent 5334911 commit 72a488c
Show file tree
Hide file tree
Showing 5 changed files with 135 additions and 27 deletions.
3 changes: 2 additions & 1 deletion Core/BotController.cs
Original file line number Diff line number Diff line change
Expand Up @@ -162,7 +162,8 @@ private void ScreenshotThread()
if (ClassConfig?.Mode == Mode.AttendedGather)
{
timestamp = Stopwatch.GetTimestamp();
minimapNodeFinder.TryFind();
WowScreen.UpdateMinimapBitmap();
minimapNodeFinder.Update();
ScreenLatencys[tickCount % SIZE] = Stopwatch.GetElapsedTime(timestamp).TotalMilliseconds;
}

Expand Down
41 changes: 20 additions & 21 deletions Core/Minimap/MinimapNodeFinder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,12 @@ namespace Core
{
public sealed class MinimapNodeFinder
{
private readonly struct Point
private readonly struct PixelPoint
{
public readonly int X;
public readonly int Y;

public Point(int x, int y)
public PixelPoint(int x, int y)
{
X = x;
Y = y;
Expand All @@ -44,20 +44,18 @@ public MinimapNodeFinder(ILogger logger, WowScreen wowScreen)
this.wowScreen = wowScreen;
}

public void TryFind()
public void Update()
{
wowScreen.UpdateMinimapBitmap();

var span = FindYellowPoints();
ScorePoints(span, out Point best, out int amountAboveMin);
ScorePoints(span, out PixelPoint best, out int amountAboveMin);
NodeEvent?.Invoke(this, new MinimapNodeEventArgs(best.X, best.Y, amountAboveMin));
}

private Span<Point> FindYellowPoints()
private Span<PixelPoint> FindYellowPoints()
{
const int SIZE = 100;
var pooler = ArrayPool<Point>.Shared;
Point[] points = pooler.Rent(SIZE);
var pooler = ArrayPool<PixelPoint>.Shared;
PixelPoint[] points = pooler.Rent(SIZE);

Bitmap bitmap = wowScreen.MiniMapBitmap;

Expand All @@ -69,14 +67,14 @@ private Span<Point> FindYellowPoints()
int maxY = bitmap.Height - 6;

Rectangle rect = new(minX, minY, maxX - minX, maxY - minY);
System.Drawing.Point center = rect.Centre();
Point center = rect.Centre();
float radius = (maxX - minX) / 2f;

int count = 0;

unsafe
{
BitmapData data = bitmap.LockBits(new Rectangle(System.Drawing.Point.Empty, bitmap.Size),
BitmapData data = bitmap.LockBits(new Rectangle(Point.Empty, bitmap.Size),
DEBUG_MASK ? ImageLockMode.ReadWrite : ImageLockMode.ReadOnly, bitmap.PixelFormat);
const int bytesPerPixel = 4; //Bitmap.GetPixelFormatSize(bitmap.PixelFormat) / 8;

Expand All @@ -103,7 +101,7 @@ private Span<Point> FindYellowPoints()
if (count >= SIZE)
return;

points[count++] = new Point(x, y);
points[count++] = new PixelPoint(x, y);

if (DEBUG_MASK)
{
Expand All @@ -120,14 +118,14 @@ private Span<Point> FindYellowPoints()

if (count >= SIZE)
{
logger.LogWarning("Too much yellow in this image!");
//logger.LogWarning("Too much yellow in this image!");
}

return points.AsSpan(0, count);

static bool IsValidSquareLocation(int x, int y, System.Drawing.Point center, float width)
static bool IsValidSquareLocation(int x, int y, Point center, float width)
{
return Math.Sqrt(((x - center.X) * (x - center.X)) + ((y - center.Y) * (y - center.Y))) < width;
return MathF.Sqrt(((x - center.X) * (x - center.X)) + ((y - center.Y) * (y - center.Y))) < width;
}

static bool IsMatch(byte red, byte green, byte blue)
Expand All @@ -136,27 +134,28 @@ static bool IsMatch(byte red, byte green, byte blue)
}
}

private static void ScorePoints(Span<Point> points, out Point best, out int amountAboveMin)
private static void ScorePoints(Span<PixelPoint> points, out PixelPoint best, out int amountAboveMin)
{
const int size = 5;

best = new Point();
best = new PixelPoint();
amountAboveMin = 0;

int maxIndex = -1;
int maxScore = 0;

for (int i = 0; i < points.Length; i++)
{
Point pi = points[i];
PixelPoint pi = points[i];

int score = 0;
for (int j = 0; j < points.Length; j++)
{
Point pj = points[j];
PixelPoint pj = points[j];

if (Math.Abs(pi.X - pj.X) < size ||
Math.Abs(pi.Y - pj.Y) < size)
if (i != j &&
(Math.Abs(pi.X - pj.X) < size ||
Math.Abs(pi.Y - pj.Y) < size))
{
score++;
}
Expand Down
77 changes: 77 additions & 0 deletions CoreTests/MinimapNodeFinder/Test_MinimapNodeFinder.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
using System;
using System.Diagnostics;
using System.Drawing;

using Core;

using Game;

using Microsoft.Extensions.Logging;

#pragma warning disable 0162
#pragma warning disable 8618

#nullable enable

namespace CoreTests
{
internal sealed class Test_MinimapNodeFinder : IDisposable
{
private const bool saveImage = false;
private const bool LogEachUpdate = false;

private readonly ILogger logger;

private readonly WowProcess wowProcess;
private readonly WowScreen wowScreen;

private readonly MinimapNodeFinder minimapNodeFinder;

private readonly Stopwatch stopwatch = new();

public Test_MinimapNodeFinder(ILogger logger)
{
this.logger = logger;

wowProcess = new();
wowScreen = new(logger, wowProcess);

minimapNodeFinder = new(logger, wowScreen);
}

public void Dispose()
{
wowScreen.Dispose();
wowProcess.Dispose();
}

public void Execute()
{
if (LogEachUpdate)
stopwatch.Restart();

wowScreen.UpdateMinimapBitmap();

if (LogEachUpdate)
logger.LogInformation($"Capture: {stopwatch.ElapsedMilliseconds}ms");

if (LogEachUpdate)
stopwatch.Restart();

minimapNodeFinder.Update();

if (LogEachUpdate)
logger.LogInformation($"Update: {stopwatch.ElapsedMilliseconds}ms");

if (saveImage)
{
SaveImage();
}
}

private void SaveImage()
{
wowScreen.MiniMapBitmap.Save("minimap.png");
}
}
}
2 changes: 1 addition & 1 deletion CoreTests/NpcNameFinder/Test_NpcNameFinder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ public sealed class Test_NpcNameFinder : IDisposable
private readonly StringBuilder stringBuilder = new();

private readonly Graphics paint;
private readonly System.Drawing.Bitmap paintBitmap;
private readonly Bitmap paintBitmap;
private readonly Font font = new("Arial", 10);
private readonly SolidBrush brush = new(Color.White);
private readonly Pen whitePen = new(Color.White, 1);
Expand Down
39 changes: 35 additions & 4 deletions CoreTests/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ sealed class Program
{
private static Microsoft.Extensions.Logging.ILogger logger;

private const bool LogSelf = false;
private const bool LogOverall = false;
private const bool ShowOverlay = false;
private const int delay = 150;

Expand All @@ -31,6 +31,7 @@ public static void Main()
Test_NPCNameFinder();
//Test_Input();
//Test_CursorGrabber();
//Test_MinimapNodeFinder();
}

private static void Test_NPCNameFinder()
Expand All @@ -51,19 +52,19 @@ private static void Test_NPCNameFinder()

while (i < count)
{
if (LogSelf)
if (LogOverall)
timestamp = Stopwatch.GetTimestamp();

test.Execute();

if (LogSelf)
if (LogOverall)
sample[i] = Stopwatch.GetElapsedTime(timestamp).TotalMilliseconds;

i++;
Thread.Sleep(delay);
}

if (LogSelf)
if (LogOverall)
Log.Logger.Information($"sample: {count} | avg: {sample.Average(),0:0.00} | min: {sample.Min(),0:0.00} | max: {sample.Max(),0:0.00} | total: {sample.Sum()}");
}

Expand All @@ -90,5 +91,35 @@ private static void Test_CursorGrabber()
}
}

private static void Test_MinimapNodeFinder()
{
using Test_MinimapNodeFinder test = new(logger);

int count = 100;
int i = 0;

long timestamp = Stopwatch.GetTimestamp();
double[] sample = new double[count];

Log.Logger.Information($"running {count} samples...");

while (i < count)
{
if (LogOverall)
timestamp = Stopwatch.GetTimestamp();

test.Execute();

if (LogOverall)
sample[i] = Stopwatch.GetElapsedTime(timestamp).TotalMilliseconds;

i++;
Thread.Sleep(delay);
}

if (LogOverall)
Log.Logger.Information($"sample: {count} | avg: {sample.Average(),0:0.00} | min: {sample.Min(),0:0.00} | max: {sample.Max(),0:0.00} | total: {sample.Sum()}");
}

}
}

0 comments on commit 72a488c

Please sign in to comment.