Jump to content

set pixel color


Recommended Posts

Okay I seem to be stuck. I've found all sorts of GDI screen capture and then pixel color set operations like BitmapSetPixel. What I can't seem to find, but what is alluded to, is some sort of DLL call to set the pixel color on a screen. I was trying to write a simple program that merrily marched across the screen inverting pixels. Please point me in the correct direction.

screen color invert v1a.au3

screen color invert v1a.au3

Link to comment
Share on other sites

Thanks. It uses GDI32.dll. Where can I find a list of GDI32.dll functions? (I searched the web but must be going to the wrong areas. http://source.winehq.org/WineAPI/gdi32.html shows LineTo as not documented :( ) I need to see if LineTo in GDI32.dll will accept a single pixel start and stop location. I'm kind of surprised that there is not another way of doing this. (I miss the old days of memory-mapped displays.)

Okay just found some info here: http://msdn.microsoft.com/en-us/library/dd145203%28v=VS.85%29.aspx

Edited by ahha
Link to comment
Share on other sites

Since that script was written a udf has been added to autoit for gdi funtions, look in the helpfile user defined function reference > GDIPlus management.

GDIPlusDispose - A modified version of GDIPlus that auto disposes of its own objects before shutdown of the Dll using the same function Syntax as the original.EzMySql UDF - Use MySql Databases with autoit with syntax similar to SQLite UDF.
Link to comment
Share on other sites

Thanks. Actually saw some of these, however, the closest seemed to be _GDIPlus_DrawImagePoints which handles an area and needs an image file and _GDIPlus_BitmapLockBits which looks like you can write to bits, however there's no example of writing - Ugh.

Link to comment
Share on other sites

This will allow you to set pixels on the primary screen. I have code to set pixels on any monitor, but this should get you started:

Func _PixelSetColor($iX,$iY,$iColor,$hWnd=0)
    Local $aRet,$iErr,$hDC
    If $hWnd And Not IsHWnd($hWnd) Then Return SetError(1,@error,False)

    $hDC=_WinAPI_GetWindowDC($hWnd)     ; 0 = DC of entire (primary) screen (desktop)
    If Not $hDC Then Return SetError(2,@error,False)

    ; Do the RGB->BGR conversion ('+' could have been used in place of BitOR)

    $aRet=DllCall ("gdi32.dll","dword","SetPixel","handle",$hDC,"int",$iX,"int",$iY,"dword",$iColor)
    If @error Then $iErr=@error


 If $iErr Then Return SetError(2,$iErr,False)

    ; Do the BGR->RGB conversion ('+' could have been used in place of BitOR)

 Return SetError(0,$iColor,True)
Edited by Ascend4nt
Link to comment
Share on other sites


Thanks will give it a try. Meanwhile I came up the attached code. Problem is that GDIPlus does not seem to be working correctly. Program attached tries to place a single pixel below some marker lines (so you can see single pixel placement). GDI works, but GDIPlus does not seem to work. See line 29 for problem. What am I doing wrong?


Link to comment
Share on other sites

Sorry, haven't messed with GDI+ yet. From what I understand, GDI+ is like a wrapper for GDI32, so basically there's some overhead in using GDI+ vs GDI32. Of course, there's added functionality in GDI+, but a lot of what people do with it is possible using GDI32 calls. (selecting pens, drawing pixels, lines, text, boxes, grabbing/manipulating bitmaps in native formats, etc). Just do what's simplest for what you need. In this case, I think I gave you that.

Link to comment
Share on other sites

Here is an example with a magnification window added.

#include <GDIPlus.au3>
#include <WinAPI.au3>
#include <GuiConstants.au3>
#include <WindowsConstants.au3>

Opt("GUIOnEventMode", 1) ;0=disabled, 1=OnEvent mode enabled

Global $GuiSizeX = 500, $GuiSizeY = 500

$hGui = GUICreate("GDIPlus Example", $GuiSizeX, $GuiSizeY)
GUISetOnEvent(-3, "_Quit")

;=== For _MAG() === 1 of 3
Global $hGUI2, $Width = 400, $Height = 300, $ZoomFactor = 10;0.4
$hGUI2 = GUICreate("Magnification x" & $ZoomFactor, $Width, $Height, 0, 400, $WS_OVERLAPPED)


$hGraphicGUI = _GDIPlus_GraphicsCreateFromHWND($hGui) ; Graphics of GUI
$hBMPBuff = _GDIPlus_BitmapCreateFromGraphics($GuiSizeX, $GuiSizeY, $hGraphicGUI) ; Memory bitmap
$hGraphic = _GDIPlus_ImageGetGraphicsContext($hBMPBuff) ; Graphics of memory bitmap

;Graphics here

_GDIPlus_GraphicsClear($hGraphic, 0xFFE8FFE8)
$hPen = _GDIPlus_PenCreate(0xFFFF0000)
_GDIPlus_GraphicsDrawLine($hGraphic, 90, 200, 100, 200, $hPen)
_GDIPlus_GraphicsDrawLine($hGraphic, 102, 200, 112, 200, $hPen)

DllCall($ghGDIPDll, "int", "GdipBitmapSetPixel", "hwnd", $hBMPBuff, "int", 101, "int", 201, "dword", 0xFF0000FF) ; 0xAARRGGBB

;End of graphics

GUIRegisterMsg(0xF, "MY_PAINT"); Register PAINT-Event 0x000F = $WM_PAINT (WindowsConstants.au3)
GUIRegisterMsg(0x85, "MY_PAINT") ; $WM_NCPAINT = 0x0085 (WindowsConstants.au3)Restore after Minimize.
_GDIPlus_GraphicsDrawImage($hGraphicGUI, $hBMPBuff, 0, 0) ; Draw memory bitmap to graphics of GUI

While 1
    ;=== For _MAG() === 2 of 3
    Local $aMousePos = MouseGetPos()
    _MAG($hGUI2, $aMousePos[0] - ($Width / $ZoomFactor) / 2, $aMousePos[1] - ($Height / $ZoomFactor) / 2)

;Func to redraw on PAINT MSG
Func MY_PAINT($hWnd, $msg, $wParam, $lParam)
    ; Check, if the GUI with the Graphic should be repainted
    _GDIPlus_GraphicsDrawImage($hGraphicGUI, $hBMPBuff, 0, 0)
EndFunc ;==>MY_PAINT

Func _Quit()
EndFunc ;==>_Quit

;3 of 3
; Modified from http://www.autoitscript.com/forum/index.php?s=&showtopic=53471&view=findpost&p=405045
Func _MAG($MyhWnd, $l, $t)
    Local $MyHDC = DllCall("user32.dll", "int", "GetDC", "hwnd", $MyhWnd); $MyHDC = _WinAPI_GetDC ($MyhWnd)
    If @error Then Return
    Local $DeskHDC = DllCall("user32.dll", "int", "GetDC", "hwnd", 0) ; $DeskHDC = _WinAPI_GetDC (0)
    If Not @error Then
        DllCall("gdi32.dll", "int", "StretchBlt", "int", $MyHDC[0], "int", 0, "int", 0, "int", $Width, "int", $Height, "int", _
                $DeskHDC[0], "int", $l, "int", $t, "int", $Width / $ZoomFactor, "int", $Height / $ZoomFactor, "long", $SRCCOPY)
        DllCall("user32.dll", "int", "ReleaseDC", "int", $DeskHDC[0], "hwnd", 0); _WinAPI_ReleaseDC ($DeskHDC, 0)
    DllCall("user32.dll", "int", "ReleaseDC", "int", $MyHDC[0], "hwnd", $MyhWnd); _WinAPI_ReleaseDC ($MyhWnd, $MyHDC)
EndFunc ;==>_MAG
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

  • Recently Browsing   0 members

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