Hello im begginer on C# and i have a bitmap with a image wich is updating every X seconds and i have another bitmap with a a model saved(As bitmap too), and i need to find on the main bitmap and get the [X, Y]
on my screen where this bitmap is found on my main bitmap, im using a Windows Forms C#, i already searched about it, and i try this code, the first answer but i no understand nothing about this code i dont know how to use, i need a method with return of [X, Y]
where is found this bitmap on my screen, here is a example what i need, that is what im trying and on my console even with the btm to found shows nothing.
private void Form1_Load(object sender, EventArgs e)
{
SearchBtm = new Bitmap(@"C:UsersghostDesktopTESTSearchBtm.png");
}
public void Reader_Tick(object sender, EventArgs e)
{
CurrentBtm = CaptureScreen();
var d = Find(CurrentBtm, SearchBtm);
Console.WriteLine(d);
}
public Point? Find(Bitmap haystack, Bitmap needle)
{
if (null == haystack || null == needle)
{
return null;
}
if (haystack.Width < needle.Width || haystack.Height < needle.Height)
{
return null;
}
var haystackArray = GetPixelArray(haystack);
var needleArray = GetPixelArray(needle);
foreach (var firstLineMatchPoint in FindMatch(haystackArray.Take(haystack.Height - needle.Height), needleArray[0]))
{
if (IsNeedlePresentAtLocation(haystackArray, needleArray, firstLineMatchPoint, 1))
{
return firstLineMatchPoint;
}
}
return null;
}
private int[][] GetPixelArray(Bitmap bitmap)
{
var result = new int[bitmap.Height][];
var bitmapData = bitmap.LockBits(new Rectangle(0, 0, bitmap.Width, bitmap.Height), ImageLockMode.ReadOnly,
PixelFormat.Format32bppArgb);
for (int y = 0; y < bitmap.Height; ++y)
{
result[y] = new int[bitmap.Width];
Marshal.Copy(bitmapData.Scan0 + y * bitmapData.Stride, result[y], 0, result[y].Length);
}
bitmap.UnlockBits(bitmapData);
return result;
}
private IEnumerable<Point> FindMatch(IEnumerable<int[]> haystackLines, int[] needleLine)
{
var y = 0;
foreach (var haystackLine in haystackLines)
{
for (int x = 0, n = haystackLine.Length - needleLine.Length; x < n; ++x)
{
if (ContainSameElements(haystackLine, x, needleLine, 0, needleLine.Length))
{
yield return new Point(x, y);
}
}
y += 1;
}
}
private bool ContainSameElements(int[] first, int firstStart, int[] second, int secondStart, int length)
{
for (int i = 0; i < length; ++i)
{
if (first[i + firstStart] != second[i + secondStart])
{
return false;
}
}
return true;
}
private bool IsNeedlePresentAtLocation(int[][] haystack, int[][] needle, Point point, int alreadyVerified)
{
//we already know that "alreadyVerified" lines already match, so skip them
for (int y = alreadyVerified; y < needle.Length; ++y)
{
if (!ContainSameElements(haystack[y + point.Y], point.X, needle[y], 0, needle.Length))
{
return false;
}
}
return true;
}
public Bitmap CaptureScreen()
{
//Getting ScreenBounds
var ScreenBounds = Screen.FromHandle(this.Handle).Bounds;
// Creating a new Bitmap
Bitmap CaptureBitmap = new Bitmap(ScreenBounds.Width, ScreenBounds.Height, PixelFormat.Format32bppArgb);
// Capture Rectangle
Rectangle CaptureRectangle = ScreenBounds;
// Graphics Object
Graphics CaptureGraphics = Graphics.FromImage(CaptureBitmap);
// Copying Image from The Screen
CaptureGraphics.CopyFromScreen(CaptureRectangle.Left, CaptureRectangle.Top, 0, 0, CaptureRectangle.Size);
// Return
return CaptureBitmap;
}
question from:
https://stackoverflow.com/questions/65912101/find-bitmap-on-another-bitmap-and-the-position