Sign in to follow this  
Followers 0
wraithdu

GUIRegisterMsg Help File Remarks

13 posts in this topic

Can anyone explain this bit of the help file remarks a bit better?

Warning: blocking of running user functions which executes window messages with commands such as "Msgbox()" can lead to unexpected behavior, the return to the system should be as fast as possible !!!

It sounds like whomever wrote it might not be a native English speaker, so some clarification would be great. If you can give the technical details why and under what circumstances this is bad it would be very helpful.

Share this post


Link to post
Share on other sites



#2 ·  Posted (edited)

Can anyone explain this bit of the help file remarks a bit better?

It sounds like whomever wrote it might not be a native English speaker, so some clarification would be great. If you can give the technical details why and under what circumstances this is bad it would be very helpful.

Sounds perfectly clear to me, and I am not a native english speaker: Functions that respond to messages registered with GUIRegisterMsg() should not take too long,or wait more than a fraction of second for user input before returning. Doing this will cause unexpected behavior,as lots of conditions used by Windows to determine it's actions will have changed, like mouse position, windows' states, keyboard input, etc.

Edited by danielkza

Share this post


Link to post
Share on other sites

That's how I interpreted it, but the more I read it, the more I wasn't sure :)

So taking that into account, can anyone explain how in the GUIRegisterMsg help file example clicking either button multiple times creates multiple messageboxes, even though the MsgBox() sits smack in the middle of the WM_COMMAND function? I would have thought (as is warned) that the first messagebox would block any more messages from being received until it was dismissed.

Share this post


Link to post
Share on other sites

That's how I interpreted it, but the more I read it, the more I wasn't sure :)

So taking that into account, can anyone explain how in the GUIRegisterMsg help file example clicking either button multiple times creates multiple messageboxes, even though the MsgBox() sits smack in the middle of the WM_COMMAND function? I would have thought (as is warned) that the first messagebox would block any more messages from being received until it was dismissed.

The Helpfile example has as only function show this MsgBox().As it's only goal is to demonstrate the function's use and show a simple message,doing this will not interfere with any other program functionality,but it should be changed anyway to avoid confusion.

Share this post


Link to post
Share on other sites

I understand that, but what I don't understand is how it can spawn multiple msgboxes. Try it! Click a button, then move the window out of the way (don't close it), then click another button. You can keep going as long as you want. That shouldn't be possible, but it is.

Share this post


Link to post
Share on other sites

I understand that, but what I don't understand is how it can spawn multiple msgboxes. Try it! Click a button, then move the window out of the way (don't close it), then click another button. You can keep going as long as you want. That shouldn't be possible, but it is.

This happens because I SUPPOSE that when you use MsgBox(), the script continuous execution routine is stopped. But the Window Procedure,that responds to windows messages, is not called by autoit,but by Windows wich is obviously not asleep. Could a Dev please confirm this?

Share this post


Link to post
Share on other sites

The fact that you don't understand how it works is proof of the warning. It says it may cause unexpected behavior and the behavior you are seeing is unexpected. So what further explanation do you need to drive the point home?

Share this post


Link to post
Share on other sites

I'm not doubting or questioning the warning. I'm trying to understand why the help file example works the way it does. It seems to clearly violate the warning it just pointed out! My problem with that is I know what should happen, but it doesn't happen that way.

To confuse the issue more, if you distill the example script down and remove the ownerdrawn stuff only, then it works as expected...all script commands are frozen until you click through the message box. Which is correct - the script shouldn't process any more WM_COMMAND messages until you release the one that's stuck by the MsgBox().

I'm just trying to learn here, not argue.

Share this post


Link to post
Share on other sites

The warning points out the results might be unpredictable. The results are unpredictable compared to your expectations, the code does not violate the warning.

Messages handled by GUIRegisterMsg() are handled asynchronously. That means you have more than one MY_WM_COMMAND() running at a time if you press the button multiple times. Also, MY_WM_COMMAND() is designed to prevent AutoIt's default event handling, so events $nButton and $nButton2 are never fired. So, when you remove MY_WM_COMMAND() from the sequence, $nButton and $nButton2 are fired once again, and since messages are processed synchronously in that case, the script blocks.

Share this post


Link to post
Share on other sites

#10 ·  Posted (edited)

But I didn't remove MY_WM_COMMAND(). Here' -

; *******************************************************
; Example - Create an ownerdrawn/colored button
; *******************************************************

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <ButtonConstants.au3>

Example()

Func Example()
    Local Const $BS_OWNERDRAW = 0x0000000B
    Local $hGUI, $nButton, $nButton2, $GUIMsg

    $hGUI = GUICreate("My Ownerdrawn Created Button", 300, 200)

    $nButton = GUICtrlCreateButton("Normal Button", 90, 50, 120, 30)

    $nButton2 = GUICtrlCreateButton("Normal Button", 90, 110, 120, 30)

    GUIRegisterMsg($WM_COMMAND, "MY_WM_COMMAND")

    GUISetState()

    While 1
        $GUIMsg = GUIGetMsg()
        
        Switch $GUIMsg
            Case $GUI_EVENT_CLOSE
                ExitLoop
                
            Case $nButton
                ; Normally should not run through cause of our MY_WM_COMMAND function
                MsgBox(0, "Info", "Button pressed")
                
            Case $nButton2
                ; Normally should not run through cause of our MY_WM_COMMAND function
                MsgBox(0, "Info", "Button2 pressed")
        EndSwitch
    WEnd
EndFunc   ;==>Example

; React on a button click
Func MY_WM_COMMAND($hWnd, $Msg, $wParam, $lParam)
    $nNotifyCode = BitShift($wParam, 16)
    $nID = BitAND($wParam, 0x0000FFFF)
    $hCtrl = $lParam
    
    If $nID <> 2 And $nNotifyCode = 0 Then ; Check for IDCANCEL - 2
        ; Ownerdrawn buttons don't send something by pressing ENTER
        ; So IDOK - 1 comes up, now check for the control that has the current focus
        If $nID = 1 Then
            $hFocus = DllCall("user32.dll", "hwnd", "GetFocus")
            $nCtrlID = DllCall("user32.dll", "int", "GetDlgCtrlID", "hwnd", $hFocus[0])
            PostButtonclick($hWnd, $nCtrlID[0])
        Else
            MsgBox(0, "MY_WM_COMMAND", "GUIHWnd" & @TAB & ":" & $hWnd & @LF & _
                    "MsgID" & @TAB & ":" & $Msg & @LF & _
                    "wParam" & @TAB & ":" & $wParam & @LF & _
                    "lParam" & @TAB & ":" & $lParam & @LF & @LF & _
                    "WM_COMMAND - Infos:" & @LF & _
                    "-----------------------------" & @LF & _
                    "Code" & @TAB & ":" & $nNotifyCode & @LF & _
                    "CtrlID" & @TAB & ":" & $nID & @LF & _
                    "CtrlHWnd" & @TAB & ":" & $hCtrl)
        EndIf
        Return 0 ; Only workout clicking on the button
    EndIf
    ; Proceed the default Autoit3 internal message commands.
    ; You also can complete let the line out.
    ; !!! But only 'Return' (without any value) will not proceed
    ; the default Autoit3-message in the future !!!
    Return $GUI_RUNDEFMSG
EndFunc   ;==>MY_WM_COMMAND


; RePost a WM_COMMAND message to a ctrl in a gui window
Func PostButtonclick($hWnd, $nCtrlID)
    DllCall("user32.dll", "int", "PostMessage", _
            "hwnd", $hWnd, _
            "int", $WM_COMMAND, _
            "int", BitAND($nCtrlID, 0x0000FFFF), _
            "hwnd", GUICtrlGetHandle($nCtrlID))
EndFunc   ;==>PostButtonclick

All I did was remove the owernerdrawn flag from the first button, and removed the WM_DRAWITEM registered message. I left all the MY_WM_COMMAND() stuff in tact. But in this script, the MsgBox()'s from MY_WM_COMMAND() are not created asynchronously like in the original example. That's what I don't understand. Why would the WM_DRAWITEM routines affect that?

And shouldn't this simpler example work as you describe? A new MsgBox() should be spawned asynchronously each time you press one of the buttons.

Edited by wraithdu

Share this post


Link to post
Share on other sites

Alright, I misunderstood what you wrote initially. I don't have an answer, and I don't care to put more time into it. You know why? Read. The. Warning. Do you get it yet? Do you get that you're chasing after something that doesn't really matter?

Share this post


Link to post
Share on other sites

Wow, feeling professional today I see.

Glad you understand what I was talking about, but I don't need your attitude, developer or not.

Share this post


Link to post
Share on other sites

Wow, feeling professional today I see.

Glad you understand what I was talking about, but I don't need your attitude, developer or not.

Here's some fucking attitude for you. You get a 24 hour ban. Why? Because I don't need your stupid comments. I've been more than fucking patient with you trying to get you to understand you're wanting an explanation to unpredictable behavior yet you keep right on going. When I finally get to the point that I'm no longer going to waste time trying to explain to you that this meets the very definition of what the warning is telling you about, you come back with this stupid bullshit? I haven't showed you any attitude until now. I suggest you crawl under a big fat rock and hide from the world if you're so thin-skinned that you can't take somebodies minor frustration at your incessant aversion to getting the point.

You lot need to be less quick to jump on the "Valik has a bad attitude" bandwagon. Do I have a bad attitude? Absolutely. Do we need comments on it every time one of you pushes me to be even remotely cross? No we don't, so drop the subject. Topic locked.

Share this post


Link to post
Share on other sites
Guest
This topic is now closed to further replies.
Sign in to follow this  
Followers 0