How can I simulate a mouse event causing the pointer to move 500 pixels to the left, then click using C++. How would I do something like this?
Asked
Active
Viewed 4.3k times
6 Answers
46
Here's some modified Win32 code I had lying around:
#define WIN32_LEAN_AND_MEAN
#define _WIN32_WINNT 0x0500
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <conio.h>
#include <string.h>
#include <windows.h>
#define X 123
#define Y 123
#define SCREEN_WIDTH 1024
#define SCREEN_HEIGHT 800
void MouseSetup(INPUT *buffer)
{
buffer->type = INPUT_MOUSE;
buffer->mi.dx = (0 * (0xFFFF / SCREEN_WIDTH));
buffer->mi.dy = (0 * (0xFFFF / SCREEN_HEIGHT));
buffer->mi.mouseData = 0;
buffer->mi.dwFlags = MOUSEEVENTF_ABSOLUTE;
buffer->mi.time = 0;
buffer->mi.dwExtraInfo = 0;
}
void MouseMoveAbsolute(INPUT *buffer, int x, int y)
{
buffer->mi.dx = (x * (0xFFFF / SCREEN_WIDTH));
buffer->mi.dy = (y * (0xFFFF / SCREEN_HEIGHT));
buffer->mi.dwFlags = (MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE);
SendInput(1, buffer, sizeof(INPUT));
}
void MouseClick(INPUT *buffer)
{
buffer->mi.dwFlags = (MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_LEFTDOWN);
SendInput(1, buffer, sizeof(INPUT));
Sleep(10);
buffer->mi.dwFlags = (MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_LEFTUP);
SendInput(1, buffer, sizeof(INPUT));
}
int main(int argc, char *argv[])
{
INPUT buffer[1];
MouseSetup(&buffer);
MouseMoveAbsolute(&buffer, X, Y);
MouseClick(&buffer);
return 0;
}
You'll need to call MouseSetup()
to each INPUT
buffer before you use it.
Resources

Mateen Ulhaq
- 24,552
- 19
- 101
- 135
-
1Better use `x * 0xFFFF / SCREEN_WIDTH + 1` for pixel-perfect coordinate normalization. (For all values of SCREEN_WIDTH < (0xFFFF / 2) and x <= SCREEN_WIDTH). Your formula can be tens of pixels off for common screen resolutions. – Kay Sarraute Sep 17 '13 at 14:17
-
This is required - otherwise you will have worsening cursor positioning accuracy from left-to-right and top-to-bottom. – Ani Dec 05 '13 at 23:15
-
`MouseSetup()` to each `INPUT` means each **variable** of type `INPUT`... I was confused - at the first sight I thought you have to call it before every mouseinput (which made no sense...). – jave.web Nov 21 '14 at 16:44
-
how to retrieve SCREEN_WIDTH and SCREEN_HEIGHT to make MouseMoveAbsolute() display size (resolution) independent? – Michał Ziobro Dec 07 '16 at 20:23
-
1" (x * (0xFFFF / SCREEN_WIDTH));" result in very huge values.Is it supposed to be like that? – Michael IV Sep 15 '17 at 16:37
-
`x * 65536 / SCREEN_WIDTH + 1` works better in my case, which is also used in [AutoHotKey](https://github.com/Lexikos/AutoHotkey_L/blob/58842fb2956fe082bc11476316d4590b0e2ee8a8/source/keyboard_mouse.cpp#L2545). – J3soon Mar 06 '18 at 13:15
26
Here is a solution using Xlib
for those who use Linux
:
#include <X11/Xlib.h>
#include<stdio.h>
#include<unistd.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
void mouseClick(int button)
{
Display *display = XOpenDisplay(NULL);
XEvent event;
if(display == NULL)
{
fprintf(stderr, "Errore nell'apertura del Display !!!\n");
exit(EXIT_FAILURE);
}
memset(&event, 0x00, sizeof(event));
event.type = ButtonPress;
event.xbutton.button = button;
event.xbutton.same_screen = True;
XQueryPointer(display, RootWindow(display, DefaultScreen(display)), &event.xbutton.root, &event.xbutton.window, &event.xbutton.x_root, &event.xbutton.y_root, &event.xbutton.x, &event.xbutton.y, &event.xbutton.state);
event.xbutton.subwindow = event.xbutton.window;
while(event.xbutton.subwindow)
{
event.xbutton.window = event.xbutton.subwindow;
XQueryPointer(display, event.xbutton.window, &event.xbutton.root, &event.xbutton.subwindow, &event.xbutton.x_root, &event.xbutton.y_root, &event.xbutton.x, &event.xbutton.y, &event.xbutton.state);
}
if(XSendEvent(display, PointerWindow, True, 0xfff, &event) == 0) fprintf(stderr, "Error\n");
XFlush(display);
usleep(100000);
event.type = ButtonRelease;
event.xbutton.state = 0x100;
if(XSendEvent(display, PointerWindow, True, 0xfff, &event) == 0) fprintf(stderr, "Error\n");
XFlush(display);
XCloseDisplay(display);
}
int main(int argc, char * argv[]) {
int x , y;
x = atoi(argv[1]);
y = atoi(argv[2]);
Display *display = XOpenDisplay(0);
Window root = DefaultRootWindow(display);
XWarpPointer(display, None, root, 0, 0, 0, 0, x, y);
mouseClick(Button1);
XFlush(display);
XCloseDisplay(display);
return 0;
}
Just Build it and then to simulate a click at x ,y do:
$ ./a.out x y
i.e.
$g++ -lX11 sgmousesim2.cpp
$./a.out 123 13

axiom
- 8,765
- 3
- 36
- 38
-
2That's quite correct for X11, but the question did get clarified to ask for a Windows solution. – Flexo Jan 09 '12 at 17:09
-
8Just noticed it :) . maybe it will help those who come looking for a Linux specific solution. – axiom Jan 09 '12 at 17:13
1
I have never did this using C++. Nevertheless, there is a Java class called Robot which is able to produce mouse events. I used this back on Java version 1.4 but it does still work. I tried the example from this Simulate a physical mouse move in Mac OS X. It runs smoothly with Oracle Java 1.6.0_26 on MacOSX Lion. The good about Java is that it is platform independent.
import java.awt.AWTException;
import java.awt.Robot;
public final class MovingMouseDemo
{
public static void main(String[] args) throws AWTException
{
Robot robot = new Robot();
robot.setAutoDelay(5);
robot.setAutoWaitForIdle(true);
//put mouse in the top left of the screen
robot.mouseMove(0, 0);
//wait so that you can see the result
robot.delay(1000);
//put the mouse 200 pixels away from the top
//10 pixels away from the left
robot.mouseMove(200, 10);
robot.delay(1000);
robot.mouseMove(40, 130);
}
}
You can still use JNI to bind it with C++.
I hope it helps
0
Use the mouse_event function.

Mateen Ulhaq
- 24,552
- 19
- 101
- 135

George Gaál
- 1,216
- 10
- 21
-
2If you read the documentation, it says "***Note** This function has been superseded. Use SendInput instead.*" – Mateen Ulhaq Sep 21 '11 at 23:36
-
1It works anyway in Win2k and WinXP. I've checked this. I don't know about support in W7, but I assume that `mouse_event` will work too because there are many legacy code using it.Also syntax of this function is more obvious than syntax of `SendInput`. – George Gaál Sep 22 '11 at 00:39
-
Whether something works or not is not important. A lot of things work fine. once, or when your testing, or on 1 machine. Whats important is that you were told by the vendor not to use it, and you ignore them. You will not PASS certification on that vendors platform. And if you dont need certification, you will most likely just piss off customers by selling them broken crap. Its deprecated for a reason. DO NOT USE IT. Could be there is a 1 in 10000 chance that you kill someone. You dont know. so dont use it. – Dan May 01 '19 at 22:39