Pixelsearch on background inactive window

Get help with using AutoHotkey (v1.1 and older) and its commands and hotkeys
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Pixelsearch on background inactive window

28 Oct 2022, 17:00

Hello, i am using a controlclick script for a totally unoticed script action, but now i need it to pixelsearch so im forced to use winactivate for it to work, efectively disrupting my pc activies.

So the ideal scenario would be Pixelsearch on non visible, non active window without disrupting mouse or keyboard constant action, i could also deal with visible window if mandatory (while maintinaining, coord, pixel, client ) but, non active is a must.

I understand a library is need, in this post the user ''noname'' suggested something interesting, tho im afraid it doesn't achieve the ''unactive'' state that i need.

viewtopic.php?t=34447

This other user had the same issue: ( worked in visible unactive, but he was forced to use /coord pixel, screen )

viewtopic.php?t=65548

Already tried the function ''inactivepixelsearch'' that this user included on his library

viewtopic.php?f=6&t=73094

I guess no luck on the sintax for me on that one
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 02:07

Depending on the application my ImageScanClass works for programs in the background, as long as they are not minimized, may also not work for some directx games/programs

example usage

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

scan := New ShinsImageScanClass("TitleHere") ;create an instance of the class
Return

F1::
if (scan.Image("image.png",0,x,y)) {
	msgbox % "Image was found at " x ", " y
} else {
	msgbox % "Image not found"
}
Return
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 04:15

Spawnova wrote:
29 Oct 2022, 02:07
Depending on the application my ImageScanClass works for programs in the background, as long as they are not minimized, may also not work for some directx games/programs

example usage

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

scan := New ShinsImageScanClass("TitleHere") ;create an instance of the class
Return

F1::
if (scan.Image("image.png",0,x,y)) {
	msgbox % "Image was found at " x ", " y
} else {
	msgbox % "Image not found"
}
Return
Sadly i need pixel detection, but thank you
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 04:40

Check the github link, it handles multiple different pixel methods as well =P
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 05:33

Spawnova wrote:
29 Oct 2022, 04:40
Check the github link, it handles multiple different pixel methods as well =P
Firstly thanks for your great work !

I assume your code works both on unactive windows & backgrounded as you mentioned, then i guess this is the function i need:

PixelRegion(color, x1, y1, w, h, variance=0, byref returnX=0, byref returnY=0, scanDir:=0)

Is there a way to specify the desired window + use coordmode, pixel, client? i asumme it will otherwise search the screen & backgrounds, but i move the desired window around, making these coords change.
If so, could i get an example code?
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 05:55

It already scans in client space, you can specify window space if you need to scan the title bar for some reason as well, moving the window around will not change the coordinates

here is an example that scans the region from 50,50 to 150,150 for a red pixel in client space, regardless of where the window is on the screen.

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

scan := New ShinsImageScanClass("TitleHere") ;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
Return

f1::

if (scan.PixelRegion(0xFF0000,50,50,100,100,0,x,y)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
} else {
	msgbox % "No red pixel found"
}

Return
Keep in mind while it does scan windows in the background, visible or not, it will not scan a minimized window
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 06:23

Spawnova wrote:
29 Oct 2022, 05:55
It already scans in client space, you can specify window space if you need to scan the title bar for some reason as well, moving the window around will not change the coordinates

here is an example that scans the region from 50,50 to 150,150 for a red pixel in client space, regardless of where the window is on the screen.

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

scan := New ShinsImageScanClass("TitleHere") ;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
Return

f1::

if (scan.PixelRegion(0xFF0000,50,50,100,100,0,x,y)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
} else {
	msgbox % "No red pixel found"
}

Return
Keep in mind while it does scan windows in the background, visible or not, it will not scan a minimized window
Not sure i explained myself accurately here hehe:
I need to scan a small area in a single window where a pixel will change at some point, and it will be detected using a loop, if i scan my screen (which i think is what your script does), many other pixels of the same color will be found, and if i reduce the region scan coords screenwise, other same color pixel may still get in the way eventually. im surely in the wrong here, feel free to enlight me with the obvious solution :crazy:
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 06:48

It does not scan the desktop, when you supply a target title as the first parameter when creating the class it will only scan that window, regardless of whether it is visible or not (though not minimized), it will not include any portion of any other window.

here is the same code but with a loop

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
scan := New ShinsImageScanClass("TitleHere") 
Return

;f1 enables / disables the scan loop
f1::
toggle := !toggle
settimer,scanLoop,(toggle ? 50 : "off") ;if enabled set a timer to check every 50 ms
return


scanLoop:
if (scan.PixelRegion(0xFF0000,50,50,100,100,0,x,y)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
	;pixel was found, do stuff here
} else {
	msgbox % "No red pixel found"
	;pixel was not found do stuff here
}
Return
Make sure you replace "TitleHere" with your target window title
You can get coordinates for scanning by opening "Window Spy" that comes with ahk, by default it uses client space so use the Client: x, y coordinates to determine your scanning positions / rectangles
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 07:29

Oh whoops, should have been a percent sign there to use expression mode
settimer,scanLoop,% (toggle ? 50 : "off")

Also keep in mind my class uses coordinates as x, y, w, h not x1, y1, x2, y2, also colors are assumed to be in RGB format
here is the updated script to account for the error

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

scan := New ShinsImageScanClass("TitleHere") ;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
Return

;f1 enabled / disabled the scan loop
f1::
toggle := !toggle
settimer,scanLoop,% (toggle ? 50 : "off") ;if enabled set a timer to check every 50 ms
return


scanLoop:
;alternatively if you just want to scan one pixel you could use 
/*
if (scan.PixelPosition(0xBB706F, 258,109,3)) {
	;code
}
*/
if (scan.PixelRegion(0xBB706F, 258,109,10,10,3,x,y)) { ;this will search at 258,109 to 268,119 for a red pixel
	msgbox % "Red pixel found at " x ", " y
	;pixel was found, so stuff here
} else {
	msgbox % "No red pixel found"
	;pixel was not found do stuff here
}
Return


;save a screenshot of the target window, this is what the program sees
f2::
scan.SaveImage("TargetImage.png")
return
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 07:39

Spawnova wrote:
29 Oct 2022, 06:48
It does not scan the desktop, when you supply a target title as the first parameter when creating the class it will only scan that window, regardless of whether it is visible or not (though not minimized), it will not include any portion of any other window.

here is the same code but with a loop

Code: Select all

#include ShinsImageScanClass.ahk ;include the library

;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
scan := New ShinsImageScanClass("TitleHere") 
Return

;f1 enables / disables the scan loop
f1::
toggle := !toggle
settimer,scanLoop,(toggle ? 50 : "off") ;if enabled set a timer to check every 50 ms
return


scanLoop:
if (scan.PixelRegion(0xFF0000,50,50,100,100,0,x,y)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
	;pixel was found, do stuff here
} else {
	msgbox % "No red pixel found"
	;pixel was not found do stuff here
}
Return
Make sure you replace "TitleHere" with your target window title
You can get coordinates for scanning by opening "Window Spy" that comes with ahk, by default it uses client space so use the Client: x, y coordinates to determine your scanning positions / rectangles

My regular pixelsearch which finds the color succesfully (3 to color variation is a must)

Code: Select all

x::
WinActivate, (Arrow - 2)

Coordmode, Pixel, Client
Pixelsearch, Px, Py, 258, 109, 258, 109, 0xBB706F, 3, fast
if (ErrorLevel = 0) {

Msgbox, found
}
Else {
msgbox, pixel not found
}

The code i build off your indications does not find the pixel

Code: Select all

SetKeyDelay, 0, 50

#include ShinsImageScanClass.ahk ;include the library

;create an instance of the class, replace TitleHere with the title of the target window, or an ahk title alternative such as ahk_id etc..
scan := New ShinsImageScanClass("(Arrow - 2)") 
Return

f1::
if (scan.PixelRegion(0xBB706F,258,109,258,109,3)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
}
else {
	msgbox % "No red pixel found"

}
Also tried the single pixel version with no success, it returns ''no red pixel found''

Code: Select all

f1::
if (scan.PixelRegion(0xBB706F,258,109,3)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "Red pixel found at " x ", " y
}
else {
	msgbox % "No red pixel found"

}
No sure abour RGB, i capture them using this code

Code: Select all

MouseGetPos, unikX, unikY
   PixelGetColor, unico, %unikX%, %unikY%
Maybe convert if it isn't rbg? how so

Yes i tried to alter the coord order to 258,258,109,109
What am i doing wrong?
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 07:57

by default that gets the color in BGR you can use MouseGetPos, unikX, unikY
PixelGetColor, unico, %unikX%, %unikY%, RGB
instead
your color BB706F can just be swapped around to rgb as well 6F70BB

if you are only scanning 1 pixel then use this instead

Code: Select all

f1::
if (scan.PixelPosition(0x6F70BB,258,109,3)) { ;if 0x6F70BB is found at 258,109 with a variance of 3, return true
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 08:13

Spawnova wrote:
29 Oct 2022, 07:57
by default that gets the color in BGR you can use MouseGetPos, unikX, unikY
PixelGetColor, unico, %unikX%, %unikY%, RGB
instead
your color BB706F can just be swapped around to rgb as well 6F70BB

if you are only scanning 1 pixel then use this instead

Code: Select all

f1::
if (scan.PixelPosition(0x6F70BB,258,109,3)) { ;if 0x6F70BB is found at 258,109 with a variance of 3, return true
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return
First of all, you are the man, it worked !!!
I also like to stick to the ranged version of it, because i also need to scan for region, so i usually just dupe the coords to find a single pixel while in a region search function

So this code worked

Code: Select all

f1::
if (scan.PixelPosition(0x6F70BB,258,109,3)) { ;if 0x6F70BB is found at 258,109 with a variance of 3, return true
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return
However the region one doesn't

Code: Select all

F3::

if (scan.PixelRegion(0x6F70BB,258,258,109,109,3,x,y)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 08:30

Those coordinates are in x1,y1,x2,y2 format, my class uses x,y,w,h
so you would instead type 258,109,w,h

Code: Select all

F3::
if (scan.PixelRegion(0x6F70BB,258,109,1,1,3,x,y)) { ;x=258 y=109 w=1 h=1, increase width and height to increase search range
	msgbox % "pixel found at pos " x ", " y
}
else {
	msgbox % "No pixel found"
}
return
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 08:59

Spawnova wrote:
29 Oct 2022, 08:30
Those coordinates are in x1,y1,x2,y2 format, my class uses x,y,w,h
so you would instead type 258,109,w,h

Code: Select all

F3::
if (scan.PixelRegion(0x6F70BB,258,109,1,1,3,x,y)) { ;x=258 y=109 w=1 h=1, increase width and height to increase search range
	msgbox % "pixel found at pos " x ", " y
}
else {
	msgbox % "No pixel found"
}
return



Gotcha, so if i were to scan lets say from 258,109 to 292 119 how would my final script look like?

Maybe adding the extra coords like this?

Code: Select all

F3::
if (scan.PixelRegion(0x6F70BB,258,109,34,10,3,x,y)) { ;x=258 y=109 w=1 h=1, increase width and height to increase search range
	msgbox % "pixel found at pos " x ", " y
}
else {
	msgbox % "No pixel found"
}
return

Btw to scan for a single pixel while maintaning the regionish function gives no pixel found on the following cases:

Code: Select all

F3::

if (scan.PixelRegion(0x6F70BB,258,109,w,h,3)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return

Code: Select all

F3::

if (scan.PixelRegion(0x6F70BB,258,109,0,0,3)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
return

Code: Select all

F3::

if (scan.PixelRegion(0x6F70BB,258,109,1,1,3)) { ;this will search at 50,50 to 150,150 for a red pixel
	msgbox % "pixel found"
}
else {
	msgbox % "No pixel found"
}
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 09:08

if (scan.PixelRegion(0x6F70BB,258,109,34,10,3,x,y)) Yes this is correct, it will scan the region from 258,109 > 292,119 (258+34=292),(109+10=119)

Your other problem lies here scan.PixelRegion(0x6F70BB,258,109,0,0,3)
0 width or 0 height will always result in a fail since there would be no pixels to search, minimum is 1
scan.PixelRegion(0x6F70BB,258,109,1,1,3)
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 09:21

Spawnova wrote:
29 Oct 2022, 09:08
if (scan.PixelRegion(0x6F70BB,258,109,34,10,3,x,y)) Yes this is correct, it will scan the region from 258,109 > 292,119 (258+34=292),(109+10=119)

Your other problem lies here scan.PixelRegion(0x6F70BB,258,109,0,0,3)
0 width or 0 height will always result in a fail since there would be no pixels to search, minimum is 1
scan.PixelRegion(0x6F70BB,258,109,1,1,3)
Got it working as well, really man thanks for your great input and time! You made a man very happy today :)
Also in case of negative coord, lets say 146 Y849 to 1288 Y177

Code: Select all

if (scan.PixelRegion(0x6F70BB,146,849,1142,-672,3,x,y))
- symbol will do ?
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 09:41

Yup it does support negative width and height, that will work :thumbup:
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

29 Oct 2022, 10:38

Spawnova wrote:
29 Oct 2022, 09:41
Yup it does support negative width and height, that will work :thumbup:
Awesome! I i'll try to make this one my last question! And thanks for everything really.

If i were to compile both (library and custom script) how can i make the #include part work ?
#include ShinsImageScanClass.ahk ;include the library

Because obviously renaming it to #include ShinsImageScanClass.exe ; won't do the trick :D
User avatar
Spawnova
Posts: 557
Joined: 08 Jul 2015, 00:12
Contact:

Re: Pixelsearch on background inactive window

29 Oct 2022, 10:44

When you compile an autohotkey script into an executable it automatically includes libraries that you have #included
You will only need the executable at that point, that's only for code though, other resources like images/audio will need to be present after
bobelyk
Posts: 64
Joined: 26 Jun 2021, 16:55

Re: Pixelsearch on background inactive window

08 Nov 2022, 12:21

Spawnova wrote:
29 Oct 2022, 10:44
When you compile an autohotkey script into an executable it automatically includes libraries that you have #included
You will only need the executable at that point, that's only for code though, other resources like images/audio will need to be present after
You script is being really usefull, i was wondering if the coords can be stored on a var to be randomized later
This is your script

Code: Select all

#include ShinsImageScanClass.ahk ;include the library
if WinExist("mywindow")
{
scan := New ShinsImageScanClass("mywindow") 
if (scan.PixelRegion(0x6D6EB6,243,99,280,403,3)) {     ;;;; I want to store the found x & y to a var
ControlClick, x1113 y294, mywindow,,,, NA
}
else {
	Sleep 300
}
Can something like this be added?

Code: Select all

Pixelsearch, Px, Py, 381, 15, 1684, 883, 0x55FDFD, 1, fast
if (ErrorLevel = 0) {
    Random, Rx , 0 , 3
    Random, Ry , 0 , 3
 Coordmode, Mouse, Client  
    Mousemove, Px+Rx, Py+Ry, 0
Sleep 100
}
Else {


}


Return to “Ask for Help (v1)”

Who is online

Users browsing this forum: Google [Bot], peter_ahk, Spawnova and 338 guests