Что нового

PixelGetColor - поиск пикселя с файла (.PNG)

c.rauf.1986

Новичок
Сообщения
27
Репутация
0
Здравствуйте.Есть вопрос по PixelGetColor.
уже третий день ищу не нашел подходящий вариант.
Суть в том что хочу Поискать цвет по изображению (.PNG).
нашел 3-4 вариант но они не подходят.

Код:
$ColorForSearch = '12851766' ; ищем цвет

for $x=0 to 370
    for $y=0 to 48
        ... 
        if $sColor = $ColorForSearch then
            ConsoleWrite('x= ' & $x & 'y= ' & $y )
    next
next



Добавлено:
Сообщение автоматически объединено:

есть много вариантов но все они выдает результат мин через 25-30 секунд
сам придумал вариант но как то не работает может кто не будь поможет

Код:
#include <GDIPlus.au3>
#include <GDIPlusConstants.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>


$h_Form1 = GUICreate("Captcha", 370, 48, 500, 500)
$o_Preview = ObjCreate("Shell.Explorer.2")
$h_PreviewCtrl = GUICtrlCreateObj($o_Preview, 0, 0, 370, 48)
$o_Preview.Navigate(@ScriptDir &'\captcha1.png')
$o_Preview.document.body.style.margin = 0
$o_Preview.document.body.scroll = "no"
GUISetState(@SW_SHOW)

Sleep(1000)

$coordStart  = PixelSearch(0, 0, @DesktopWidth, @DesktopHeight,'0xF3F2E7')

If Not @error Then
	MsgBox(0,'Warnin','Color found in x= ' & $coordStart[0] & 'y= ' & $coordStart[1])
	Sleep(500)
	$coord = PixelSearch(0, 0, @DesktopWidth, @DesktopHeight,'0xF3F2E7')
	Switch $coord
		Case @error to 1
		MouseMove($coord[0],$coord[1])
	EndSwitch	
EndIf

ConsoleWrite('1')

While 1
	$nMsg = GUIGetMsg()
	Switch $nMsg
		Case $GUI_EVENT_CLOSE
			Exit
	EndSwitch
WEnd
 

WSWR

AutoIT Гуру
Сообщения
941
Репутация
365
c.rauf.1986

Вот вариант, хотя скорее всего тут можно и попроще, т.к. изначально такие методы лучше использовать для больших картинок...
Код:
#include <Array.au3>
#include <GDIPlus.au3>

$Color = 'CF322A' ; цвет без '0x'

$aMatrix = _DesktopMatrix1($Color, @ScriptDir & '\1.png')

_ArrayDisplay($aMatrix, $Color)

Func _DesktopMatrix1($sColor, $sPatch)
	Local $hBitmap2, $tMap, $bData2, $Width, $Height
	_GDIPlus_Startup()
	$hBitmap2 = _GDIPlus_BitmapCreateFromFile($sPatch)

	$Width = _GDIPlus_ImageGetWidth($hBitmap2) - 1
	$Height = _GDIPlus_ImageGetHeight($hBitmap2) - 1
	$tMap = _GDIPlus_BitmapLockBits($hBitmap2, 0, 0, $Width, $Height, $GDIP_ILMREAD, $GDIP_PXF32ARGB)
	$bData2 = DllStructGetData(DllStructCreate('byte[' & ($Width * $Height * 4) & ']', DllStructGetData($tMap, 'Scan0')), 1)

	_GDIPlus_BitmapUnlockBits($hBitmap2, $tMap)
	_GDIPlus_BitmapDispose($hBitmap2)
	_GDIPlus_Shutdown()

	$bData2 = '######FF' & StringTrimLeft($bData2, 2)
	$sColor = StringRegExpReplace($sColor, '(.{2})(.{2})(.{2})', '\3\2\1')

	If StringInStr($bData2, $sColor) Then

		$aTemp = StringRegExp($bData2, '(\S{6})FF', 3)

		$aiResult = _ArrayFindAll($aTemp, $sColor)
		If $aiResult <> -1 Then
			Dim $uArray[UBound($aiResult)][2] = [[0]]
			For $i = 0 To UBound($aiResult) - 1
				$y = Floor($aiResult[$i] / ($Width))
				$x = ($aiResult[$i] - $y * $Width)
				$uArray[$i][0] = $x
				$uArray[$i][1] = $y
			Next
		Else
			Return SetError(1, 0, 0)
		EndIf
		Return $uArray
	Else
		Return SetError(1, 0, 0)
	EndIf
EndFunc   ;==>_DesktopMatrix


Также можно поискать по форуму примеры работы функции
Код:
_GDIPlus_BitmapGetPixel
 
Автор
C

c.rauf.1986

Новичок
Сообщения
27
Репутация
0
спасибо за ответ.Но ваш код иногда ошибается.Я проверил проблема не в том что не правильно распознает а в том что в конце - или + его путает.не правильно делает что - или +.
например распознает цвет красный в белом листе но координаты надо высчитать с лева или справа.вот в этом проблема.

выложил изображение для проверки можете проверить сами.(Просьба)
 

Garrett

Модератор
Локальный модератор
Сообщения
3,999
Репутация
967
Код:
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

HotKeySet('{F1}', '_GoSearch')

Opt('PixelCoordMode', 2)

$h_Form1 = GUICreate("Captcha: для поиска нажмите F1", 370, 48, 500, 500)
$o_Preview = ObjCreate("Shell.Explorer.2")
$h_PreviewCtrl = GUICtrlCreateObj($o_Preview, 0, 0, 370, 48)
;~ $o_Preview.Navigate(@ScriptDir &'\c1.png') ; 57x32
;~ $o_Preview.Navigate(@ScriptDir &'\c2.png') ; 271x32
$o_Preview.Navigate(@ScriptDir &'\c3.png') ; 311x10
$o_Preview.document.body.style.margin = 0
$o_Preview.document.body.scroll = "no"
GUISetState(@SW_SHOW)

While 1
    $nMsg = GUIGetMsg()
    Switch $nMsg
        Case $GUI_EVENT_CLOSE
            Exit
    EndSwitch
WEnd

Func _GoSearch()
	$a_Coord = _SearchPixel(370, 48, '0xC41A36') ; крассная точка
	If @error Then
		MsgBox(16, @ScriptName,'Цвет не найден :(')
	Else	
		MsgBox(16, @ScriptName, 'Цвет найден :)' & @CRLF & 'X: ' & $a_Coord[0] &' x Y: '& $a_Coord[1])
	EndIf
EndFunc

Func _SearchPixel($W, $Y, $i_Color)
	
	$a_Coord = PixelSearch(0, 0, $W, $Y, $i_Color, 73, 1, WinGetHandle('[active]'))
	If @error Then
		Return SetError(1, 0, 0)
	EndIf
	
	Return SetError(0, 0, $a_Coord)
EndFunc
 
Автор
C

c.rauf.1986

Новичок
Сообщения
27
Репутация
0
Garrett Спасибо за ответ.

но если можно то хочу чтобы найти цвет не открывая .png на GUI
Короче код который написал WSWR подходит и даже супер. то что надо.
проверил я этот код.Все хорошо.Находит координат Y а проблема с X-ом.






Добавлено:
Сообщение автоматически объединено:

WSWR

можете сказать как определить X Y с этого результата?
по каким принципам код который вы написали распознает координаты?

и еще какая функция изменяет результат №1 на №2

результат №1

зтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуяязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтууязтуязтуязтуязтуязтуязтуяззтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязтуязту

результат №2

######FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FFE7F2F3FF
 

WSWR

AutoIT Гуру
Сообщения
941
Репутация
365
c.rauf.1986
Да, там была ошибка

Так вроде правильно:
Код:
#include <Array.au3>
#include <GDIPlus.au3>

$Color = 'A96351' ; цвет без '0x'

$aMatrix = _DesktopMatrix1($Color, @ScriptDir & '\captcha11.png')

_ArrayDisplay($aMatrix, $Color)

Func _DesktopMatrix1($sColor, $sPatch)
	Local $hBmp, $hBitmap2, $tMap, $bData2, $Width, $Height

	_GDIPlus_Startup()
	$hBitmap2 = _GDIPlus_BitmapCreateFromFile($sPatch)

	$Width = _GDIPlus_ImageGetWidth($hBitmap2)
	$Height = _GDIPlus_ImageGetHeight($hBitmap2)
	$tMap = _GDIPlus_BitmapLockBits($hBitmap2, 0, 0, $Width, $Height, $GDIP_ILMREAD, $GDIP_PXF32ARGB)
	$bData2 = DllStructGetData(DllStructCreate('byte[' & ($Width * $Height * 4) & ']', DllStructGetData($tMap, 'Scan0')), 1)

	_GDIPlus_BitmapUnlockBits($hBitmap2, $tMap)
	_GDIPlus_BitmapDispose($hBitmap2)
	_GDIPlus_Shutdown()

	$bData2 = '######FF' & StringTrimLeft($bData2, 2)
	$sColor = StringRegExpReplace($sColor, '(.{2})(.{2})(.{2})', '\3\2\1')

	If StringInStr($bData2, $sColor) Then

		$aTemp = StringRegExp($bData2, '(\S{6})FF', 3)

		$aiResult = _ArrayFindAll($aTemp, $sColor)
		If $aiResult <> -1 Then

			Dim $uArray[UBound($aiResult)][2] = [[0]]
			For $i = 0 To UBound($aiResult) - 1
				$uArray[$i][0] = Mod($aiResult[$i], $Width) - 1
				$uArray[$i][1] = Ceiling($aiResult[$i] / $Width) - 1
			Next
		Else
			Return SetError(1, 0, 0)
		EndIf
		Return $uArray
	Else
		Return SetError(1, 0, 0)
	EndIf
EndFunc   ;==>_DesktopMatrix1
 
Автор
C

c.rauf.1986

Новичок
Сообщения
27
Репутация
0
WSWR
вопрос 2:
Вы Можете подробно описать только эту часть
не как не понимаю как использовать в других функциях.

Код:
DllStructGetData
DllStructCreate

именно это строку не как не могу понять как она работает с каким принципом определяет каждую пиксель и их цвет.

Код:
$bData2 = DllStructGetData(DllStructCreate('byte[' & ($Width * $Height * 4) & ']', DllStructGetData($tMap, 'Scan0')), 1)



Добавлено:
Сообщение автоматически объединено:

я искал но не нашел подробное описание об

Код:
DllStructGetData
DllStructCreate
DllCallbackGetPtr
DllStructGetSize
.
если у вас есть ссылка на какой то пост можете дать это тоже пригодится.
 

madmasles

Модератор
Глобальный модератор
Сообщения
7,790
Репутация
2,323
c.rauf.1986,
Предупреждение За нарушение общих правил (пункт В.4):
Не лепите несколько вопросов разной тематики в один пост. По типу "Ребят, а ещё такой вопрос...". Каждый вопрос в свою тему.


С уважением, ваш Глобальный модератор.
 
Верх