The
lexikos methodology for preventing redraw is significantly more reliable and user-friendly (no flickering) than the other solutions. Thanks.
However, I had a significant amount of trouble implementing it into a real-world application because the WM_SETREDRAW messages introduced some unexpected side effects.
From the "just in case you care" department, I've updated the example/test script from the
Maximize window anomaly post to include the lexikos methodology and modified it so that it can (OK, "should be able to be") used in any script with only a few modifications. Who knows? It might be useful to someone someday.
Code: Select all
/*
Preface: Do not change the order of the GUI options
Instructions:
Test 1
------
Comment out the "-SysMenu" option (may already commented out). When the
window is shown, the Maximize button is showing but is not enabled.
Run the script. Press F11 to maximize the window. Press F11 again to
restore the window. The contents of the web browser control should be
visible in all cases.
Test 2
------
Uncomment the "-SysMenu" option. When the window is shown, everything on
the title bar is hidden. Because the -MaximizeBox option is also used, the
MaximizeBox is not showing _and_ it is not enabled.
Run the script. Press F11 to maximize the window. Press F11 again to
restore the window. The contents of the web browser control should be
visible in all cases.
Test 3 (if you get bored)
------
Uncomment all GUI options including -Sysmenu. Delete or comment out the
-MaximizeBox option.
Run the script. Press F11 to maximize the window. Press F11 again to
restore the window. The contents of the web browser control should be
visible in all cases.
Because the -SysMenu option is used, no buttons on the title bar are
visible. However, since the -MaximizeBox option was removed, the window
still has the WS_MAXIMIZEBOX style and and so the window operates the same
as if the Maximize button were showing. The script uses the standard "gui
Maximize" command without any of the before and after code.
*/
#NoEnv
#SingleInstance Force
;-- Window style flags
WS_MAXIMIZEBOX :=0x10000
WS_SIZEBOX :=0x40000
WS_SYSMENU :=0x80000
;-- Messages
WM_SETREDRAW :=0xB
;-- Build GUI
gui -DPIScale +hWndhWindow +Resize -MaximizeBox ;-SysMenu
GroupAdd MyWindowGroup,ahk_id %hWindow%
gui Margin,0,0
gui Add,ActiveX,w600 r26 +hWndhWB vMyWB,Shell.Explorer
gui Add,Text,h20 vMyText,Text control - 20 pixels high
MyWB.Navigate("https://www.google.com/")
;-- Show it
gui Show
return
GUISize:
$Maximized:=(A_EventInfo=2) ? True:False
GUIControl Move,MyWB,% "w" . A_GUIWidth . " h" . A_GUIHeight-20
GUIControl Move,MyText,% "y" . A_GUIHeight-20
return
GUIClose:
GUIEscape:
ExitApp
#IfWinActive ahk_group MyWindowGroup
F11::
if $Maximized
gui Restore
else
{
WinGet l_Style,Style,ahk_id %hWindow%
if (l_Style & WS_MAXIMIZEBOX)
gui Maximize
else
{
;-- Add the WS_MAXIMIZEBOX style to the window. Without the
; WS_MAXIMIZEBOX style, the OS will not size the window correctly when
; the Maximize command is executed.
;
; There are two undesired side effects of adding the WS_MAXIMIZEBOX
; style. First of all, the WS_MAXIMIZEBOX style cannot exist without
; the WS_SYSMENU style and so the WS_SYSMENU style is automatically
; added when the WS_MAXIMIZEBOX style is added if it wasn't already
; included. Also, this command causes the content of the web browser
; control to disappear in most cases. No, I don't know why.
;
; To counteract the "web browser control disappears" effect of adding
; the WS_MAXIMIZEBOX style, the WM_SETREDRAW message is sent to the
; window before (to disable redraw) and after (to enable redraw)
; adding the WS_MAXIMIZEBOX style.
;
; There is one undesired side effect of sending the WM_SETREDRAW
; message to disable redrawing. This message removes the window from
; the list of visible windows. This is the same as if the window were
; hidden. To ensure that the window is visible for all AutoHotkey
; commands, DetectHiddenWindows is temporarily set On.
;
$DetectHiddenWindows:=A_DetectHiddenWindows
DetectHiddenWindows On
SendMessage WM_SETREDRAW,False,,,ahk_id %hWindow%
gui +MaximizeBox
SendMessage WM_SETREDRAW,True,,,ahk_id %hWindow%
;-- Maximize the window. This command triggers the GUISize routine
; which in turn, resizes the web browser control. The web browser
; control is automatically redrawn because of the "Move" commands.
gui Maximize
;-- Remove the WS_MAXIMIZEBOX style that was added earlier. This command
; causes the content of the web browser control to disappear (yes,
; again) in most cases. To counteract this effect, WM_SETREDRAW is
; sent before and after.
SendMessage WM_SETREDRAW,False,,,ahk_id %hWindow%
gui -MaximizeBox
SendMessage WM_SETREDRAW,True,,,ahk_id %hWindow%
;-- If needed, remove the WS_SYSMENU style
if not (l_Style & WS_SYSMENU)
{
SendMessage WM_SETREDRAW,False,,,ahk_id %hWindow%
gui -SysMenu
SendMessage WM_SETREDRAW,True,,,ahk_id %hWindow%
}
;-- Reapply the styles and redraw the frame if needed
; Note: This step is needed if the Desktop Window Manager is not
; enabled. Without it, changes to the title bar won't correctly
; redraw to reflect the changes made.
DllCall("SetWindowPos","ptr",hWindow,"ptr",0,"int",0,"int",0,"int",0,"int",0
,"int",0x27) ; SWP_FRAMECHANGED | SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER
;-- Restore DetectHiddenWindows
DetectHiddenWindows %$DetectHiddenWindows%
}
}
;-- Sleep added to reduce the number of F11 calls that can be made consecutively
Sleep 150
return
#IfWinActive