15

I want to simulate a click on a button located in a dialog box.

I have the handle to that window. This is an Abort/Retry/Ignore kind of window.

I don't want to go with simulating a click having X and Y coordinates as it doesn't suit my needs.

2
  • Could this be of help? forums.codeguru.com/… Commented Apr 30, 2013 at 8:47
  • It is not normal. Seems that assert fails somewhere and you are running debug version. Try _set_abort_behavior(). Commented Apr 30, 2013 at 8:50

5 Answers 5

20

Send a BM_CLICK message to the HWND of the button:

SendMessage(hButton, BM_CLICK, 0, 0);

That causes the button to receive WM_LBUTTONDOWN and WM_LBUTTONUP messages, and the parent to receive an BN_CLICKED notification, as if the user had physically clicked on the button.

Sign up to request clarification or add additional context in comments.

Comments

13

Find the handle to the button that you want to click (by using FindWindowEx), and just send click message:

SendMessage(hButton, WM_LBUTTONDOWN, MK_LBUTTON, MAKELPARAM(0, 0));
SendMessage(hButton, WM_LBUTTONUP, MK_LBUTTON, MAKELPARAM(0, 0));

4 Comments

It works but it's not an ellegant solution. Doesn't WinAPI support functions that would directly "click" one of the windows's buttons? And I had to use Spy++ to get the name of the Button which wasn't straight-forward.
@AronBoguta You can enumerate all windows using EnumChildWindows, until you find out target button handle. If WinAPI contained a function that would directly "click" on of the window's buttons, it would do exactly the same that we did. Also, WinAPI is treating buttons as (child) windows.
thanks, I know already about the EnumChildWindows still I would expect more from WinAPI :)
@AronBoguta: Use a single BM_CLICK message instead of two WM_LBUTTON... messages: SendMessage(hButton, BM_CLICK, 0, 0);
12
SendMessage(hParent, WM_COMMAND, MAKEWPARAM(IdOfButton, BN_CLICKED), (LPARAM)hwndOfButton);

Typically you can get away without the hwndOfButton, if you don't know it - depends on the dialog's implementation!

It can be SendMessage or PostMessage, depending on your use case.

4 Comments

Tried all the other answers. This one is the only one that worked for me.
You do realize that in WinUser.h, BN_CLICKED is defined as follows: #define BN_CLICKED 0, so the MAKEWPARAM is superfluous here. WPARAM(idOfButton) is all you need for a WM_COMMAND that resulted from a mouse click, unless you are trying to document in the code.
Sure, but the intent very clear if you use the #define - much better practice, much clearer code and easier to edit (to a different code). Appreciate you pointing it out though :)
This worked for me too: SendMessage(WM_COMMAND, MAKEWPARAM(IDC_BUTTON_MODIFY_TALK, BN_CLICKED), (LPARAM)m_btnModify.GetSafeHwnd());
3

Try this for OK:

SendMessage(hWnd, WM_COMMAND, 1, NULL);

1 Comment

There is no OK button. Only Abort/Retry/Ignore like I said and I wish to click Abort
1

Here is a complete function:

void clickControl(HWND hWnd, int x, int y)
{
    POINT p;
    p.x = x; p.y = y;
    ClientToScreen(hWnd, &p);
    SetCursorPos(p.x, p.y);
    PostMessage(hWnd, WM_MOUSEMOVE, 0, MAKELPARAM(x, y));
    PostMessage(hWnd, WM_LBUTTONDOWN, MK_LBUTTON, MAKELPARAM(x, y));
    PostMessage(hWnd, WM_LBUTTONUP, MK_LBUTTON, MAKELPARAM(x, y));
}

1 Comment

Even though this doesn't answer the original question, it helped me for what I was looking for, thanks !

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.