意义与演示
众所周知群星mods多如星辰,并且不同mods还要考虑排序问题,好在有先人已做了排序实验,我们只需根据大佬的排序清单进行排列即可,不幸的是p社启动器存在一些(很多)问题
每每进行手动排序都感觉自己像个猿人,于是打算做一份模拟鼠标点击的自动排序程序,最终效果如下
群星mods自动排序c++
前置工作
1.大佬的排序文件
只要可以转文本的,什么都行,本文用的json如下
2.c++基础知识
3.已安装好的mods
代码
头文件
#include “mouse_click.h”
#pragma once
#include <Windows.h>
#include<string>
//模拟鼠标事件
class mouse_click
{
public:
//初始化
void init(int x,int y);
//点击查找按钮
void click_find();
//点击选择框位置
void click_seclect();
//粘贴文本
void paste();
//复制到粘贴板
void copy(std::string str);
//启动器初始位置
int pos_inti_x = 0, pos_inti_y = 0;
//启动器选择框位置
int pos_select_x = 1426 + pos_inti_x, pos_select_y = 254 + pos_inti_y;
//启动器查找建位置
int pos_find_x = 1312 + pos_inti_x, pos_find_y = 111 + pos_inti_y;
};
源文件
#include “mouse_click.cpp”
#include "mouse_click.h"
void mouse_click:: init(int x, int y) {
pos_inti_x = x;
pos_inti_y = y;
//鼠标绝对值移动+按下松开事件,屏幕分65536*65536大小,本屏幕为2560*1440
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, pos_inti_x * 65536 / 2560, pos_inti_y * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
Sleep(200);
}
void mouse_click::click_find() {
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, pos_find_x * 65536 / 2560, pos_find_y * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
Sleep(200);
}
void mouse_click::click_seclect() {
//如果mod在最下面只点一下会点不到,所以就把一流全点了
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, pos_select_x * 65536 / 2560, pos_select_y * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, 1424 * 65536 / 2560, 331 * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, 1424 * 65536 / 2560, 451 * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, 1425 * 65536 / 2560, 552 * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, 1425 * 65536 / 2560, 662 * 65536 / 1440, 0, 0);
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, 0, 0, 0, 0);
}
void mouse_click::paste() {
//粘贴
keybd_event(17, 0, 0, 0);//按下ctril键
keybd_event('V', 0, 0, 0);//按下V键
Sleep(100);
keybd_event('V', 0, KEYEVENTF_KEYUP, 0);//松开V键
keybd_event(17, 0, KEYEVENTF_KEYUP, 0);//松开ctril键
Sleep(1500);
}
void mouse_click::copy(std::string str) {
//复制到剪贴板
OpenClipboard(NULL);//打开剪切板
EmptyClipboard();//清空剪切板
HANDLE hHandle = GlobalAlloc(GMEM_FIXED, 1000);//分配内存
char* pData = (char*)GlobalLock(hHandle);//锁定内存,返回申请内存的首地址
strcpy_s(pData, 1000, str.c_str());
SetClipboardData(CF_TEXT, hHandle);//设置剪切板数据
GlobalUnlock(hHandle);//解除锁定
CloseClipboard();//关闭剪切板
}
main.cpp
#include <iostream>
#include <windows.h>
#include<json/json.h>
#include <fstream>
#include <conio.h>
#include"mouse_click.h"
using namespace std;
//utf8转换gbk
string UTF8ToGB(const char* str)
{
string result;
WCHAR* strSrc;
LPSTR szRes;
int i = MultiByteToWideChar(CP_UTF8, 0, str, -1, NULL, 0);
strSrc = new WCHAR[i + 1];
MultiByteToWideChar(CP_UTF8, 0, str, -1, strSrc, i);
i = WideCharToMultiByte(CP_ACP, 0, strSrc, -1, NULL, 0, NULL, NULL);
szRes = new CHAR[i + 1];
WideCharToMultiByte(CP_ACP, 0, strSrc, -1, szRes, i, NULL, NULL);
result = szRes;
delete[]strSrc;
delete[]szRes;
return result;
}
int main() {
//是否退出
bool isrun = true;
Json::Reader reader;
Json::Value root;
mouse_click _mouse;
//从文件中读取,保证当前文件有demo.json文件
ifstream modslist("E:/Down/Stellaris/mods/播放集/战舰少女(阵列).json", ios::binary);
if (reader.parse(modslist, root)) {
int count = root["mods"].size();
_mouse.init(0, 0);
_mouse.click_find();
for (int i = 0; i < count; i++) {
if (_kbhit()) {
isrun = false;
}
if (!isrun)
break;
//json读取mod名称并转化为gbk
Json::Value mod1 = root["mods"][i]["displayName"];
string a = UTF8ToGB(mod1.toStyledString().c_str());
string mod_name(a.begin() + 1, a.end() - 2);
//模拟开始
_mouse.copy(mod_name);
_mouse.click_find();
_mouse.click_find();
_mouse.paste();
_mouse.click_seclect();
}
}
}