经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » Python » 查看文章
Python开发游戏自动化后台脚本的实现
来源:jb51  时间:2022/1/19 11:43:57  对本文有异议

前言

前段时间沉迷猪场一梦江湖,由于实在太肝便萌生出用脚本做日常的想法,写了第一个test.py,随着后来各种功能的逐步添加,脚本也从前台变成了支持后台静默运行,功能渐渐完善,包括了常用的

1.鼠标左键单击指定坐标
2.识别并单击指定图像
3.识别图像中文字
4.后台截取程序画面以供识别
5.鼠标滚轮上下滚动
6.鼠标左键范围点击以防检测
7.程序中的键盘控制
8.程序中字符的输入

说明

获取窗口句柄

寻找标题为title的窗口,激活该窗口并置于x_coor, y_coor处,title可利用visual studio的spy++.exe查看;SWP_NOSIZE指定了窗口大小不变

  1. def get_winds(self, title: str):
  2. ? ? """
  3. ? ? @description : 获取游戏句柄 ,并把游戏窗口置顶并激活窗口
  4. ? ? ---------
  5. ? ? @param : 窗口名
  6. ? ? -------
  7. ? ? @Returns : 窗口句柄
  8. ? ? -------
  9. ? ? """
  10. ? ? # self.__handle = win32gui.FindWindowEx(0, 0, "Qt5QWindowIcon", "MuMu模拟器")
  11. ? ? self.__handle = windll.user32.FindWindowW(None, title)
  12. ? ? self.__classname = win32gui.GetClassName(self.__handle)
  13. ? ? # print(self.__classname)
  14. ? ? if self.__classname == 'Qt5QWindowIcon':
  15. ? ? ? ? self.__mainhandle = win32gui.FindWindowEx(self.__handle, 0, "Qt5QWindowIcon", "MainWindowWindow")
  16. ? ? ? ? # print(self.__mainhandle)
  17. ? ? ? ? self.__centerhandle = win32gui.FindWindowEx(self.__mainhandle, 0, "Qt5QWindowIcon", "CenterWidgetWindow")
  18. ? ? ? ? # print(self.__centerhandle)
  19. ? ? ? ? self.__renderhandle = win32gui.FindWindowEx(self.__centerhandle, 0, "Qt5QWindowIcon", "RenderWindowWindow")
  20. ? ? ? ? # print(self.__renderhandle)
  21. ? ? ? ? self.__clickhandle = self.__renderhandle
  22. ? ? else:
  23. ? ? ? ? self.__clickhandle = self.__handle
  24. ? ? # self.__subhandle = win32gui.FindWindowEx(self.__renderhandle, 0, "subWin", "sub")
  25. ? ? # print(self.__subhandle)
  26. ? ? # self.__subsubhandle = win32gui.FindWindowEx(self.__subhandle, 0, "subWin", "sub")
  27. ? ? # print(self.__subsubhandle)
  28. ? ? # win32gui.ShowWindow(hwnd1, win32con.SW_RESTORE)
  29. ? ? # print(win32gui.GetWindowRect(hwnd1))
  30. ? ? win32gui.SetWindowPos(self.__handle, win32con.HWND_TOP, x_coor, y_coor, 0, 0, win32con.SWP_SHOWWINDOW | win32con.SWP_NOSIZE)
  31. ? ? print(self.__clickhandle)
  32. ? ? return self.__handle

获得后台窗口截图

窗口上方有39个像素的边框,左、右、下则有8个像素的边框

  1. def get_src(self):
  2. ? ? """
  3. ? ? @description : 获得后台窗口截图
  4. ? ? ---------
  5. ? ? @param : None
  6. ? ? -------
  7. ? ? @Returns : None
  8. ? ? -------
  9. ? ? """
  10.  
  11. ? ? left, top, right, bot = win32gui.GetWindowRect(self.__handle)
  12. ? ? #Remove border around window (8 pixels on each side)
  13. ? ? bl = 8
  14. ? ? #Remove border on top
  15. ? ? bt = 39
  16.  
  17. ? ? width = int((right - left + 1) * scale) - 2 * bl
  18. ? ? height = int((bot - top + 1) * scale) - bt - bl
  19. ? ? # 返回句柄窗口的设备环境,覆盖整个窗口,包括非客户区,标题栏,菜单,边框
  20. ? ? hWndDC = win32gui.GetWindowDC(self.__handle)
  21. ? ? # 创建设备描述表
  22. ? ? mfcDC = win32ui.CreateDCFromHandle(hWndDC)
  23. ? ? # 创建内存设备描述表
  24. ? ? saveDC = mfcDC.CreateCompatibleDC()
  25. ? ? # 创建位图对象准备保存图片
  26. ? ? saveBitMap = win32ui.CreateBitmap()
  27. ? ? # 为bitmap开辟存储空间
  28. ? ? saveBitMap.CreateCompatibleBitmap(mfcDC, width, height)
  29. ? ? # 将截图保存到saveBitMap中
  30. ? ? saveDC.SelectObject(saveBitMap)
  31. ? ? # 保存bitmap到内存设备描述表
  32. ? ? saveDC.BitBlt((0, 0), (width, height), mfcDC, (bl, bt), win32con.SRCCOPY)
  33. ? ? ###获取位图信息
  34. ? ? bmpinfo = saveBitMap.GetInfo()
  35. ? ? bmpstr = saveBitMap.GetBitmapBits(True)
  36. ? ? ###生成图像
  37. ? ? im_PIL = Image.frombuffer('RGB', (bmpinfo['bmWidth'], bmpinfo['bmHeight']), bmpstr, 'raw', 'BGRX', 0, 1)
  38. ? ? # 内存释放
  39. ? ? win32gui.DeleteObject(saveBitMap.GetHandle())
  40. ? ? saveDC.DeleteDC()
  41. ? ? mfcDC.DeleteDC()
  42. ? ? win32gui.ReleaseDC(self.__handle, hWndDC)
  43. ? ? ###PrintWindow成功,保存到文件,显示到屏幕
  44. ? ? im_PIL.save("src.jpg") ?# 保存
  45. ? ? # im_PIL.show() ?# 显示

数字识别

依赖项——Tesseract OCR
下载并添加至系统环境变量

注意:这里将ocr识别范围限定为0-9的数字以提高准确率
截取范围为src.jpg中左上(x1,y1)到右下(x2,y2)的矩形区域

  1. def get_num(self, x1, y1, x2, y2):
  2. ? ? """
  3. ? ? @description : 获取屏幕截图中的数字
  4. ? ? ---------
  5. ? ? @param : 截图中需要截取的含数字部分边界
  6. ? ? -------
  7. ? ? @Returns : num:int
  8. ? ? -------
  9. ? ? """
  10. ? ? ? ??
  11. ? ? img = Image.open("src.jpg")
  12. ? ? num_img = img.crop((x1, y1, x2, y2))
  13. ? ? num_img = ImageOps.invert(num_img)
  14. ? ? num = pytesseract.image_to_string(num_img, lang="eng",
  15. ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? config='--psm 6 --oem 3 -c tessedit_char_whitelist=0123456789').strip()
  16. ? ? # num = pytesseract.image_to_string(num_img, lang="eng")
  17. ? ? try:
  18. ? ? ? ? print("数量为", int(num))
  19. ? ? ? ? return int(num)
  20. ? ? except:
  21. ? ? ? ? print("未检测到数字")
  22. ? ? ? ? return 0

识别并点击图片位置

所需识别的图片模板事先准备好并放在同一目录下,输入图片文件路径
这里confidence设置为0.9

  1. def mouse_click_image(self, name : str, times = 0.5):
  2. ? ? """
  3. ? ? @Description : 鼠标左键点击识别到的图片位置
  4. ? ? ---------
  5. ? ? @Args : name:输入图片名; times:单击后延时
  6. ? ? -------
  7. ? ? @Returns : None
  8. ? ? -------
  9. ? ? """
  10. ? ? try:
  11. ? ? ? ? result = self.recognize(name)
  12. ? ? ? ? if result is None or result['confidence'] < 0.9:
  13. ? ? ? ? ? ? print("No results!")
  14. ? ? ? ? else:
  15. ? ? ? ? ? ? print(result['result'][0] + x_coor * scale + 8, " ",result['result'][1] + y_coor * scale + 39)
  16. ? ? ? ? ? ? self.mouse_click(result['result'][0] + x_coor * scale + 8, result['result'][1] + y_coor * scale + 39)
  17. ? ? except:
  18. ? ? ? ? raise Exception("error")

后台文字输入

  1. def type_str(self, msg: str):
  2. """
  3. @Description : 打字
  4. ---------
  5. @Args : msg:目标字符
  6. -------
  7. @Returns : None
  8. -------
  9. """
  10. for i in msg:
  11. self.__PostMessageW(self.__handle, win32con.WM_CHAR, ord(i), 0)

完整代码

GITEE网址: 项目-AutoClick.

  1. #!/usr/bin/env python
  2. # -*- encoding: utf-8 -*-
  3. '''
  4. @File : AutoClick.py
  5. @Time : 2021/10/09 15:10:01
  6. @Author : Yaadon
  7. '''
  8.  
  9. # here put the import lib
  10. import win32con
  11. import win32gui
  12. import win32ui
  13. import time
  14. # import threading
  15. import numpy as np
  16. import os
  17. from PIL import Image
  18. from PIL import ImageOps
  19. import aircv as ac
  20. import pytesseract
  21. from ctypes import windll, byref
  22. from ctypes.wintypes import HWND, POINT
  23. import string
  24. # import sys
  25. # import cv2
  26. # from memory_pic import *
  27. # import win32api
  28. # import autopy
  29. # from PIL import ImageGrab
  30.  
  31. scale = 1.25 # 电脑的缩放比例
  32. radius = 5 # 随机半径
  33. x_coor = 10 # 窗口位置
  34. y_coor = 10 # 窗口位置
  35.  
  36. class AutoClick():
  37. """
  38. @description :自动点击类,包含后台截图、图像匹配
  39. ---------
  40. @param :
  41. -------
  42. @Returns :
  43. -------
  44. """
  45. __PostMessageW = windll.user32.PostMessageW
  46. __SendMessageW = windll.user32.SendMessageW
  47. __MapVirtualKeyW = windll.user32.MapVirtualKeyW
  48. __VkKeyScanA = windll.user32.VkKeyScanA
  49. __ClientToScreen = windll.user32.ClientToScreen
  50.  
  51. __WM_KEYDOWN = 0x100
  52. __WM_KEYUP = 0x101
  53. __WM_MOUSEMOVE = 0x0200
  54. __WM_LBUTTONDOWN = 0x0201
  55. __WM_LBUTTONUP = 0x202
  56. __WM_MOUSEWHEEL = 0x020A
  57. __WHEEL_DELTA = 120
  58. __WM_SETCURSOR = 0x20
  59. __WM_MOUSEACTIVATE = 0x21
  60.  
  61. __HTCLIENT = 1
  62. __MA_ACTIVATE = 1
  63.  
  64. __VkCode = {
  65. "back": 0x08,
  66. "tab": 0x09,
  67. "return": 0x0D,
  68. "shift": 0x10,
  69. "control": 0x11,
  70. "menu": 0x12,
  71. "pause": 0x13,
  72. "capital": 0x14,
  73. "escape": 0x1B,
  74. "space": 0x20,
  75. "end": 0x23,
  76. "home": 0x24,
  77. "left": 0x25,
  78. "up": 0x26,
  79. "right": 0x27,
  80. "down": 0x28,
  81. "print": 0x2A,
  82. "snapshot": 0x2C,
  83. "insert": 0x2D,
  84. "delete": 0x2E,
  85. "lwin": 0x5B,
  86. "rwin": 0x5C,
  87. "numpad0": 0x60,
  88. "numpad1": 0x61,
  89. "numpad2": 0x62,
  90. "numpad3": 0x63,
  91. "numpad4": 0x64,
  92. "numpad5": 0x65,
  93. "numpad6": 0x66,
  94. "numpad7": 0x67,
  95. "numpad8": 0x68,
  96. "numpad9": 0x69,
  97. "multiply": 0x6A,
  98. "add": 0x6B,
  99. "separator": 0x6C,
  100. "subtract": 0x6D,
  101. "decimal": 0x6E,
  102. "divide": 0x6F,
  103. "f1": 0x70,
  104. "f2": 0x71,
  105. "f3": 0x72,
  106. "f4": 0x73,
  107. "f5": 0x74,
  108. "f6": 0x75,
  109. "f7": 0x76,
  110. "f8": 0x77,
  111. "f9": 0x78,
  112. "f10": 0x79,
  113. "f11": 0x7A,
  114. "f12": 0x7B,
  115. "numlock": 0x90,
  116. "scroll": 0x91,
  117. "lshift": 0xA0,
  118. "rshift": 0xA1,
  119. "lcontrol": 0xA2,
  120. "rcontrol": 0xA3,
  121. "lmenu": 0xA4,
  122. "rmenu": 0XA5
  123. }
  124.  
  125. def __get_virtual_keycode(self, key: str):
  126. """根据按键名获取虚拟按键码
  127.  
  128. Args:
  129. key (str): 按键名
  130.  
  131. Returns:
  132. int: 虚拟按键码
  133. """
  134. if len(key) == 1 and key in string.printable:
  135. # https://docs.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-vkkeyscana
  136. return self.__VkKeyScanA(ord(key)) & 0xff
  137. else:
  138. return self.__VkCode[key]
  139.  
  140.  
  141. def __key_down(self, handle: HWND, key: str):
  142. """按下指定按键
  143.  
  144. Args:
  145. handle (HWND): 窗口句柄
  146. key (str): 按键名
  147. """
  148. vk_code = self.__get_virtual_keycode(key)
  149. scan_code = self.__MapVirtualKeyW(vk_code, 0)
  150. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-keydown
  151. wparam = vk_code
  152. lparam = (scan_code << 16) | 1
  153. self.__PostMessageW(handle, self.__WM_KEYDOWN, wparam, lparam)
  154.  
  155.  
  156. def __key_up(self, handle: HWND, key: str):
  157. """放开指定按键
  158.  
  159. Args:
  160. handle (HWND): 窗口句柄
  161. key (str): 按键名
  162. """
  163. vk_code = self.__get_virtual_keycode(key)
  164. scan_code = self.__MapVirtualKeyW(vk_code, 0)
  165. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-keyup
  166. wparam = vk_code
  167. lparam = (scan_code << 16) | 0XC0000001
  168. self.__PostMessageW(handle, self.__WM_KEYUP, wparam, lparam)
  169.  
  170.  
  171. def __activate_mouse(self, handle: HWND):
  172. """
  173. @Description : 激活窗口接受鼠标消息
  174. ---------
  175. @Args : handle (HWND): 窗口句柄
  176. -------
  177. @Returns :
  178. -------
  179. """
  180. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-mouseactivate
  181. lparam = (self.__WM_LBUTTONDOWN << 16) | self.__HTCLIENT
  182. self.__SendMessageW(handle, self.__WM_MOUSEACTIVATE, self.__handle, lparam)
  183.  
  184. def __set_cursor(self, handle: HWND, msg):
  185. """
  186. @Description : Sent to a window if the mouse causes the cursor to move within a window and mouse input is not captured
  187. ---------
  188. @Args : handle (HWND): 窗口句柄, msg : setcursor消息
  189. -------
  190. @Returns :
  191. -------
  192. """
  193. # https://docs.microsoft.com/en-us/windows/win32/menurc/wm-setcursor
  194. lparam = (msg << 16) | self.__HTCLIENT
  195. self.__SendMessageW(handle, self.__WM_SETCURSOR, handle, lparam)
  196.  
  197. def __move_to(self, handle: HWND, x: int, y: int):
  198. """移动鼠标到坐标(x, y)
  199.  
  200. Args:
  201. handle (HWND): 窗口句柄
  202. x (int): 横坐标
  203. y (int): 纵坐标
  204. """
  205. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-mousemove
  206. wparam = 0
  207. lparam = y << 16 | x
  208. self.__PostMessageW(handle, self.__WM_MOUSEMOVE, wparam, lparam)
  209.  
  210.  
  211. def __left_down(self, handle: HWND, x: int, y: int):
  212. """在坐标(x, y)按下鼠标左键
  213.  
  214. Args:
  215. handle (HWND): 窗口句柄
  216. x (int): 横坐标
  217. y (int): 纵坐标
  218. """
  219. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-lbuttondown
  220. wparam = 0x001 # MK_LBUTTON
  221. lparam = y << 16 | x
  222. self.__PostMessageW(handle, self.__WM_LBUTTONDOWN, wparam, lparam)
  223.  
  224.  
  225. def __left_up(self, handle: HWND, x: int, y: int):
  226. """在坐标(x, y)放开鼠标左键
  227.  
  228. Args:
  229. handle (HWND): 窗口句柄
  230. x (int): 横坐标
  231. y (int): 纵坐标
  232. """
  233. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-lbuttonup
  234. wparam = 0
  235. lparam = y << 16 | x
  236. self.__PostMessageW(handle, self.__WM_LBUTTONUP, wparam, lparam)
  237.  
  238.  
  239. def __scroll(self, handle: HWND, delta: int, x: int, y: int):
  240. """在坐标(x, y)滚动鼠标滚轮
  241.  
  242. Args:
  243. handle (HWND): 窗口句柄
  244. delta (int): 为正向上滚动,为负向下滚动
  245. x (int): 横坐标
  246. y (int): 纵坐标
  247. """
  248. self.__move_to(handle, x, y)
  249. # https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-mousewheel
  250. wparam = delta << 16
  251. p = POINT(x, y)
  252. self.__ClientToScreen(handle, byref(p))
  253. lparam = p.y << 16 | p.x
  254. self.__PostMessageW(handle, self.__WM_MOUSEWHEEL, wparam, lparam)
  255.  
  256.  
  257. def __scroll_up(self, handle: HWND, x: int, y: int):
  258. """在坐标(x, y)向上滚动鼠标滚轮
  259.  
  260. Args:
  261. handle (HWND): 窗口句柄
  262. x (int): 横坐标
  263. y (int): 纵坐标
  264. """
  265. self.__scroll(handle, self.__WHEEL_DELTA, x, y)
  266.  
  267.  
  268. def __scroll_down(self, handle: HWND, x: int, y: int):
  269. """在坐标(x, y)向下滚动鼠标滚轮
  270.  
  271. Args:
  272. handle (HWND): 窗口句柄
  273. x (int): 横坐标
  274. y (int): 纵坐标
  275. """
  276. self.__scroll(handle, -self.__WHEEL_DELTA, x, y)
  277.  
  278.  
  279. def get_winds(self, title: str):
  280. """
  281. @description : 获取游戏句柄 ,并把游戏窗口置顶并激活窗口
  282. ---------
  283. @param : 窗口名
  284. -------
  285. @Returns : 窗口句柄
  286. -------
  287. """
  288. # self.__handle = win32gui.FindWindowEx(0, 0, "Qt5QWindowIcon", "MuMu模拟器")
  289. self.__handle = windll.user32.FindWindowW(None, title)
  290. self.__classname = win32gui.GetClassName(self.__handle)
  291. # print(self.__classname)
  292. if self.__classname == 'Qt5QWindowIcon':
  293. self.__mainhandle = win32gui.FindWindowEx(self.__handle, 0, "Qt5QWindowIcon", "MainWindowWindow")
  294. # print(self.__mainhandle)
  295. self.__centerhandle = win32gui.FindWindowEx(self.__mainhandle, 0, "Qt5QWindowIcon", "CenterWidgetWindow")
  296. # print(self.__centerhandle)
  297. self.__renderhandle = win32gui.FindWindowEx(self.__centerhandle, 0, "Qt5QWindowIcon", "RenderWindowWindow")
  298. # print(self.__renderhandle)
  299. self.__clickhandle = self.__renderhandle
  300. else:
  301. self.__clickhandle = self.__handle
  302. # self.__subhandle = win32gui.FindWindowEx(self.__renderhandle, 0, "subWin", "sub")
  303. # print(self.__subhandle)
  304. # self.__subsubhandle = win32gui.FindWindowEx(self.__subhandle, 0, "subWin", "sub")
  305. # print(self.__subsubhandle)
  306. # win32gui.ShowWindow(hwnd1, win32con.SW_RESTORE)
  307. # print(win32gui.GetWindowRect(hwnd1))
  308. win32gui.SetWindowPos(self.__handle, win32con.HWND_TOP, x_coor, y_coor, 0, 0, win32con.SWP_SHOWWINDOW | win32con.SWP_NOSIZE)
  309. print(self.__clickhandle)
  310. return self.__handle
  311.  
  312. def get_src(self):
  313. """
  314. @description : 获得后台窗口截图
  315. ---------
  316. @param : None
  317. -------
  318. @Returns : None
  319. -------
  320. """
  321.  
  322. left, top, right, bot = win32gui.GetWindowRect(self.__handle)
  323. #Remove border around window (8 pixels on each side)
  324. bl = 8
  325. #Remove border on top
  326. bt = 39
  327.  
  328. width = int((right - left + 1) * scale) - 2 * bl
  329. height = int((bot - top + 1) * scale) - bt - bl
  330. # 返回句柄窗口的设备环境,覆盖整个窗口,包括非客户区,标题栏,菜单,边框
  331. hWndDC = win32gui.GetWindowDC(self.__handle)
  332. # 创建设备描述表
  333. mfcDC = win32ui.CreateDCFromHandle(hWndDC)
  334. # 创建内存设备描述表
  335. saveDC = mfcDC.CreateCompatibleDC()
  336. # 创建位图对象准备保存图片
  337. saveBitMap = win32ui.CreateBitmap()
  338. # 为bitmap开辟存储空间
  339. saveBitMap.CreateCompatibleBitmap(mfcDC, width, height)
  340. # 将截图保存到saveBitMap中
  341. saveDC.SelectObject(saveBitMap)
  342. # 保存bitmap到内存设备描述表
  343. saveDC.BitBlt((0, 0), (width, height), mfcDC, (bl, bt), win32con.SRCCOPY)
  344. ###获取位图信息
  345. bmpinfo = saveBitMap.GetInfo()
  346. bmpstr = saveBitMap.GetBitmapBits(True)
  347. ###生成图像
  348. im_PIL = Image.frombuffer('RGB', (bmpinfo['bmWidth'], bmpinfo['bmHeight']), bmpstr, 'raw', 'BGRX', 0, 1)
  349. # 内存释放
  350. win32gui.DeleteObject(saveBitMap.GetHandle())
  351. saveDC.DeleteDC()
  352. mfcDC.DeleteDC()
  353. win32gui.ReleaseDC(self.__handle, hWndDC)
  354. ###PrintWindow成功,保存到文件,显示到屏幕
  355. im_PIL.save("src.jpg") # 保存
  356. # im_PIL.show() # 显示
  357.  
  358.  
  359. def recognize(self, objs):
  360. """
  361. @description : 图像识别之模板匹配
  362. ---------
  363. @param : 需要匹配的模板名
  364. -------
  365. @Returns : 将传进来的图片和全屏截图匹配如果找到就返回图像在屏幕的坐标 否则返回None
  366. -------
  367. """
  368. imobj = ac.imread(objs)
  369. imsrc = ac.imread('%s\\src.jpg' % os.getcwd())
  370. pos = ac.find_template(imsrc, imobj, 0.5)
  371. return pos
  372.  
  373.  
  374. def mouse_click(self, x, y, times=0.5):
  375. """
  376. @description : 单击左键
  377. ---------
  378. @param : 位置坐标x,y 单击后延时times(s)
  379. -------
  380. @Returns :
  381. -------
  382. """
  383. # self.__set_cursor(self.__clickhandle, self.__WM_MOUSEACTIVATE)
  384. # self.__move_to(self.__clickhandle, int(x / scale), int(y / scale))
  385. # self.__activate_mouse(self.__clickhandle)
  386. # self.__set_cursor(self.__clickhandle, self.__WM_LBUTTONDOWN)
  387. self.__left_down(self.__clickhandle, int(x / scale), int(y / scale))
  388. self.__move_to(self.__clickhandle, int(x / scale), int(y / scale))
  389. self.__left_up(self.__clickhandle, int(x / scale), int(y / scale))
  390. time.sleep(times)
  391.  
  392. def mouse_click_image(self, name : str, times = 0.5):
  393. """
  394. @Description : 鼠标左键点击识别到的图片位置
  395. ---------
  396. @Args : name:输入图片名; times:单击后延时
  397. -------
  398. @Returns : None
  399. -------
  400. """
  401. try:
  402. result = self.recognize(name)
  403. if result is None or result['confidence'] < 0.9:
  404. print("No results!")
  405. else:
  406. print(result['result'][0] + x_coor * scale + 8, " ",result['result'][1] + y_coor * scale + 39)
  407. self.mouse_click(result['result'][0] + x_coor * scale + 8, result['result'][1] + y_coor * scale + 39)
  408. except:
  409. raise Exception("error")
  410.  
  411. def mouse_click_radius(self, x, y, times=0.5):
  412. """
  413. @description : 在范围内随机位置单击(防检测)
  414. ---------
  415. @param : 位置坐标x,y 单击后延时times(s)
  416. -------
  417. @Returns :
  418. -------
  419. """
  420. random_x = np.random.randint(-radius, radius)
  421. random_y = np.random.randint(-radius, radius)
  422. self.mouse_click(x + random_x, y + random_y)
  423. # self.__left_down(self.__clickhandle, int((x + random_x) / scale), int((y + random_y) / scale))
  424. # time.sleep(0.1)
  425. # self.__left_up(self.__clickhandle, int((x + random_x) / scale), int((y + random_y) / scale))
  426. time.sleep(times)
  427.  
  428.  
  429. def push_key(self, key: str, times = 1):
  430. """
  431. @Description : 按键
  432. ---------
  433. @Args : key:按键 times:按下改键后距松开的延时
  434. -------
  435. @Returns : None
  436. -------
  437. """
  438. self.__key_down(self.__clickhandle, key)
  439. time.sleep(times)
  440. self.__key_up(self.__clickhandle, key)
  441. time.sleep(0.5)
  442.  
  443. def type_str(self, msg: str):
  444. """
  445. @Description : 打字
  446. ---------
  447. @Args : msg:目标字符
  448. -------
  449. @Returns : None
  450. -------
  451. """
  452. for i in msg:
  453. self.__PostMessageW(self.__clickhandle, win32con.WM_CHAR, ord(i), 0)
  454.  
  455.  
  456. if __name__ == '__main__':
  457. click = AutoClick()
  458. click.get_winds("微信")
  459. click.get_src()
  460. # click.mouse_click(254, 536)
  461. click.mouse_click_image('test.png')
  462. # click.mouse_click(1086, 269) # 输入框
  463. # click.mouse_click(237, 211) # 输入框
  464. # click.mouse_click(1228, 201) # 输入框
  465. # click.type_str("123木头人abc")

参考

部分参考自: Python开发游戏自动化脚本(四)后台键鼠操作.

到此这篇关于Python开发游戏自动化后台脚本的实现的文章就介绍到这了,更多相关Python 游戏自动化后台脚本内容请搜索w3xue以前的文章或继续浏览下面的相关文章希望大家以后多多支持w3xue!

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号