Sign in to follow this  
Followers 0
BruceCopperField

ControlClick Not Working for Swapped Button

12 posts in this topic

#1 ·  Posted (edited)

I swapped the mouse buttons and used ControlClick to click a button control (the Next button of an installation window).

These don't work:

ControlClick ( $vboxTitle, "", $buttonID, "primary") 
ControlClick ( $vboxTitle, "", $buttonID, "right")

The button isn't clicked. No left click. But I expect the above should make a left click because 'right' = left button now and 'Primary' should always=left.

This works

ControlClick ( $vboxTitle, "", $buttonID, "left")

So probably the left/right/primary keywords for ControlClick doesnt honor swapped mouse button.

My version is v3.3.6.1

Edited by BruceCopperField

Share this post


Link to post
Share on other sites



Dog ate your help file? :)

Quoting the comments in the help file under ControlClick():

If the user has swapped the left and right mouse buttons in the control panel, then the behaviour of the buttons is different. "Left" and "right" always click those buttons, whether the buttons are swapped or not. The "primary" or "main" button will be the main click, whether or not the buttons are swapped. The "secondary" or "menu" buttons will usually bring up the context menu, whether the buttons are swapped or not.

There is even a handy chart.

:)


Valuater's AutoIt 1-2-3, Class... Is now in Session!For those who want somebody to write the script for them: RentACoder"Any technology distinguishable from magic is insufficiently advanced." -- Geek's corollary to Clarke's law

Share this post


Link to post
Share on other sites

Dog ate your help file? :)

Quoting the comments in the help file under ControlClick():

There is even a handy chart.

:)

So, in that case why these don't result in a logical left click in a swapped mouse?

ControlClick ( $vboxTitle, "", $buttonID, "primary") 
ControlClick ( $vboxTitle, "", $buttonID, "right")

Because as decribed in the help file the first one always cause the primay click. And, the second one should cause a logical left click because the physical right button is now assigned as the logical left button due to the swap.

And this should not cause any click at all (but it does in my test)

ControlClick ( $vboxTitle, "", $buttonID, "left")

because now physical left button is the logic right button

Share this post


Link to post
Share on other sites

So, in that case why these don't result in a logical left click in a swapped mouse?

ControlClick ( $vboxTitle, "", $buttonID, "primary") 
ControlClick ( $vboxTitle, "", $buttonID, "right")

Because as decribed in the help file the first one always cause the primay click. And, the second one should cause a logical left click because the physical right button is now assigned as the logical left button due to the swap.

And this should not cause any click at all (but it does in my test)

ControlClick ( $vboxTitle, "", $buttonID, "left")

because now physical left button is the logic right button

I think there might be differences due to a combination of mouse drivers and errors in the help.

For me, if I swap the mouse buttons then for MouseClick

left acts as unswapped right

right acts as unswapped left

primary acts as unswapped left

secondary acts as unswapped right.

Also, the left shift button on my laptop moves the whole laptop to the right.! (But you have to press it quite hard.) The help doesn't mention that.


Serial port communications UDF Includes functions for binary transmission and reception.printing UDF Useful for graphs, forms, labels, reports etc.Add User Call Tips to SciTE for functions in UDFs not included with AutoIt and for your own scripts.Functions with parameters in OnEvent mode and for Hot Keys One function replaces GuiSetOnEvent, GuiCtrlSetOnEvent and HotKeySet.UDF IsConnected2 for notification of status of connected state of many urls or IPs, without slowing the script.

Share this post


Link to post
Share on other sites

I think there might be differences due to a combination of mouse drivers and errors in the help.

By the way, I am using an old PS/2 optical mouse. Probably the PS/2 mouse driver is an issue.

Share this post


Link to post
Share on other sites

#6 ·  Posted (edited)

Dog ate your help file? :)

And more importantly, I read my help files before posting my questions. Dogs don't eat help file. They eat dog food. Use your mind little kid and learn how to answer questions in proper manner. Or just simply STFU.

Edited by BruceCopperField

Share this post


Link to post
Share on other sites

And more importantly, I read my help files before posting my questions. Dogs don't eat help file. They eat dog food. Use your mind little kid and learn how to answer questions in proper manner. Or just simply STFU.

You could have taken this remark a little more lightly in stead of replaying like this.

A little research would have revealed that you are not talking to a child ... so cool down.

Jos


Visit the SciTE4AutoIt3 Download page for the latest versions        Beta files                                                          Forum Rules
 
Live for the present,
Dream of the future,
Learn from the past.
  :)

Share this post


Link to post
Share on other sites

#8 ·  Posted (edited)

Hi, I'm resurrecting this topic because I'm also having the same issue when I swap the mouse buttons in the control panel.

The help file says:

If the user has swapped the left and right mouse buttons in the control panel, then the behavior of the buttons is different. "Left" and "right" always click those buttons, whether the buttons are swapped or not. The "primary" or "main" button will be the main click, whether or not the buttons are swapped. The "secondary" or "menu" buttons will usually bring up the context menu, whether the buttons are swapped or not.

 

But in my case, if the mouse buttons are swapped, "left" and "menu" perform the main click and "right" and "main" bring up the context menu.

I'm not sure it is a driver issue, but I don't think so. I tested in 2 pcs (one laptop and one desktop) running Windows 7 x64.

Also tested in 2 VMs (Xp x86 and Windows 7 x86). Same result. Is anyone else experimenting the same issue?

I only tested with ControlClick() yet. I'll  to test MouseClick() and keep you posted..

Edited by FredAI

Share this post


Link to post
Share on other sites

Ok, I tested with MouseClick(), and it works just like specified in the help file. The issue seems to be only with ControlClick().

My guess is that AutoIt uses the SendInput() api for MouseClick() and sends the following messages to the control for ControlClick():

WM_LBUTTONDOWN / WM_LBUTTONUP (for left click), and WM_RBUTTONDOWN / WM_RBUTTONUP (for right click).

I'm guessing, if the mouse buttons are swapped, and we use "main" or "primary" it (wrongly) sends the WM_R* messages instead of the W_L* ones. Now that's not right. The applications do not need to be aware of the mouse buttons swapped state. It's the system that changes the messages sent. That means the messages should be changed for "left" and "right", not for "main" or "menu".

I think someone should notify the devs about this issue.

Share this post


Link to post
Share on other sites

Instead of resurrecting a 2 year old thread, why not put in a bug ticket in the Bug Tracker? You can link to this thread, but I see no point in that if there is a bug that is reproducable and you post a script that does show that.


If I posted any code, assume that code was written using the latest release version unless stated otherwise. Also, if it doesn't work on XP I can't help with that because I don't have access to XP, and I'm not going to.
Give a programmer the correct code and he can do his work for a day. Teach a programmer to debug and he can do his work for a lifetime - by Chirag Gude
How to ask questions the smart way!

I hereby grant any person the right to use any code I post, that I am the original author of, on the autoitscript.com forums, unless I've specifically stated otherwise in the code or the thread post. If you do use my code all I ask, as a courtesy, is to make note of where you got it from.

Back up and restore Windows user files _Array.au3 - Modified array functions that include support for 2D arrays.  -  ColorChooser - An add-on for SciTE that pops up a color dialog so you can select and paste a color code into a script.  -  Customizable Splashscreen GUI w/Progress Bar - Create a custom "splash screen" GUI with a progress bar and custom label.  -  _FileGetProperty - Retrieve the properties of a file  -  SciTE Toolbar - A toolbar demo for use with the SciTE editor  -  GUIRegisterMsg demo - Demo script to show how to use the Windows messages to interact with controls and your GUI.  -   Latin Square password generator

Share this post


Link to post
Share on other sites

I don't see anything wrong in resurrecting an old thread. I did it because it was the only thread I found mentioning this issue, and I wondered if anyone else was having the same issue. But maybe everyone is using "left" and "right", which work for ControlClick() even if the mouse buttons are swapped.

You want an example script? so here it goes. Try first with mouse buttons not swapped.

$GUI = GUICreate('ControlClick test',400,300,0,0)
$edit = GUICtrlCreateEdit('',0,0,400,300)
$hedit = GUICtrlGetHandle($edit)
GUISetState()
Sleep(500)
ControlClick($GUI, '', 'Edit1', 'menu')
While GUIGetMsg() <> -3

WEnd

You'll see the right click menu opens. Now swap the mouse buttons in the control panel and try again.

It does not work.

Now replace ControlClick($GUI, '', 'Edit1', 'menu') with ControlClick($GUI, '', 'Edit1', 'right').

It works, but according to the help file, it shouldn't.

Now replace ControlClick($GUI, '', 'Edit1', 'right') with MouseClick('menu',200,150,1,0).

It works.

Thus, if the mouse buttons are swapped, the behavior of "right", "left" and "menu" is different for MouseClick() and ControlClick().

The help file is correct for MouseClick, but not for ControlClick.

Share this post


Link to post
Share on other sites

#12 ·  Posted (edited)

I created a function _Click control(), which takes the same parameters as ControlClick(), but only uses the Windows api to send the correct messages to the control. It's working accordingly to the ControlClick() help. I hope it will prove my point.

Edit I edited the code. I was sending screen coordinates instead of client coordinates. Also added support for middle button clicks.

Edit 2: Added support for double clicks. Guess I won't be needing ControlClick() anymore, at least until the bug is fixed.

I'm actually glad I resurrected this thread. It didn't get the attention it deserved back then, leading to an important bug lasting for several years. :ermm:

Global Const $User32Dll         = DllOpen('user32.dll')

;Message codes for left click
Global Const $WM_LBUTTONDOWN    = 513
Global Const $WM_LBUTTONUP      = 514

;Message codes for middle click
Global Const $WM_MBUTTONDOWN    = 519
Global Const $WM_MBUTTONUP      = 520

;Message codes for right click
Global Const $WM_RBUTTONDOWN    = 516
Global Const $WM_RBUTTONUP      = 517

;Message codes for double click
Global Const $WM_LBUTTONDBLCLK  = 515
Global Const $WM_MBUTTONDBLCLK  = 521
Global Const $WM_RBUTTONDBLCLK  = 518

$GUI = GUICreate('MouseClick test',400,300,0,0)
$edit = GUICtrlCreateEdit('Some text.',0,0,400,300)
GUISetState()
Sleep(200)

;Test mouse click
;MouseClick('menu',200,150,1,0)
;MouseClick('right',200,150,1,0)
;MouseClick('left',200,150,1,0)

;ControlClick($GUI, '', 'Edit1', 'menu')
;ControlClick($GUI, '', 'Edit1', 'right')
;ControlClick($GUI, '', 'Edit1', 'left')

_ClickControl($GUI, '', 'Edit1', 'menu')
;_ClickControl($GUI, '', 'Edit1', 'right')
;_ClickControl($GUI, '', 'Edit1', 'left')

;Test double click (will select the last word of the edit text)
;_ClickControl($GUI, '', 'Edit1', 'main', 2)
;ControlClick($GUI, '', 'Edit1', 'main', 2)
;MouseClick('main', 200, 150, 2, 0)

While GUIGetMsg() <> -3
WEnd

Func _ClickControl($title, $text, $hCtrl, $button = 'main', $clicks = 1, $x = Default, $y = Default)
    If Not IsHWnd($hCtrl) Then $hCtrl = ControlGetHandle($title, $text, $hCtrl)
    If $hCtrl = 0 Then Return 0

    Local $sRect = _GetClientRect($hCtrl)
    If $x = Default Then $x = DllStructGetData($sRect,3)/2
    If $y = Default Then $y = DllStructGetData($sRect,4)/2

    Local $MsgDown = $WM_LBUTTONDOWN, $MsgUp = $WM_LBUTTONUP
    Local $msgDbClick = $WM_LBUTTONDBLCLK
    Switch $button
    Case '', 'main', 'primary'
        ;Already set
    Case 'menu', 'secondary'
        $MsgDown = $WM_RBUTTONDOWN
        $MsgUp = $WM_RBUTTONUP
        $msgDbClick = $WM_RBUTTONDBLCLK
    Case 'middle'
        $MsgDown = $WM_MBUTTONDOWN
        $MsgUp = $WM_MBUTTONUP
        $msgDbClick = $WM_MBUTTONDBLCLK
    Case 'left', 'right'
        If _GetSystemMetrics(23) Then
            $MsgDown = _IsTrue($button = 'left',$WM_RBUTTONDOWN,$WM_LBUTTONDOWN)
            $MsgUp = _IsTrue($button = 'left',$WM_RBUTTONUP,$WM_LBUTTONDOWN)
            $msgDbClick = _IsTrue($button = 'left',$WM_RBUTTONDBLCLK,$WM_LBUTTONDBLCLK)
        Else
            $MsgDown = _IsTrue($button = 'left',$WM_LBUTTONDOWN,$WM_RBUTTONDOWN)
            $MsgUp = _IsTrue($button = 'left',$WM_LBUTTONDOWN,$WM_RBUTTONUP)
            $msgDbClick = _IsTrue($button = 'left',$WM_LBUTTONDBLCLK,$WM_RBUTTONDBLCLK)
        EndIf
    Case Else
        Return 0
    EndSwitch

    Local $lParam = BitOR($x,BitShift($y,-16))
    If $clicks = 2 Then
        _Send_Message($hCtrl, $msgDbClick, 0, $lParam)
    Else
        For $i = 1 To $clicks
            _Send_Message($hCtrl, $MsgDown, 0, $lParam)
            _Send_Message($hCtrl, $MsgUp, 0, $lParam)
            Sleep(20)
        Next
    EndIf
    Return 1
EndFunc ;==> _ClickControl

Func _IsTrue($val, $true, $false)
    If $val Then Return $true
    Return $false
EndFunc ;==> _IsTrue

Func _GetClientRect($hwnd)
    Local $RECT = DllStructCreate('LONG left;LONG top;LONG right;LONG bottom')
    Local $aCall = DllCall($User32Dll, 'BOOL','GetClientRect', 'HWND',$hwnd, 'struct*',$RECT)
    If @error Then Return SetError(@error,0,$RECT)
    Return SetError(Number($aCall[0] = 0),0,$RECT)
EndFunc ;==> _GetWindowRect

Func _GetSystemMetrics($Index)
    Local $aCall = DllCall($User32Dll, 'int','GetSystemMetrics', 'int',$Index)
    If Not @error Then Return $aCall[0]
    Return SetError(1,0,0)
EndFunc ;==> _GetSystemMetrics

Func _Send_Message($hWnd, $uMsg, $wParam = 0, $lParam = 0)
    Local $aCall = DllCall($User32Dll, 'LRESULT','SendMessageW', _
    'HWND',$hWnd, 'UINT',$uMsg, 'WPARAM',$wParam, 'LPARAM',$lParam)
    If Not @error Then Return $aCall[0]
EndFunc ;==> _Send_Message
Edited by FredAI

Share this post


Link to post
Share on other sites

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
Sign in to follow this  
Followers 0