天天看点

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版

一 窗口版

1.h和cpp

h: DesktopMouseClick1.h

#pragma once

#include "resource.h"
#include <thread>
#include <process.h>
#include <string>



#define KEY_DOWN(VK_NONAME) ((GetAsyncKeyState(VK_NONAME) & 0x8000) ? 1:0) // 对比判断是不是哪个键按下

using namespace std;




static int interval = 3001;  // ClickPress间隔时间 ms毫秒
static wchar_t intervalStr [10];  // 用于从间隔时间编辑框获取值得缓存
HWND intervalEdit;    // 间隔时间输入框
HWND intervalEditCommitButton;    // 间隔时间输入框提交按钮
wchar_t interval_dec_itow_buffer[_MAX_ITOSTR_BASE10_COUNT];  //定义一个 _itow()  十进制用的缓冲 
const int KeyUpDownInterval = 1;
static int choose = 0;

const char MouseLeftClickStartKey = 'L';
const char MouseRightClickStartKey = 'R';
const char EnterpressStartKey = 'E';
const char SetIntervalMillisecondKey = 'T';

void keypress(int vk) {
	keybd_event(vk, 0, 0, 0); // keydown 按下
	Sleep(KeyUpDownInterval);
	keybd_event(vk, 0, KEYEVENTF_KEYUP, 0);  // keyup 起来
}
void enterpress() { keypress(VK_RETURN); }  // 模拟回车键


void hotkeyListen() {
	while (1) {
		if (KEY_DOWN(VK_SPACE)) {//VK_SPACE 是空格的虚拟键值     停止
			choose = 0;			Sleep(KeyUpDownInterval);//你的手不会再一瞬间送开,所以要处理一下 
		}
		if (KEY_DOWN(MouseLeftClickStartKey)) { choose = MouseLeftClickStartKey;			Sleep(KeyUpDownInterval); }   // 左键连击
		if (KEY_DOWN(MouseRightClickStartKey)) { choose = MouseRightClickStartKey;			Sleep(KeyUpDownInterval); }  // 右键连击
		if (KEY_DOWN(EnterpressStartKey)) { choose = EnterpressStartKey;			Sleep(KeyUpDownInterval); }  //enter连击

		
		Sleep(KeyUpDownInterval);
	}
}
void intervalFromEditCommit() {
	GetWindowText(intervalEdit, intervalStr, (int)GetWindowTextLength(intervalEdit) + 1);
	interval = _wtoi(intervalStr);
}

void ClickPressWork(void* ignored) {
	thread thread010(hotkeyListen);
	while (1) {

		if (choose == MouseLeftClickStartKey) {//模拟点击左键 
			mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);//要留给某些应用的反应时间 
			mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
		}
		if (choose == MouseRightClickStartKey) {//模拟点击右键 
			mouse_event(MOUSEEVENTF_RIGHTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);
			mouse_event(MOUSEEVENTF_RIGHTUP, 0, 0, 0, 0);
		}
		if (choose == EnterpressStartKey) {  //Enter
			enterpress();
		}
		if (interval < KeyUpDownInterval || interval >99999)interval = KeyUpDownInterval + 1;
		Sleep(interval - KeyUpDownInterval);//点击间隔 单位是毫秒 
	}
}
           

cpp : DesktopMouseClick1.cpp

// DesktopMouseClick1.cpp : 定义应用程序的入口点。
//
//#include<iostream>
#define _CRT_SECURE_NO_WARNINGS 1   //压制编译警告, 要放最上面  压制 _itow()  (int转wchar_t *) 的C4996警告
#include "framework.h"
#include "DesktopMouseClick1.h"

using namespace std;


#define _CRT_SECURE_NO_WARNINGS 1
#include <stdlib.h>

#define MAX_LOADSTRING 100

// 全局变量:
HINSTANCE hInst;                                // 当前实例
WCHAR szTitle[MAX_LOADSTRING] ;                  // 标题栏文本
WCHAR szWindowClass[MAX_LOADSTRING] ;            // 主窗口类名

// 此代码模块中包含的函数的前向声明:
ATOM                MyRegisterClass(HINSTANCE hInstance);
BOOL                InitInstance(HINSTANCE, int);
LRESULT CALLBACK    WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK    About(HWND, UINT, WPARAM, LPARAM);

// 我声明的变量  ↓ ↓ ↓
RECT  rect;   //用于绘制


// 我声明的变量  ↑ ↑ ↑

int APIENTRY wWinMain(_In_ HINSTANCE hInstance,
                     _In_opt_ HINSTANCE hPrevInstance,
                     _In_ LPWSTR    lpCmdLine,
                     _In_ int       nCmdShow)
{
    UNREFERENCED_PARAMETER(hPrevInstance);
    UNREFERENCED_PARAMETER(lpCmdLine);

    // TODO: 在此处放置代码。

    // 初始化全局字符串
    LoadStringW(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
    LoadStringW(hInstance, IDC_DESKTOPMOUSECLICK1, szWindowClass, MAX_LOADSTRING);
    MyRegisterClass(hInstance);

    // 执行应用程序初始化:
    if (!InitInstance (hInstance, nCmdShow))
    {
        return FALSE;
    }

    HACCEL hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_DESKTOPMOUSECLICK1));

    MSG msg;

    // 主消息循环:
    while (GetMessage(&msg, nullptr, 0, 0))
    {
        if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
        {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
    }

    return (int) msg.wParam;
}

//
//  函数: MyRegisterClass()
//
//  目标: 注册窗口类。
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{
    WNDCLASSEXW wcex;

    wcex.cbSize = sizeof(WNDCLASSEX);

    wcex.style          = CS_HREDRAW | CS_VREDRAW;
    wcex.lpfnWndProc    = WndProc;
    wcex.cbClsExtra     = 0;
    wcex.cbWndExtra     = 0;
    wcex.hInstance      = hInstance;
    wcex.hIcon          = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_DESKTOPMOUSECLICK1));
    wcex.hCursor        = LoadCursor(nullptr, IDC_ARROW);
    wcex.hbrBackground  = (HBRUSH)(COLOR_WINDOW+1);
    wcex.lpszMenuName   = MAKEINTRESOURCEW(IDC_DESKTOPMOUSECLICK1);
    wcex.lpszClassName  = szWindowClass;
    wcex.hIconSm        = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));

    return RegisterClassExW(&wcex);
}

//
//   函数: InitInstance(HINSTANCE, int)
//
//   目标: 保存实例句柄并创建主窗口
//
//   注释:
//
//        在此函数中,我们在全局变量中保存实例句柄并
//        创建和显示主程序窗口。
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
   hInst = hInstance; // 将实例句柄存储在全局变量中
   
   HWND hWnd = CreateWindowW(
       //第 1 个参数
       szWindowClass    // window class name   用法:   TEXT("EDIT")则可编辑  | 
       //TEXT("EDIT")

       //第 2 个参数
       , szTitle      // window title caption  用法:  TEXT ("你好世界")
       //, TEXT("3000")

       // 第3个参数  dwStyle
       , WS_OVERLAPPEDWINDOW  //默认  WS_OVERLAPPEDWINDOW可以创建一个拥有各种窗口风格的窗体,包括标题,系统菜单,边框,最小化和最大化按钮等。
       //, WS_VISIBLE |  WS_BORDER | ES_AUTOHSCROLL  | WS_OVERLAPPEDWINDOW


       //第4,5,6,7个参数
       , CW_USEDEFAULT  // left      如果这个参数设置CW_USEDEFAULT,系统选择的默认位置窗口的左上角,而忽略了y参数。CW_USEDEFAULT只有对重叠窗口是有效的;如果指定一个弹出子窗口,x和y 参数设置为零。        也就是说一般用它来创建你的程序的父窗口用的。
       , 0     
       , 333  //width
       , 120   //height

       //第8,9,10.11个参数          nullptr 为 c11 的指针专用NULL
       , nullptr     // parent window handle  为“父窗口句柄”,一般为NULL,如果有窗口之间存在父子关系,则子窗口总是出现在父窗口的上面。但应用程序窗口出现在桌面窗口的上面时,不必为调用CreateWindow而找出桌面窗口的句柄。
       , nullptr     // window menu handle   为“窗口菜单句柄”,如没有菜单则为NULL
       , hInstance   // program instance handle   为“程序实例句柄”,设置为实例句柄,它是作为WinMain的参数传递给这个程序的。
       , nullptr    //  // creation parameters  “创建参数”指针,设置为NULL,可以用这个指针访问以后想要引用的程序中的数据
   );
   if (!hWnd)   {      return FALSE;   }

   

   ShowWindow(hWnd, nCmdShow);
   UpdateWindow(hWnd);
   return TRUE;
}

//
//  函数: WndProc(HWND, UINT, WPARAM, LPARAM)
//
//  目标: 处理主窗口的消息。
//
//  WM_COMMAND  - 处理应用程序菜单
//  WM_PAINT    - 绘制主窗口
//  WM_DESTROY  - 发送退出消息并返回
//
//

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
    switch (message)
    {
    case WM_CREATE: {   //创建窗口时调用
        intervalEdit = CreateWindow(TEXT("EDIT"),  _itow(interval, interval_dec_itow_buffer, 10) ,  WS_VISIBLE | WS_CHILD, 150, 0, 100, 20, hWnd, nullptr, hInst, nullptr);
        intervalEditCommitButton = CreateWindow(L"Button", L"提交", WS_VISIBLE | WS_CHILD | BS_PUSHBUTTON,
            258, 0, 60, 20, hWnd, (HMENU)333, hInst, nullptr);


        //thread thread030(ClickPressWork);  // 开线程方式1;
        _beginthread(ClickPressWork, 0, 0);   //开线程方式2;
       
       
        break;
    }
    case WM_COMMAND:
        {
            int wmId = LOWORD(wParam);
            // 分析菜单选择:
            switch (wmId)
            {
            case ID_ClickPressStop :                choose = 0;                 break;
            case ID_StopClickPress001:                choose = 0;                 break;
            case ID_MouseLeftClickStart001:                 choose = MouseLeftClickStartKey;		                break;
            case ID_MouseLeftClickStart002:                 choose = MouseLeftClickStartKey;		                break;
            case ID_MouseLeftClickStart003:                 choose = MouseLeftClickStartKey;		                break;
            case ID_MouseRightClickStart002:                 choose = MouseRightClickStartKey;		                break;
            case ID_MouseRightClickStart003:                 choose = MouseRightClickStartKey;		                break;
            case ID_KeyboardEnterPressStart002:                 choose = MouseRightClickStartKey;		                break;
            case ID_KeyboardEnterPressStart003:                 choose = MouseRightClickStartKey;		                break;
            case 333:   intervalFromEditCommit();      MessageBox(hWnd, _itow(interval, interval_dec_itow_buffer, 10), L"间隔时间为(ms)", MB_OK);   break;  //间隔时间提交按钮
           


            case IDM_ABOUT:
                DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);
                break;
            case IDM_EXIT: 
                DestroyWindow(hWnd);
                break;
            default:
                return DefWindowProc(hWnd, message, wParam, lParam);
            }
        }
        break;
    case WM_PAINT:
        {
            PAINTSTRUCT ps;
            HDC hdc = BeginPaint(hWnd, &ps);
            // TODO: 在此处添加使用 hdc 的任何绘图代码...
            //我添加的代码  ↓↓↓↓↓↓↓↓↓↓↓↓↓

            wchar_t str010[] = L"点击间隔时间(毫秒) : ";
            TextOut(hdc, 0, 0, str010, (int)wcslen(str010));   // 第 2 , 3 个参数可以指定 x , y
            
            
            wchar_t str020[] = L"空格停止, L左键, R右键, E回车连击";
            //GetClientRect(hWnd, &rect);  /*传入指定窗口的矩形区域*/    DrawText(hdc, str020, wcslen(str020), &rect, DT_CENTER | DT_VCENTER);
            TextOut(hdc, 0, 20, str020, (int)wcslen(str020));   // 第 2 , 3 个参数可以指定 x , y
           
            





            //我添加的代码    ↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑
            EndPaint(hWnd, &ps);
        }
        break;
    case WM_DESTROY: 
        PostQuitMessage(0);
        break;
    default:
        return DefWindowProc(hWnd, message, wParam, lParam);
    }
    
    return 0;
}

// “关于”框的消息处理程序。
INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
    UNREFERENCED_PARAMETER(lParam);
    switch (message)
    {
    case WM_INITDIALOG:
        return (INT_PTR)TRUE;

    case WM_COMMAND:
        if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL)
        {
            EndDialog(hDlg, LOWORD(wParam));
            return (INT_PTR)TRUE;
        }
        break;
    }
    return (INT_PTR)FALSE;
}




           

2.根据所需功能创建菜单

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版

3.根据菜单ID编写功能

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版

效果截图

64位版大小109k 轻快小巧纯绿色 win32原生api

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版

二 命令行版

效果截图

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版

代码

鼠标连击-命令行版.cpp

#include <iostream>
#include<windows.h>
#include <thread>

#define KEY_DOWN(VK_NONAME) ((GetAsyncKeyState(VK_NONAME) & 0x8000) ? 1:0) 

using namespace std;


static int interval = 3000;  // 连击间隔时间 单位毫秒
const int KeyUpDownInterval = 1;  //按下与弹起的间隔 单位毫秒
static int choose = 0;

const char MouseLeftClickStartKey = 'L';
const char MouseRightClickStartKey = 'R';
const char EnterpressStartKey = 'E';
const char SetIntervalMillisecondKey = 'T';

void keypress(int vk) {
	keybd_event(vk, 0, 0, 0); // keydown 按下
	Sleep(KeyUpDownInterval);
	keybd_event(vk, 0, KEYEVENTF_KEYUP, 0);  // keyup 起来
}
void enterpress() { keypress(VK_RETURN); }  // 模拟回车键
void configMethod() {


	string s = "3000";
	string* r = &s;
	while (1) {
		if (KEY_DOWN(VK_SPACE)) {//VK_SPACE 是空格的虚拟键值  
			choose = 0;
			Sleep(KeyUpDownInterval);//你的手不会再一瞬间送开,所以要处理一下 
		}
		if (KEY_DOWN(MouseLeftClickStartKey)) { choose = MouseLeftClickStartKey;			Sleep(KeyUpDownInterval); }
		if (KEY_DOWN(MouseRightClickStartKey)) { choose = MouseRightClickStartKey;			Sleep(KeyUpDownInterval); }
		if (KEY_DOWN(EnterpressStartKey)) { choose = EnterpressStartKey;			Sleep(KeyUpDownInterval); }

		if (KEY_DOWN(SetIntervalMillisecondKey)) {


			cout << "当前时间间隔" << interval - KeyUpDownInterval << "毫秒   " << endl;
			cout << "   请输入时间: 单位毫秒" << endl;

			try { cin.end;   cin >> s; }
			catch (exception exception) { cout << exception.what(); }



			cout << "输入的内容是 : " << s << endl;
			interval = atoi(s.c_str());
			if (interval < KeyUpDownInterval || interval >99999)interval = KeyUpDownInterval + 1;
			cout << "当前时间间隔" << interval- KeyUpDownInterval << "毫秒   " << endl;
			printf("按   空格   键停止\n");
			
			Sleep(KeyUpDownInterval);
		}
		Sleep(KeyUpDownInterval);
	}
}

int main() {


	::thread thread(configMethod);

	printf("按   空格   键停止\n");
	cout << "按   " << MouseLeftClickStartKey << "   开始鼠标左键点击" << endl;
	cout << "按   " << MouseRightClickStartKey << "   开始鼠标右键点击" << endl;
	cout << "按   " << EnterpressStartKey << "   开始Enter键点击" << endl;
	cout << "按   " << SetIntervalMillisecondKey << "    设置时间间隔 单位毫秒" << endl;



	while (1) {

		if (choose == MouseLeftClickStartKey) {//模拟点击左键 
			mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);
			mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
		}
		if (choose == MouseRightClickStartKey) {//模拟点击右键 
			mouse_event(MOUSEEVENTF_RIGHTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);
			mouse_event(MOUSEEVENTF_RIGHTUP, 0, 0, 0, 0);
		}
		if (choose == EnterpressStartKey) {  //Enter
			enterpress();
		}
		if (interval < KeyUpDownInterval || interval >99999)interval = KeyUpDownInterval + 1;
		Sleep(interval - KeyUpDownInterval);//点击间隔 单位是毫秒 
	}
}
           

带正则验证的命令行版

Visual C C++ studio2019 自制鼠标点击器,窗口版和命令行版 210325一 窗口版二 命令行版
#include <iostream>
#include<regex>
#include<windows.h>
#include <thread>

#define KEY_DOWN(VK_NONAME) ((GetAsyncKeyState(VK_NONAME) & 0x8000) ? 1:0) 

using namespace std;


static int interval = 3000;  // 连击间隔时间 单位毫秒
string s = "3000";
char charArray100[100];
const int KeyUpDownInterval = 1;  //按下与弹起的间隔 单位毫秒
static int choose = 0;
static regex regexNotDigit("\\D");

const char ExitKey = 'X';
const char MouseLeftClickStartKey = 'L';
const char MouseRightClickStartKey = 'R';
const char EnterpressStartKey = 'E';
const char SetIntervalMillisecondKey = 'T';

void keypress(int vk) {
	keybd_event(vk, 0, 0, 0); // keydown 按下
	Sleep(KeyUpDownInterval);
	keybd_event(vk, 0, KEYEVENTF_KEYUP, 0);  // keyup 起来
}

void enterpress() { keypress(VK_RETURN); }  // 模拟回车键


void hint() {
	printf("按   空格   键停止\n");
	cout << "按   " << MouseLeftClickStartKey << "   开始鼠标左键点击" << endl;
	cout << "按   " << MouseRightClickStartKey << "   开始鼠标右键点击" << endl;
	cout << "按   " << EnterpressStartKey << "   开始Enter键点击" << endl;
	cout << "按   " << SetIntervalMillisecondKey << "   设置时间间隔 单位毫秒" << endl;
	cout << "按   " << ExitKey << "   退出" << endl;
}

void controlKeyListen() {

	while (1) {
		if (choose == ExitKey) { return; }
		if (KEY_DOWN(VK_SPACE)) { 	choose = 0;	Sleep(KeyUpDownInterval);		}  //VK_SPACE 是空格的虚拟键值    暂停点击
		if (KEY_DOWN(MouseLeftClickStartKey)) { choose = MouseLeftClickStartKey;			Sleep(KeyUpDownInterval); }
		if (KEY_DOWN(MouseRightClickStartKey)) { choose = MouseRightClickStartKey;			Sleep(KeyUpDownInterval); }
		if (KEY_DOWN(EnterpressStartKey)) { choose = EnterpressStartKey;			Sleep(KeyUpDownInterval); }

		if (KEY_DOWN(SetIntervalMillisecondKey)) {  //设置间隔时间
			cout << "当前时间间隔" << interval - KeyUpDownInterval << "毫秒   " << endl;
			cout << "   请移除非数字(如果有的话),并输入时间: 单位毫秒" << endl;

			cin.getline(charArray100, 100);  s = charArray100;  cout << "输入的内容是 : " << s << endl;
			// regex_replace(字符串, 正则表达式,替换后的字符串部分)函数,它返回一个string字符串对象
			s = regex_replace(s, regexNotDigit, "");

			cout << "替换后的输入的内容是 : " << s << endl;
			interval = atoi(s.c_str());
			if (interval < KeyUpDownInterval || interval >999999999)interval = KeyUpDownInterval + 1;
			cout << "当前时间间隔" << interval << "毫秒   " << endl;
			hint();
			
			Sleep(KeyUpDownInterval);
		}
		if (KEY_DOWN(ExitKey)) { choose = ExitKey;	 } 
		Sleep(KeyUpDownInterval);
	}
}

int main() {
	
	thread ControlKeyListenThread(controlKeyListen);  // 键盘监听线程
	
	hint();

	while (1) {
		if (choose == ExitKey) { ControlKeyListenThread.join();  break; }  //退出程序
		if (choose == MouseLeftClickStartKey) {//模拟点击左键 
			mouse_event(MOUSEEVENTF_LEFTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);
			mouse_event(MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
		}
		if (choose == MouseRightClickStartKey) {//模拟点击右键 
			mouse_event(MOUSEEVENTF_RIGHTDOWN, 0, 0, 0, 0);
			Sleep(KeyUpDownInterval);
			mouse_event(MOUSEEVENTF_RIGHTUP, 0, 0, 0, 0);
		}
		if (choose == EnterpressStartKey) {  //Enter
			enterpress();
		}
		if (interval < KeyUpDownInterval || interval >999999999)interval = KeyUpDownInterval + 1;
		Sleep(interval - KeyUpDownInterval);//点击间隔 单位是毫秒 
	}
	
}
           

初始参考

继续阅读