Jump to content

LoadImage and use CreateDIBSection to get pixels in it


Recommended Posts

Ok guys i have been trying to load an image into hBitmap and read all the pixels (colors) into an array so i have developed something which is incomplete because i havent find a chance to figure out something... Any help would be appreciated... Change the code below so that i can read the images from a file not (desktop coordinates) into an array...

here is my code which reads pixels (very fast) from a Context Device which belongs to desktop coords (not image coords)

#include <WinAPI.au3>
#include <GDIPlus.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <String.au3>
#include <misc.au3>
#include <ScreenCapture.au3>
#include <Array.au3>


HotKeySet("`", "GetPixels")
HotKeySet("{ESC}", "terminate")
HotKeySet("1", "ShowNewImage")

; Device contexts
Dim $hDC, $hCDC
Dim $aDIB, $hGraphic, $hBitmap
Dim $aiColorMatrix[1][1]

; single char size in pixels
Const $iX = 0
Const $iY = 0
Const $iWidth = 30
Const $iHeight = 30

Const $DEFAULT_TRESHOLD = 1
Const $iBitCount = 24
;Having selected the area of screen to duplicate, this function reads all the pixels within
; the rectangle. It put all the pixel in an array that don't match the color of the top left
; corner pixel. It assigns x, y values to each pixel. These values are relative to the centre
; pixel of the rectangle.
Func GetPixels()
    Local $row, $incremArray

    $tBMI = DllStructCreate($tagBITMAPINFO)
    DllStructSetData($tBMI, "Size", DllStructGetSize($tBMI) - 4)
    DllStructSetData($tBMI, "Width", $iWidth)
    DllStructSetData($tBMI, "Height", -$iHeight)
    DllStructSetData($tBMI, "Planes", 1)
    DllStructSetData($tBMI, "BitCount", $iBitCount)
    $hDC = _WinAPI_GetDC(0)
    $hCDC = _WinAPI_CreateCompatibleDC($hDC)
    
   ; Siao's bodacious creation
    $aDIB = DllCall('gdi32.dll', 'ptr', 'CreateDIBSection', _
            'ptr', 0, _
            'ptr', DllStructGetPtr($tBMI), _
            'uint', 1, _
            'ptr*', 0, _
            'ptr', 0, _
            'uint', 0)
    _WinAPI_SelectObject($hCDC, $aDIB[0])
    _WinAPI_BitBlt($hCDC, 0, 0, $iWidth, $iHeight, $hDC, $iX, $iY, $SRCCOPY)
    
;_ScreenCapture_Capture("deneme.jpg",$iX,$iY, $iX + $iWidth, $iY + $iHeight, False)
    $tBits = DllStructCreate('byte[' & $iWidth * $iHeight * $iBitCount / 8 & ']', $aDIB[4])
    $sHex = Hex(DllStructGetData($tBits, 1), 6)
   ;ConsoleWrite($sHex & @CRLF)
    $row = StringSplit(StringRegExpReplace($sHex, '(.){6}', '$0Chr(0)',0),'Chr(0)',1)
    ConsoleWrite("done getting array" & @CRLF)
;_ArrayDisplay($row)
    
    ReDim $aiColorMatrix[$iWidth][$iHeight]
    
    $pCtr = 0
    For $wCtr = 0 To $iWidth - 1
        For $hCtr = 0 To $iHeight - 1
            $pCtr = $pCtr + 1
            $aiColorMatrix[$wCtr][$hCtr] = $row[$pCtr]
        Next
    Next
    _ArrayDisplay($aiColorMatrix)
EndFunc  ;==>GetPixels

Func SetPixel($hDC, $iX, $iY, $iColor, $hDll = "gdi32.dll")
    $iColor = DllCall($hDll, "int", "SetPixel", "int", $hDC, "int", $iX, "int", $iY, "int", $iColor)
    If $iColor[0] = -1 Then Return SetError(1, 0, -1)
    Return $iColor[0]
EndFunc  ;==>_PixelGetColor_GetPixelRaw

Func ShowNewImage()
    $iTreshold = 1
    ConsoleWrite("Writing pixels" & @CRLF)
    
    For $i = 0 To $iWidth - 1
        For $j = 0 To $iHeight - 1
            SetPixel($hDC, $i,$j, $aiColorMatrix[$j][$i])
            #cs
            If $aiColorMatrix[$i][$j] < $iTreshold Then 
                SetPixel($hCDC, $i,$j, 0xFFFFFF)
            Else
                SetPixel($hCDC, $i,$j, 0x000000)
            EndIf
            #ce
            
        Next
    Next
    ConsoleWrite("Creating GUI to display image" & @CRLF)
    $hGUI = GUICreate("", $iWidth + 1, $iHeight + 1,$iX, $iY,$WS_POPUP)
    
    GUISetState()

   ; Initialize GDI+ library
    _GDIPlus_Startup ()

   ; Draw bitmap to GUI
    $hBitmap = _GDIPlus_BitmapCreateFromHBITMAP ($aDIB[0])
    $hGraphic = _GDIPlus_GraphicsCreateFromHWND ($hGUI)
    
    _GDIPlus_GraphicsDrawImage ($hGraphic, $hBitmap, 0, 0)


   ; Loop until user exits
    Do
    Until GUIGetMsg() = $GUI_EVENT_CLOSE
    
    Finalize()
    
    GUIDelete($hGUI)
    
EndFunc

Func Finalize()
; Clean up resources
    _GDIPlus_GraphicsDispose ($hGraphic)
    _GDIPlus_ImageDispose ($hBitmap)
    _WinAPI_DeleteObject($aDIB[0])
    _WinAPI_DeleteDC($hCDC)
    _WinAPI_ReleaseDC(0, $hDC)
   ; Shut down GDI+ library
    _GDIPlus_ShutDown ()
EndFunc

Func terminate()
    Exit
EndFunc

While (1)
    Sleep(10)
WEnd

Your mission (Summary) : Change the code so that it reads pixels from an image rather than the screen coordinates (cdc)

Link to comment
Share on other sites

Here is old original code from Larry (he deleted his posts):

getpixel_from_external_bmp.au3

$szPicFile = ".\larry.bmp"
$x = 62
$y = 82

Const $GWL_HINSTANCE = -6
Const $IMAGE_BITMAP = 0
Const $LR_LOADFROMFILE = 0x0010 

Dim $hInst, $hBmp, $hMemDC, $hwnd

Opt("WinWaitDelay",1)
AutoItWinSetTitle("qqqqqq")
$hwnd = WinGetHandle("qqqqqq")

$hInst = DllCall("user32.dll","int","GetWindowLong","hWnd",$hwnd, "int",$GWL_HINSTANCE) 
$hInst = $hInst[0]

$hBmp = DllCall("user32.dll","hwnd","LoadImage","hwnd",$hInst,"str",$szPicFile,"int",$IMAGE_BITMAP, _
        "int",0,"int",0,"int",$LR_LOADFROMFILE)
$hBmp = $hBmp[0]

$hMemDC = DllCall("gdi32.dll", "int", "CreateCompatibleDC", "int", 0)
$hMemDC = $hMemDC[0]

DllCall("gdi32.dll", "hwnd", "SelectObject", "int", $hMemDC, "hwnd", $hBmp)

$ret = DLLCall("gdi32.dll","int","GetPixel","int",$hMemDC,"int",$x,"int",$y)
$ret = Hex( $ret[0], 6)
$ret = StringRight($ret,2) & StringMid($ret,3,2) & StringLeft($ret,2)

DllCall("gdi32.dll", "int", "DeleteDC", "hwnd", $hMemDC)
DllCall("gdi32.dll", "int", "DeleteObject", "hwnd", $hBmp)

MsgBox(4096,"",$ret)
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...