AHKv2-Gdip icon indicating copy to clipboard operation
AHKv2-Gdip copied to clipboard

Fallback when hBitmap is device dependent

Open iseahound opened this issue 3 years ago • 5 comments

Main Change:

  • Check if the hBitmap has a pointer to the pixel data. If it does, it's a device independent bitmap created by CreateDIBSection, and this function is valid. If not, it is a device dependent bitmap, so call the built in method. I am not aware of any transparency in device dependent bitmaps.

Housekeeping

  • Remove unnecessary ByRef.
  • Reformat comments + references.
  • Remove some commas.
  • Remove unused lines in BitmapData. The function doesn't care if width, height, or PixelFormat are set, as they are set in other places.

iseahound avatar Oct 17 '21 02:10 iseahound

I'll look at this later

but the commas aren't unnecessary, they are for performance to chain lines together into one expression:

https://www.autohotkey.com/docs/Variables.htm#CommaPerf

mmikeww avatar Oct 18 '21 04:10 mmikeww

For assignment expressions only, and those are kept.

iseahound avatar Oct 19 '21 19:10 iseahound

oh ok, i thought it was for all expressions

mmikeww avatar Oct 19 '21 20:10 mmikeww

References:

https://github.com/iseahound/ImagePut/blob/0c1110cd0aad14625c1814eed464f703ac4df0ad/ImagePut%20(for%20v1).ahk#L1015

https://github.com/iseahound/ImagePut/blob/0c1110cd0aad14625c1814eed464f703ac4df0ad/ImagePut%20(for%20v1).ahk#L1738

I made the discovery that the obm returned by select object is a stock bitmap that can never be leaked. I can update the two functions to be even more in line with what I have.

Also, if you’d need anything for conversion to v2 feel free to copy paste from my projects.

iseahound avatar Oct 19 '21 21:10 iseahound

For testing the aforementioned change I called GetDC(0) then called GetCurrentObject() with a value of 7 to retrieve the hbitmap, and GetObject() to return the pBits. I noticed it was 0 and realized that it was a device dependent bitmap.

sdc := DllCall("GetDC", "ptr", WinExist("A"), "ptr")
h := DllCall("GetCurrentObject", "ptr", sdc, "uint", 7)
VarSetCapacity(dib, size := 64+5*A_PtrSize) ; sizeof(DIBSECTION) = 84, 104
DllCall("GetObject", "ptr", h, "int", size, "ptr", &dib)
MsgBox % width  := NumGet(dib, 4, "uint")
MsgBox % height := NumGet(dib, 8, "uint")
MsgBox % bpp    := NumGet(dib, 18, "ushort")
MsgBox % pBits := NumGet(dib, A_PtrSize = 4 ? 20:24, "ptr")  ; bmBits
MsgBox % size  := NumGet(dib, A_PtrSize = 4 ? 44:52, "uint") ; biSizeImage

I also just call ImagePutWindow() to see what's happening.

iseahound avatar Oct 19 '21 21:10 iseahound