Leo1906 Posted September 17, 2016 Posted September 17, 2016 (edited) Hello there, it's me aggain .. I just noticed that displaying a png GUI doesn't seem to work on Windows 7 ..? I recently used some code written by UEZ with some minor changes: expandcollapse popup#include <ButtonConstants.au3> #include <MsgBoxConstants.au3> #include <StructureConstants.au3> #include <WinAPIConstants.au3> #include <GDIPlus.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> $hMain = GUICreate("Parent", 400, 400, -1, -1, $WS_POPUP, BitOR($WS_EX_LAYERED,$WS_EX_TOOLWINDOW,$WS_EX_TOPMOST,$WS_EX_LAYERED)) _WinAPI_SetLayeredWindowAttributes($hMain, 0xABCDEF, 255) GUISetBkColor(0xABCDEF) GUISetState() _GDIPlus_Startup() Global Const $SC_DRAGMOVE = 0xF012 Global $iW, $iH, $hImage, $hBitmap, $hGUI $hImage = _GDIPlus_BitmapCreateFromFile("C:\Program Files (x86)\AutoIt3\Examples\GUI\Torus.png") $hBitmap = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hImage) $iW = _GDIPlus_ImageGetWidth($hImage) $iH = _GDIPlus_ImageGetHeight($hImage) $hGUI = GUICreate("", $iW, $iH, 0, 0, $WS_POPUP, $WS_EX_LAYERED) _WinAPI_SetParent($hGUI, $hMain) GUISetState() _WinAPI_BitmapDisplayTransparentInGUI($hBitmap, $hGUI) ;~ GUIRegisterMsg($WM_NCHITTEST, "WM_NCHITTEST") GUIRegisterMsg($WM_LBUTTONDOWN, "_WM_LBUTTONDOWN") Do Until GUIGetMsg() = $GUI_EVENT_CLOSE _WinAPI_DeleteObject($hBitmap) _GDIPlus_BitmapDispose($hImage) _GDIPlus_Shutdown() GUIDelete() Func _WinAPI_BitmapDisplayTransparentInGUI(ByRef $hHBitmap, ByRef $hGUI, $iOpacity = 0xFF, $bReleaseGDI = True) If Not BitAND(GUIGetStyle($hGUI)[1], $WS_EX_LAYERED) = $WS_EX_LAYERED Then Return SetError(1, 0, 0) Local $tDim = DllStructCreate($tagBITMAP) If Not _WinAPI_GetObject($hHBitmap, DllStructGetSize($tDim), DllStructGetPtr($tDim)) Then Return SetError(2, 0, 0) Local $tSize = DllStructCreate($tagSIZE), $tSource = DllStructCreate($tagPOINT), $tBlend = DllStructCreate($tagBLENDFUNCTION) Local Const $hScrDC = _WinAPI_GetDC(0), $hMemDC = _WinAPI_CreateCompatibleDC($hScrDC), $hOld = _WinAPI_SelectObject($hMemDC, $hHBitmap) $tSize.X = $tDim.bmWidth $tSize.Y = $tDim.bmHeight $tBlend.Alpha = $iOpacity $tBlend.Format = 1 _WinAPI_UpdateLayeredWindow($hGUI, $hScrDC, 0, DllStructGetPtr($tSize), $hMemDC, DllStructGetPtr($tSource), 0, DllStructGetPtr($tBlend), $ULW_ALPHA) _WinAPI_ReleaseDC(0, $hScrDC) _WinAPI_SelectObject($hMemDC, $hOld) _WinAPI_DeleteDC($hMemDC) If $bReleaseGDI Then _WinAPI_DeleteObject($hHBitmap) Return True EndFunc Func _WM_LBUTTONDOWN($hWnd, $iMsg, $wParam, $lParam) _SendMessage($hGUI, $WM_SYSCOMMAND, $SC_DRAGMOVE, 0) EndFunc ;==>_WM_LBUTTONDOWN Func WM_NCHITTEST($hWnd, $iMsg, $iwParam, $ilParam) If ($iMsg = $WM_NCHITTEST) Then Return $HTCAPTION EndFunc The png GUI is a child GUI, captured in the invisible borders of the parent GUI. I was using this code under Windows 10 Pro without any problems. Now I tried it with Windows 7 Ultimate (32 Bit - on VMWare) and Windows 7 Professional (32 Bit) (real laptop). Using any of those operating systems the code will be executed without errors but won't display anything .. (the path to the png was ofcourse adjusted ) I didn't test Windows 8 right now, because if have no running installation of it, but I will set it up on a VM soon .. Any ideas why this feature isn't available on all recent OS? Searching the forum didn't help .. Thanks for your help! Edit: just testet under Windows 8.1 x64 and the png is shown .. So it seems to be a Windows 7 only problem? Edit2: maybe something with _WinAPI_SetParent() ..? Because if this get's disabled the GUI is displayed (but not inside the other GUI ..) Edited September 17, 2016 by Leo1906
qwert Posted September 18, 2016 Posted September 18, 2016 I can't test things right now, but I did notice that this Program Files path is not valid on my Win7 Pro 32-bit: $hImage = _GDIPlus_BitmapCreateFromFile("C:\Program Files (x86)\AutoIt3\Examples\GUI\Torus.png") There is no "(x86)" portion.
AutoBert Posted September 18, 2016 Posted September 18, 2016 (edited) 4 hours ago, qwert said: I can't test things right now, but I did notice that this Program Files path is not valid on my Win7 Pro 32-bit To avoid such problem i use: Local $sAutoItPath = StringReplace(StringReplace(@AutoItExe,"_64",""), "autoit3.exe", "") ConsoleWrite($sAutoItPath & "Examples\GUI\msoobe.jpg" & @CRLF) Edited September 18, 2016 by AutoBert
Leo1906 Posted September 18, 2016 Author Posted September 18, 2016 (edited) Well .. I'm not stupid and as I said: I adjustet the path to point to the png. So that's definitly not the problem .. Edit: The same with non PNG-GUIs. Normal $WS_POPUP GUI won't be shown either. Example code: expandcollapse popup#include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <WinApi.au3> HotKeySet("^w", "_test") ; ctrl + w Global $numberCores = 7 Global $WorkAera = _GetWorkArea() Global $GUIFADE_MAXTRANS = 240 $dummy = GUICreate("", 255, $numberCores*50+140, @DesktopWidth-255, $WorkAera[3]-$numberCores*50-165, $WS_POPUP, BitOR($WS_EX_LAYERED,$WS_EX_TOPMOST)) ;~ _WinAPI_SetLayeredWindowAttributes($dummy, 0xABCDEF, 255) ;~ GUISetBkColor(0xABCDEF) GUISetState(@SW_SHOWNA) $MainGUIMainGUI = GUICreate("ThreadMain", 230, 130,10, 10, BitOR($WS_POPUP, $WS_SYSMENU, $WS_MINIMIZEBOX), $WS_EX_TOPMOST) GUISetBkColor(0x919191) ;~ WinSetTrans($MainGUIMainGUI, "", 240) $progressALL = GUICtrlCreateProgress(20, 70, 190, 20) _GuiRoundCorners($MainGUIMainGUI, 0, 0, 20, 20) _WinAPI_SetParent($MainGUIMainGUI, $dummy) GUISetState(@SW_SHOWNA, $MainGUIMainGUI) GUIRegisterMsg($WM_NCHITTEST, "WM_NCHITTEST") GUIRegisterMsg($WM_WINDOWPOSCHANGING, 'WM_WINDOWPOSCHANGING') _FadeInGUI($MainGUIMainGUI) While 1 Sleep(100) WEnd Func WM_WINDOWPOSCHANGING($hWnd, $iMsg, $wParam, $lParam) #forceref $iMsg, $wParam, $lParam Local $aWinGetPos = WinGetPos($hWnd) If @error Then Return $GUI_RUNDEFMSG Local $tWindowPos = DllStructCreate($tagWINDOWPOS, $lParam) ;~ If DLLStructGetData($tWindowPos, "X") < @DesktopWidth-235 Then ;~ DllStructSetData($tWindowPos, 'X', $aWinGetPos[0]) ;~ EndIf DllStructSetData($tWindowPos, 'Y', 10) Return $GUI_RUNDEFMSG EndFunc Func WM_NCHITTEST($hWnd, $iMsg, $iwParam, $ilParam) If ($iMsg = $WM_NCHITTEST) Then Return $HTCAPTION EndFunc Func _GetWorkArea() Local $Area[6] Local $StartRect = DllStructCreate("int[4]") Local $PStartRect = DllStructGetPtr($StartRect) DllCall("user32.dll", "int", "SystemParametersInfo", "int", 48, "int", 0, "ptr", $PStartRect, "int", 0) $Area[0] = DllStructGetData($StartRect,1,1) $Area[1] = DllStructGetData($StartRect,1,2) $Area[2] = DllStructGetData($StartRect,1,3) $Area[3] = DllStructGetData($StartRect,1,4) $Area[4] = $Area[2] - $Area[0] $Area[5] = $Area[3] - $Area[1] Return $Area EndFunc Func _GuiRoundCorners($h_win, $i_x1, $i_y1, $i_x3, $i_y3) Dim $pos, $ret, $ret2 $pos = WinGetPos($h_win) $ret = DllCall("gdi32.dll", "long", "CreateRoundRectRgn", "long", $i_x1, "long", $i_y1, "long", $pos[2], "long", $pos[3], "long", $i_x3, "long", $i_y3) If $ret[0] Then $ret2 = DllCall("user32.dll", "long", "SetWindowRgn", "hwnd", $h_win, "long", $ret[0], "int", 1) If $ret2[0] Then Return 1 Else Return 0 EndIf Else Return 0 EndIf EndFunc Func _FadeInGUI($hWnd) WinSetTrans($hWnd, "", 0) GUISetState(@SW_SHOW, $hWnd) For $i = 1 To $GUIFADE_MAXTRANS Step 0.05 WinSetTrans($hWnd, "", $i) Next EndFunc Func _FadeOutGUI($hWnd) For $i = $GUIFADE_MAXTRANS To 0 Step -0.05 WinSetTrans($hWnd, "", $i) Next GUISetState(@SW_HIDE, $hWnd) EndFunc Func _test() ;~ WinActivate($hChild) WinMove($dummy, "", 100, 100, 500, 500, 10) EndFunc This code works fine under Windows 8.1, Windows 10 and Windows Server 2012 (all three testet). The code does not work on Windows XP, Windows Vista and Windows 7 (tested) But where's the problem? MSDN says that minimum requirement for the SetParent function is Windows 2000, so that should work .. but it obvioulsy doesn't ..? Is the DllCall in the WinAPI.au3 not ok? Edited September 18, 2016 by Leo1906
UEZ Posted September 18, 2016 Posted September 18, 2016 What I found is that it depends on if Aero is enabled. Further coordinates for the image are not relative to the main GUI. Example: expandcollapse popup#include <ButtonConstants.au3> #include <MsgBoxConstants.au3> #include <StructureConstants.au3> #include <WinAPIConstants.au3> #include <GDIPlus.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> Global $tChkAero = DllStructCreate("int Enabled;") DllCall("DwmApi.Dll", "int", "DwmIsCompositionEnabled", "ptr", DllStructGetPtr($tChkAero)) If $tChkAero.Enabled Then DllCall("DwmApi.Dll", "int", "DwmEnableComposition", "uint", 0) $hMain = GUICreate("Parent", @DesktopWidth, @DesktopHeight, -1, -1, $WS_POPUP, BitOR($WS_EX_LAYERED, $WS_EX_TOPMOST)) ;~ GUISetBkColor(0xABCDEF) ;~ _WinAPI_SetLayeredWindowAttributes($hMain, 0xABCDEF, 255) _GDIPlus_Startup() Global Const $SC_DRAGMOVE = 0xF012 Global $iW, $iH, $hImage, $hBitmap, $hGUI $hImage = _GDIPlus_BitmapCreateFromFile("C:\Program Files (x86)\AutoIt3\Examples\GUI\Torus.png") $hBitmap = _GDIPlus_BitmapCreateHBITMAPFromBitmap($hImage) $iW = _GDIPlus_ImageGetWidth($hImage) $iH = _GDIPlus_ImageGetHeight($hImage) $aPos = WinGetPos($hMain) $hGUI = GUICreate("", $iW, $iH, 500, 300, $WS_POPUP, BitOR($WS_EX_LAYERED, $WS_EX_TOPMOST)) _WinAPI_SetParent($hGUI, $hMain) _WinAPI_BitmapDisplayTransparentInGUI($hBitmap, $hGUI) GUISetState(@SW_SHOWNA, $hMain) GUISetState(@SW_SHOW, $hGUI) ;~ GUIRegisterMsg($WM_NCHITTEST, "WM_NCHITTEST") GUIRegisterMsg($WM_LBUTTONDOWN, "_WM_LBUTTONDOWN") Do Until GUIGetMsg() = $GUI_EVENT_CLOSE _WinAPI_DeleteObject($hBitmap) _GDIPlus_BitmapDispose($hImage) _GDIPlus_Shutdown() GUIDelete() If $tChkAero.Enabled Then DllCall("DwmApi.Dll", "int", "DwmEnableComposition", "uint", 1) Func _WinAPI_BitmapDisplayTransparentInGUI(ByRef $hHBitmap, ByRef $hGUI, $iOpacity = 0xFF, $bReleaseGDI = True) If Not BitAND(GUIGetStyle($hGUI)[1], $WS_EX_LAYERED) = $WS_EX_LAYERED Then Return SetError(1, 0, 0) Local $tDim = DllStructCreate($tagBITMAP) If Not _WinAPI_GetObject($hHBitmap, DllStructGetSize($tDim), DllStructGetPtr($tDim)) Then Return SetError(2, 0, 0) Local $tSize = DllStructCreate($tagSIZE), $tSource = DllStructCreate($tagPOINT), $tBlend = DllStructCreate($tagBLENDFUNCTION) Local Const $hScrDC = _WinAPI_GetDC(0), $hMemDC = _WinAPI_CreateCompatibleDC($hScrDC), $hOld = _WinAPI_SelectObject($hMemDC, $hHBitmap) $tSize.X = $tDim.bmWidth $tSize.Y = $tDim.bmHeight $tBlend.Alpha = $iOpacity $tBlend.Format = 1 _WinAPI_UpdateLayeredWindow($hGUI, $hScrDC, 0, DllStructGetPtr($tSize), $hMemDC, DllStructGetPtr($tSource), 0, DllStructGetPtr($tBlend), $ULW_ALPHA) _WinAPI_ReleaseDC(0, $hScrDC) _WinAPI_SelectObject($hMemDC, $hOld) _WinAPI_DeleteDC($hMemDC) If $bReleaseGDI Then _WinAPI_DeleteObject($hHBitmap) Return True EndFunc Func _WM_LBUTTONDOWN($hWnd, $iMsg, $wParam, $lParam) _SendMessage($hGUI, $WM_SYSCOMMAND, $SC_DRAGMOVE, 0) EndFunc ;==>_WM_LBUTTONDOWN Func WM_NCHITTEST($hWnd, $iMsg, $iwParam, $ilParam) If ($iMsg = $WM_NCHITTEST) Then Return $HTCAPTION EndFunc The image cannot be moved. Please don't send me any personal message and ask for support! I will not reply! Selection of finest graphical examples at Codepen.io The own fart smells best! ✌Her 'sikim hıyar' diyene bir avuç tuz alıp koşma!¯\_(ツ)_/¯ ٩(●̮̮̃•̃)۶ ٩(-̮̮̃-̃)۶ૐ
Leo1906 Posted September 20, 2016 Author Posted September 20, 2016 Ok good to know. So this feature is basically not available for Windows below 8 .. Windows XP has no aero either, but it still doesn't work. And disabling the aero like you do know isn't a great of a deal I think ..
Recommended Posts
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 accountSign in
Already have an account? Sign in here.
Sign In Now