Hello whomever!
I've noticed there aren't alot of posts via Classes and Code Snippets, the ones that are here seem to be a little boring and rather useless (with the exception of the mouse emulation), so I've decided to post a few examples of how you could go about emulating key/mouse presses using C++. There'll be a very short list of links to a very useful and resourceful site after the examples are posted.
I'll assume some of you are Blizzard fans, which can make this practical (StarCraft for ASCII art, Diablo II for Baal/Diablo runs, World of WarCraft, etc) usage for you, if you really put thought into it and not just copy & paste somebody elses code (I'm all for open-source code, but not learning is like watching TV without watching the commercials!).
NOTE: These examples are compiled on the Windows Operating System using Dev-C++ 4.9.9.2
First example - SendInput:
Small note: This will work in channels on Battle.net
Second example - varation of SendInput:Code:#include <iostream> #include <windows.h> #include <winable.h> /* Dev-C++ specific */ using namespace std; /* HWND = "Window Handle" */ HWND GameWindow = FindWindow(0, "Brood War"); /* This is a function to simplify usage of sending keys */ void GenerateKey(int vk, BOOL bExtended) { KEYBDINPUT kb = {0}; INPUT Input = {0}; /* Generate a "key down" */ if (bExtended) { kb.dwFlags = KEYEVENTF_EXTENDEDKEY; } kb.wVk = vk; Input.type = INPUT_KEYBOARD; Input.ki = kb; SendInput(1, &Input, sizeof(Input)); /* Generate a "key up" */ ZeroMemory(&kb, sizeof(KEYBDINPUT)); ZeroMemory(&Input, sizeof(INPUT)); kb.dwFlags = KEYEVENTF_KEYUP; if (bExtended) { kb.dwFlags |= KEYEVENTF_EXTENDEDKEY; } kb.wVk = vk; Input.type = INPUT_KEYBOARD; Input.ki = kb; SendInput(1, &Input, sizeof(Input)); return; } int main() { /* SetForegroundWindow will give the window focus for the keyboard/mouse! In other words, you don't have to have the game opened upfront in order to emulate key/mouse presses, it's very helpful if it's a game that runs in fullscreen mode, like StarCraft: Brood War does */ SetForegroundWindow(GameWindow); GenerateKey(VK_CAPITAL, TRUE); GenerateKey('I', FALSE); GenerateKey(' ', FALSE); GenerateKey(VK_CAPITAL, TRUE); GenerateKey('A', FALSE); GenerateKey('M', FALSE); GenerateKey(' ', FALSE); GenerateKey('C', FALSE); GenerateKey('O', FALSE); GenerateKey('O', FALSE); GenerateKey('L', FALSE); GenerateKey('E', FALSE); GenerateKey('R', FALSE); GenerateKey(' ', FALSE); GenerateKey('T', FALSE); GenerateKey('H', FALSE); GenerateKey('A', FALSE); GenerateKey('N', FALSE); GenerateKey(' ', FALSE); GenerateKey('Y', FALSE); GenerateKey('O', FALSE); GenerateKey('U', FALSE); GenerateKey(' ', FALSE); GenerateKey('W', FALSE); GenerateKey('I', FALSE); GenerateKey('L', FALSE); GenerateKey('L', FALSE); GenerateKey(' ', FALSE); GenerateKey('E', FALSE); GenerateKey('V', FALSE); GenerateKey('E', FALSE); GenerateKey('R', FALSE); GenerateKey(' ', FALSE); GenerateKey('B', FALSE); GenerateKey('E', FALSE); GenerateKey('n', FALSE); GenerateKey(' ', FALSE); GenerateKey(0x3A, FALSE); /* period key */ GenerateKey(0x0D, FALSE); /* enter key */ return 0; }
Small note: This will work in channels on Battle.net
Third example - SendMessage (heavily unreliable and unpredictable):Code:#include <windows.h> #include <winable.h> /* Dev-C++ specific */ using namespace std; /* HWND = "Window Handle" */ HWND hWnd = FindWindow(0, "Brood War"); void GenerateKey(BYTE vk) { INPUT Input; ZeroMemory(&Input, sizeof(Input)); Input.type = INPUT_KEYBOARD; Input.ki.dwFlags = KEYEVENTF_EXTENDEDKEY; Input.ki.wVk = vk; SendInput(1, &Input, sizeof(INPUT)); return; } int main() { SetForegroundWindow(hWnd); GenerateKey((UCHAR)VkKeyScan('C')); GenerateKey((UCHAR)VkKeyScan('o')); GenerateKey((UCHAR)VkKeyScan('d')); GenerateKey((UCHAR)VkKeyScan('i')); GenerateKey((UCHAR)VkKeyScan('n')); GenerateKey((UCHAR)VkKeyScan('g')); GenerateKey((UCHAR)VkKeyScan(' ')); GenerateKey((UCHAR)VkKeyScan('i')); GenerateKey((UCHAR)VkKeyScan('s')); GenerateKey((UCHAR)VkKeyScan(' ')); GenerateKey((UCHAR)VkKeyScan('f')); GenerateKey((UCHAR)VkKeyScan('u')); GenerateKey((UCHAR)VkKeyScan('n')); GenerateKey((UCHAR)VkKeyScan('.')); GenerateKey((UCHAR)VkKeyScan('\n')); /* enter key */ return 0; }
Small note: This will work not in channels on Battle.net, but will in games
SendInput can emulate not only keyboard input but also mouse input!Code:#include <windows.h> #include <iostream> using namespace std; /* HWND = "Window handle" */ HWND hwnd = FindWindow(0, "Brood War"); void PressButton(HWND hwnd, BYTE vk) { SendMessage(hwnd, vk, WM_KEYDOWN, 0); /* Due to Blizzard's latest patch, I had to change this to PostMessage */ PostMessage(hwnd, WM_CHAR, vk, 0); SendMessage(hwnd, vk, WM_KEYUP, 0); } void TypeText(HWND hwnd, char String[]) { /* You could filter text in here if you wanted :) */ for (int x = 0; String[x] != 0; x++) { PressButton(hwnd, String[x]); } } void DrawBox() { TypeText(hwnd, "\n /-----\\ \n"); Sleep(25); TypeText(hwnd, "\n | | \n"); Sleep(25); TypeText(hwnd, "\n \\-----/ \n"); return; } int main() { TypeText(hwnd, "\nThis is a really cool example! :)\n"); Sleep(25); /* You must pause to give StarCraft time to respond */ TypeText(hwnd, "\nUnfortuantly with Brood War, it only works while in-game... :(\n"); Sleep(10000); /* Paused for a while so you can alt + tab to SC: BW and watch it be drawn */ /* Here's an ideal ASCII art! */ DrawBox(); return 0; }
Which I shall now demonstrate with a few examples... But before I do.
This is a nifty little application to help find coordinates:
First example - SetCursorPos:Code:#include <iostream> #include <windows.h> int main () { POINT pos; while (true) { if (GetAsyncKeyState(VK_HOME)) { GetCursorPos(&pos); printf("%i - %i\n", pos.x, pos.y); Sleep(50); } if (GetAsyncKeyState(VK_END)) { break; } } return 0; }
Small note: This is just for pure fun, but can be used in conjunction with other stuff
Second example - SendMessage (heavily unreliable and unpredictable):Code:#include <windows.h> int main () { /* A crazy mouse gone wild!! */ while (true) { Sleep(rand() % 100); SetCursorPos(rand() % 500, rand() % 500); } return 0; }
Small note: This is a very unreliable method, might/might not work with games/applications
Third example - SendInput:Code:#include <iostream> #include <windows.h> int main () { HWND hwnd = FindWindow(0, "Dev-C++ 4.9.9.2"); /* This will NOT close Dev-C++, because Dev-C++ does not respond to the message */ SetCursorPos(1269, 8); SendMessage(hwnd, WM_LBUTTONDOWN, 1269, 8); Sleep(25); SendMessage(hwnd, WM_LBUTTONUP, 1269, 8); return 0; }
Small note: This will work with any application
Fourth example - SendInput:Code:#include <iostream> #include <windows.h> #include <winable.h> /* Dev-C++ specific */ using namespace std; int main() { /* This WILL close Dev-C++ with a resolution size of: 1280x1024 */ SetCursorPos(1296, 8); INPUT Input[2]; ZeroMemory(Input, sizeof(INPUT) * 2); Input[0].type = INPUT_MOUSE; Input[0].mi.dwFlags = MOUSEEVENTF_LEFTDOWN; Input[1].type = INPUT_MOUSE; Input[1].mi.dwFlags = MOUSEEVENTF_LEFTUP; SendInput(2, Input, sizeof(INPUT)); return 0; }
Small note: This will work with any application
That's all the examples I can possibly think of right now (they could be improved, but I'll leave that up to the readers (that's you!)).Code:#include <iostream> #include <windows.h> #include <winable.h> /* Dev-C++ specific */ using namespace std; void Click(const int X, const int Y) { SetCursorPos(X, Y); INPUT Input[2]; ZeroMemory(Input, sizeof(INPUT) * 2); Input[0].type = INPUT_MOUSE; Input[0].mi.dwFlags = MOUSEEVENTF_LEFTDOWN; Input[1].type = INPUT_MOUSE; Input[1].mi.dwFlags = MOUSEEVENTF_LEFTUP; SendInput(2, Input, sizeof(INPUT)); return; } int main() { HWND GameWindow = FindWindow(0, "Brood War"); ShowWindow(GameWindow, SW_RESTORE); Sleep(2000); Click(49, 275); Sleep(2000); Click(488, 454); Sleep(2000); Click(514, 388); return 0; }
I hope this was helpful to somebody, and as I promised, here's a list of useful links:
- Sleep: Sleep Function (Windows)
- SendMessage: SendMessage Function ()
- PostMessage: PostMessage Function ()
- FindWindow: FindWindow Function ()
- ShowWindow:ShowWindow Function ()
- SetForegroundWindow: SetForegroundWindow Function ()
- User Input branch: User Input
- INPUT structure: INPUT Structure ()
- KEYBDINPUT struct: KEYBDINPUT Structure ()
- POINT struct: POINT Structure
- SendInput: SendInput Function ()
- VkKeyScan: VkKeyScan Function ()
- GetAsyncKeyState: GetAsyncKeyState Function ()
- ZeroMemory: ZeroMemory Macro (Windows)
- GetCursorPos: GetCursorPos Function ()
- SetCursorPos: SetCursorPos Function ()
- List of Virtual Keys: List of Virtual Key Codes
“You may be disappointed if you fail, but you are doomed if you don't try.”
- Beverly Sills
It was absolutely great and works fine for me!
Let me ask you a question, I'm interested in using this kind of program to unlock a computer after logging into it with remote desktop, in order to avoid someone to go and type the login user and pass.
What I should do is use some code like yours but i need to make focus on the login screen, does anybody knows how can i reference the windows login screen prompted when the computer is locked by remote desktop?
Many Thanks for your help!
This is a very good example; I appreciate you putting this up... Now for a question.
Any reason why a period would not show up?
Thanks in advance!
I do not think that is possible, but it might be, I've never actually attempted something like that.Let me ask you a question, I'm interested in using this kind of program to unlock a computer after logging into it with remote desktop, in order to avoid someone to go and type the login user and pass.
You wouldn't need focus, you can use SendInput, because it clicks as if your mouse would.
I'm unsure. It depends on a lot of things. Especially which one you're refering to.Any reason why a period would not show up?
“You may be disappointed if you fail, but you are doomed if you don't try.”
- Beverly Sills
There are currently 1 users browsing this thread. (0 members and 1 guests)
Bookmarks