Jump to content

Recommended Posts

Posted

Hello,

I want to create a semi transparency "hole" in a picture, i tried _GDIPlus_ColorMatrixCreateTranslate but it applies to the entire image (cf image 1) and i want only a zone defined by a mask (cf image 2)

 

Image 1

image.png.eaf469f2b622adb03a7d1e841512adfb.png

 

Image 2

image.png.ecda675a57d1fab1d16fd583a51e42c9.png

Is it possible with GDIPlus functions ?

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)

Not sure what do you mean by "hole". I see an ellipse (or a part) of a certain color drawn over the background image with some transparency.

Edited by Andreik
Posted (edited)

I made the second image on paint to illustrate what i want.

I want to make a part of image semi transparent to see background image behind.

 

Sorry i didn't say that in my script, there are 2 images, one is the background (floor) and the second is the wall i want to render semi transparent

There is the script and images :

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

GUISetState()
$gui = GUICreate("Test", 580, 400)
GUISetBkColor(0xFF0000, $gui)

_GDIPlus_Startup()

$hBmp1 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\bg_classroom1.png")
$hBmp2 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_front.png")

$hAttribute = _GDIPlus_ImageAttributesCreate()
$matrix = _GDIPlus_ColorMatrixCreateTranslate(0, 0, 0, -0.5)
_GDIPlus_ImageAttributesSetColorMatrix($hAttribute, 0, True, $matrix)

$dims1 = _GDIPlus_ImageGetDimension($hBmp1)
$dims2 = _GDIPlus_ImageGetDimension($hBmp2)

GUISetState()

Local $hGraphics = _GDIPlus_GraphicsCreateFromHWND($gui)
_GDIPlus_GraphicsSetInterpolationMode($hGraphics, $GDIP_INTERPOLATIONMODE_NearestNeighbor)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp1, 0, 0, $dims1[0], $dims1[1], -420, -240, $dims1[0]*4, $dims1[1]*4)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp2, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4)


; Loop until user exits
Do
Until GUIGetMsg() = $GUI_EVENT_CLOSE

_GDIPlus_ImageAttributesDispose($hAttribute)
_GDIPlus_ImageDispose($hBmp2)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()

 

bg_classroom1.png

wall_front.png

Edited by TommyDDR
_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted

Here is an example but I used some hard coded value just to demonstrate the concept.

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

GUISetState()
$gui = GUICreate("Test", 580, 400)
GUISetBkColor(0xFF0000, $gui)

_GDIPlus_Startup()

$hBmp1 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\bg_classroom1.png")
$hBmp2 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_front.png")
$hBrush = _GDIPlus_BrushCreateSolid(0x30000000)

$hAttribute = _GDIPlus_ImageAttributesCreate()
$matrix = _GDIPlus_ColorMatrixCreateTranslate(0, 0, 0, -0.5)
_GDIPlus_ImageAttributesSetColorMatrix($hAttribute, 0, True, $matrix)

$dims1 = _GDIPlus_ImageGetDimension($hBmp1)
$dims2 = _GDIPlus_ImageGetDimension($hBmp2)

GUISetState()

Local $hGraphics = _GDIPlus_GraphicsCreateFromHWND($gui)
_GDIPlus_GraphicsSetInterpolationMode($hGraphics, $GDIP_INTERPOLATIONMODE_NearestNeighbor)

$hPath = _GDIPlus_PathCreate()
_GDIPlus_PathAddArc($hPath, 140, 50, 300, 300, 225, 145)
_GDIPlus_PathAddEllipse($hPath, 140, 50, 300, 300)
_GDIPlus_PathAddArc($hPath, 140, 50, 300, 300, 44, 145)

_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp1, 0, 0, $dims1[0], $dims1[1], -420, -240, $dims1[0]*4, $dims1[1]*4)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp2, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4)
_GDIPlus_GraphicsFillPath($hGraphics, $hPath, $hBrush)

; Loop until user exits
Do
Until GUIGetMsg() = $GUI_EVENT_CLOSE

_GDIPlus_BrushDispose($hBrush)
_GDIPlus_PathDispose($hPath)
_GDIPlus_ImageAttributesDispose($hAttribute)
_GDIPlus_ImageDispose($hBmp2)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()

Basically your mask needs to be a path and then you can fill the path with the desired color of a certain transparency when it's drawn to graphics.

Posted

Thanks for your answer, but I don't see any transparency in the result, just a gray circle. I want to see the floor through the wall.

image.png.dd2bc2048b0cd60f27a11dfae897b641.png

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)

With a lot of digging, i found a workaround with _GDIPlus_GraphicsSetClipRegion()

I draw the whole wall transparency, then i draw a solid wall on top of it without the region defined by a path

But i want a solution with a mask defined by another image :'( (maybe there isn't such a solution with GDIPlus)

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

GUISetState()
$gui = GUICreate("Test", 580, 400)
GUISetBkColor(0xFF0000, $gui)

_GDIPlus_Startup()

$hBmp1 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\bg_classroom1.png")
$hBmp2 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_front.png")

$hAttribute = _GDIPlus_ImageAttributesCreate()
$matrix = _GDIPlus_ColorMatrixCreateTranslate(0, 0, 0, -0.5)
_GDIPlus_ImageAttributesSetColorMatrix($hAttribute, 0, True, $matrix)

$dims1 = _GDIPlus_ImageGetDimension($hBmp1)
$dims2 = _GDIPlus_ImageGetDimension($hBmp2)

GUISetState()

Local $hPath = _GDIPlus_PathCreate()
_GDIPlus_PathAddEllipse($hPath, 50, 10, 80, 80)
Local $hRegion = _GDIPlus_RegionCreate()
_GDIPlus_RegionCombinePath($hRegion, $hPath, 4)

Local $hBmp3 = _GDIPlus_BitmapCreateFromScan0($dims2[0], $dims2[1])
Local $hGraphics3 = _GDIPlus_ImageGetGraphicsContext($hBmp3)
_GDIPlus_GraphicsSetClipRegion($hGraphics3, $hRegion)
_GDIPlus_GraphicsSetInterpolationMode($hGraphics3, $GDIP_INTERPOLATIONMODE_NearestNeighbor)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics3, $hBmp2, 0, 0, $dims2[0], $dims2[1], 0, 0, $dims2[0], $dims2[1])
_GDIPlus_GraphicsDispose($hGraphics3)

Local $hGraphics = _GDIPlus_GraphicsCreateFromHWND($gui)

_GDIPlus_GraphicsSetInterpolationMode($hGraphics, $GDIP_INTERPOLATIONMODE_NearestNeighbor)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp1, 0, 0, $dims1[0], $dims1[1], -420, -240, $dims1[0]*4, $dims1[1]*4)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp2, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4, $hAttribute)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp3, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4)

Do
Until GUIGetMsg() = $GUI_EVENT_CLOSE

_GDIPlus_ImageAttributesDispose($hAttribute)
_GDIPlus_ImageDispose($hBmp2)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()

image.png.8340a754f59c4b529b2fc85a2d5fb4eb.png

Edited by TommyDDR
_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)

I understand now what you mean. The paths are created from basic primitive shapes so the complexity of creating a path from an image it really depends by the complexity of that image. I think it will be a challenge to do it with GDI+ but it should be possible. I suppose that mask have different levels of transparency also.

Edited by Andreik
Posted

not necessarily different transparencies (even if that would be perfect), at least one mask of this type (green = we add transparency)

 

Mask exemple : bus_mask.png.e26f225d87b9b63c1456da70e143e878.png

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)

I wrote a function to combine a bitmap with a mask and set the transparency accordingly with the color of the mask.

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

GUISetState()
$gui = GUICreate("Test", 580, 400)
GUISetBkColor(0xFF0000, $gui)

_GDIPlus_Startup()

$hBmp1 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\bg_classroom1.png")
$hBmp2 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_front.png")
$hBmp3 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_mask.png")

SetBitmapMask($hBmp2, $hBmp3)

$dims1 = _GDIPlus_ImageGetDimension($hBmp1)
$dims2 = _GDIPlus_ImageGetDimension($hBmp2)

GUISetState()

Local $hGraphics = _GDIPlus_GraphicsCreateFromHWND($gui)

_GDIPlus_GraphicsSetInterpolationMode($hGraphics, $GDIP_INTERPOLATIONMODE_NearestNeighbor)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp1, 0, 0, $dims1[0], $dims1[1], -420, -240, $dims1[0]*4, $dims1[1]*4)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp2, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4)

Do
Until GUIGetMsg() = $GUI_EVENT_CLOSE

_GDIPlus_ImageDispose($hBmp1)
_GDIPlus_ImageDispose($hBmp2)
_GDIPlus_ImageDispose($hBmp3)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()

Func SetBitmapMask($hBitmap, $hMask,  $iMaskColor = 0xFF000000, $iTransparency = 0xBB000000)
    Local $aDim = _GDIPlus_ImageGetDimension($hBitmap)
    Local $tBitmap = _GDIPlus_BitmapLockBits($hBitmap, 0, 0, $aDim[0], $aDim[1], BitOR($GDIP_ILMWRITE, $GDIP_ILMREAD), $GDIP_PXF32ARGB)
    Local $tMask = _GDIPlus_BitmapLockBits($hMask, 0, 0, $aDim[0], $aDim[1], BitOR($GDIP_ILMWRITE, $GDIP_ILMREAD), $GDIP_PXF32ARGB)
    Local $sCode = '0x8B4C24048B7C24088B74240C8B5424108B5C2414AD39D075068B0731D8890783C704E2F0C21400'
    Local $dCode = Binary($sCode)
    Local $iCode = BinaryLen($dCode)
    Local $tCode = DllStructCreate('byte Code[' & $iCode & ']')
    $tCode.Code = $dCode
    Local $aCall = DllCallAddress('int', DllStructGetPtr($tCode), 'int', $aDim[0] * $aDim[1], 'ptr', $tBitmap.Scan0, 'ptr', $tMask.Scan0, 'int', $iMaskColor, 'int', $iTransparency)
    _GDIPlus_BitmapUnlockBits($hBitmap, $tBitmap)
    _GDIPlus_BitmapUnlockBits($hMask, $tMask)
    Return $aCall[0]
EndFunc

If I have some time tomorrow I might rewrite the function to fit all levels of transparency for the mask.

 

 

 

Edited by Andreik
Posted

Obviously I couldn't wait until tomorrow, so here it's the function that apply the alpha channel of the mask to a bitmap. The color of the mask is not important at all, it can be even a combination of multiple colors (as you can see below).

 

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

GUISetState()
$gui = GUICreate("Test", 580, 400)
GUISetBkColor(0xFF0000, $gui)

_GDIPlus_Startup()

$hBmp1 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\bg_classroom1.png")
$hBmp2 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_front.png")
$hBmp3 = _GDIPlus_ImageLoadFromFile(@ScriptDir & "\wall_mask.png")

SetBitmapMask($hBmp2, $hBmp3)

$dims1 = _GDIPlus_ImageGetDimension($hBmp1)
$dims2 = _GDIPlus_ImageGetDimension($hBmp2)

GUISetState()

Local $hGraphics = _GDIPlus_GraphicsCreateFromHWND($gui)

_GDIPlus_GraphicsSetInterpolationMode($hGraphics, $GDIP_INTERPOLATIONMODE_NearestNeighbor)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp1, 0, 0, $dims1[0], $dims1[1], -420, -240, $dims1[0]*4, $dims1[1]*4)
_GDIPlus_GraphicsDrawImageRectRect($hGraphics, $hBmp2, 0, 0, $dims2[0], $dims2[1], -50, -10, $dims2[0]*4, $dims2[1]*4)

Do
Until GUIGetMsg() = $GUI_EVENT_CLOSE

_GDIPlus_ImageDispose($hBmp1)
_GDIPlus_ImageDispose($hBmp2)
_GDIPlus_ImageDispose($hBmp3)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()

Func SetBitmapMask($hBitmap, $hMask)
    Local $aDim = _GDIPlus_ImageGetDimension($hBitmap)
    Local $tBitmap = _GDIPlus_BitmapLockBits($hBitmap, 0, 0, $aDim[0], $aDim[1], BitOR($GDIP_ILMWRITE, $GDIP_ILMREAD), $GDIP_PXF32ARGB)
    Local $tMask = _GDIPlus_BitmapLockBits($hMask, 0, 0, $aDim[0], $aDim[1], BitOR($GDIP_ILMWRITE, $GDIP_ILMREAD), $GDIP_PXF32ARGB)
    Local $sCode = '0x8B4C24048B7C24088B74240CAD25000000FF8B1F81E3FFFFFF0009D8890783C704E2E9C20C00'
    Local $dCode = Binary($sCode)
    Local $iCode = BinaryLen($dCode)
    Local $tCode = DllStructCreate('byte Code[' & $iCode & ']')
    $tCode.Code = $dCode
    Local $aCall = DllCallAddress('int', DllStructGetPtr($tCode), 'int', $aDim[0] * $aDim[1], 'ptr', $tBitmap.Scan0, 'ptr', $tMask.Scan0)
    _GDIPlus_BitmapUnlockBits($hBitmap, $tBitmap)
    _GDIPlus_BitmapUnlockBits($hMask, $tMask)
    Return $aCall[0]
EndFunc

For this example use the classroom floor and the wall from the previous example and this mask.

wall_mask.png

Posted

I tried your script, but it fails at :

Local $aCall = DllCallAddress('int', DllStructGetPtr($tCode), 'int', $aDim[0] * $aDim[1], 'ptr', $tBitmap.Scan0, 'ptr', $tMask.Scan0)

AutoIt3.exe ended.rc:-1073741819

What is this adress ? why a fixed adress ? why not a classic DllCall with a function name ?

Thanks

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)

Have you tried my examples or what did you changed in script? The bitmap and the mask need to be bitmaps of same size. Also the function doesn't work if your run the 64bit version of AutoIt. So what is your case?

3 hours ago, TommyDDR said:

What is this adress ? why a fixed adress ? why not a classic DllCall with a function name ?

It's a call to a function written in asm. You have the opcodes in the function.

With first mask and with second mask.

image.thumb.png.e7c007d21ef6d4d424d2058432054b4e.png

You have attached a zip with the resources and both examples.

Mask blending.zip

Edited by Andreik
Posted

Ok, i was in 64bits, thank you ! :)

That's exactly what i want !

image.png.f0b74c59516c545ed0da6db9531a0655.png

I know it's a bit complicated, but... can you explain this ? :D

Let's try myself :

mov ecx, esp + 0x4  -> move 1st parameter into ecx register (size of image in pixels)
mov edi, esp + 0x8  -> move 2nd parameter into ecx register (image scan0 ptr)
mov esi, esp + 0xc  -> move 3rd parameter into ecx register (mask scan0 ptr)
lods eax, esi       -> idk what this line is really doing
and eax,0xFF000000  -> logical and between eax and 0xFF000000 -> get the alpha channel of the mask
mov ebx, edi        -> move edi (image pixels) into ebx -> get ARGB data
and ebx, 0xFFFFFF   -> get the RGB channels                  -> (if i understand, we lose the original transparency, so the mask need to have it to keep it)
or eax, ebx         -> logical or between eax and ebx -> mix alpha chanel into original image
mov edi, eax        -> move eax (mix between 2 images) onto edi -> replace original pixel with new one
add edi, 0x4        -> add 4 to edi -> move ptr to the next pixel
loop 0xc            -> loop to line 0xc (loop to loads line) (i don't understand how to stop looping)
ret 0xc             -> return 0xc ? (i don't understand the 0xc)

 

Where do you use ecx to find out where the end is ?

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted (edited)
43 minutes ago, TommyDDR said:

Ok, i was in 64bits, thank you ! :)

That's exactly what i want !

image.png.f0b74c59516c545ed0da6db9531a0655.png

I know it's a bit complicated, but... can you explain this ? :D

Let's try myself :

mov ecx, esp + 0x4  -> move 1st parameter into ecx register (size of image in pixels)
mov edi, esp + 0x8  -> move 2nd parameter into ecx register (image scan0 ptr)
mov esi, esp + 0xc  -> move 3rd parameter into ecx register (mask scan0 ptr)
lods eax, esi       -> idk what this line is really doing
and eax,0xFF000000  -> logical and between eax and 0xFF000000 -> get the alpha channel of the mask
mov ebx, edi        -> move edi (image pixels) into ebx -> get ARGB data
and ebx, 0xFFFFFF   -> get the RGB channels                  -> (if i understand, we lose the original transparency, so the mask need to have it to keep it)
or eax, ebx         -> logical or between eax and ebx -> mix alpha chanel into original image
mov edi, eax        -> move eax (mix between 2 images) onto edi -> replace original pixel with new one
add edi, 0x4        -> add 4 to edi -> move ptr to the next pixel
loop 0xc            -> loop to line 0xc (loop to loads line) (i don't understand how to stop looping)
ret 0xc             -> return 0xc ? (i don't understand the 0xc)

 

Where do you use ecx to find out where the end is ?

Here is a better version that supports 64bit also. The algorithm for x64 is the same as above but using the x64 calling convention and maybe other registers. The code is explained below:

mov ecx, [esp+4]            ; Move first parameter of DllCallAddress() to ECX, so ECX = number of pixels in the image = width * height
mov edi [esp+8]             ; Move second parameter of DllCallAddress() to EDI, the pointer to the structure that holds the pixels of the bitmap
mov esi, [esp+12]           ; Move third parameter of DllCallAddress() to ESI, the pointer to the structure that holds the pixels of the mask
mov ebx, 0xffffff           ; EBX = 0xFFFFFF - this will be used as a mask later
nextPixel:  
lodsd                       ; Load a DWORD from [ESI] and then increment the ESI with 4 (the size of a DWORD)
and eax, 0xff000000         ; Preserve the higher byte of eax
and [edi], ebx              ; Preserve the lower 3 bytes of the DWORD pointed by the EDI
or  [edi], eax              ; Combine the transparency of the mask with the bitmap data
add edi, 4                  ; Increment EDI with 4 (the size of a DWORD) - basically move the index to keep in line with the next pixel
loop nextPixel              ; If ECX > 0 then decrement ECX and jump to nextPixel
ret 12                      ; Return and pop 12 bytes from stack

This is the code for x64:

push rsi                            ; RSI and RBX are nonvolatile registers 
push rbx                            ; so they must be saved and restored by a function that uses them
mov rsi, r8                         ; move in RSI the pointer of the structure that holds the pixels of the mask
mov ebx, 0xffffff                   ; EBX = 0xFFFFFF - a mask used later to preserve the lower bytes of the bitmap pixel
nextPixel:                          
    lodsd                           ; Load in EAX a DWORD from the memory pointed by RSI
    and eax, 0xff000000             ; Preserve the transparency of the mask
    and [rdx], ebx                  ; Preserve the color of the bitmap
    or [rdx], eax                   ; Combine the bitmap color with mask transparency
    add rdx, 4                      ; Increase RDX with 4 (the size of a DWORD) to keep in line with next bitmap pixel
loop nextPixel                      ; If ECX > 0 Then jump to nextPixel and decrement ECX
pop rbx                             ; Restore the saved registers
pop rsi
ret                                 ; Return from function

 

Edited by Andreik
Posted (edited)
41 minutes ago, UEZ said:

@Andreik very good work.

 

Here another version

 

Didn't know about. I reinvented the wheel. :mad2:

At least my code is shorter and faster. :lol:

Edited by Andreik
Posted

Amazing, thanks for all your responses ! ❤️

UEZ's always watching us 🧐

I can now try to adapt it to my final goal (there is an exemple really not optimized before i read your answer)

test.zip

 

I'll post it here when i'll sucess it !

 

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).
Posted

Few month ago, i was looking for a tutorial for SDL in AutoIt but never found any, do you have some ?

_GUIRegisterMsg (Register more than 1 time the same Msg), _Resize_Window (GUICtrlSetResizing for children windows), _GUICtrlSetOnHover (Link a function when mouse go on, left, clic down, clic up, on a control), _InputHeure (Create an input for hour contain), _GUICtrlCalendar (Make a complete calendar), _GUICtrlCreateGraphic3D (Create a 3D graph), _ArrayEx.au3 (Array management), _GUIXViewEx.au3 (List/Tree View management).

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...