用纯文本配置的桌面操作自动化工具:录屏回放、坐标点击、快捷键模拟全支持

该文章已生成可运行项目,

本文还有配套的精品资源,点击获取 menu-r.4af5f7ec.gif

简介:这个工具用Python写成,不依赖图形界面开发框架,靠几个简单文本文件就能驱动整套自动化流程。操作录制器recorder.py能捕获鼠标移动、点击、键盘输入并保存为可编辑的脚本;parser.py负责读取main.txt、repeat.txt等指令文件,按顺序执行动作;coords.txt存屏幕坐标点,实现精准点击和拖拽;keymap.py定义常用快捷键组合,比如Ctrl+C、Alt+Tab;copy-paste.txt和linux-term.txt分别处理剪贴板内容与Linux终端命令交互。所有逻辑由grammar.py语法解析器统一调度,main.py提供命令行入口,setup.py和requirements.txt确保环境一键安装。测试文件如simple_test.py、test_run.py和playlist.txt方便快速验证功能,test目录里还包含多场景用例。整个方案轻量、透明、易调试,适合批量重命名、网页表单填写、UI操作预演、重复性办公任务等日常需求,Windows和Linux基础操作都覆盖,不需要编程经验,改几行文本就能调整行为。

1. 项目概述:为什么我最终放弃了所有GUI自动化框架,转而手写这套纯文本驱动的桌面操作引擎

你有没有过这样的时刻:想让电脑自动完成一个看似简单、却重复到让人抓狂的操作?比如每天上午9:05准时打开某个内部系统,登录后点开三个固定菜单,复制当前日期粘贴进表单第7行,再导出PDF并重命名成“日报_20240523_v2.pdf”——整个流程耗时47秒,但你连续干了23天,手指已经形成肌肉记忆,脑子却开始宕机。这时候你去搜“桌面自动化工具”,首页跳出的全是SikuliX、AutoHotkey、PyAutoGUI、Robot Framework……点进去一看,要么要装Java环境配OpenCV,要么得学一套新语法写脚本,要么在Windows上跑得好好的,一换Linux就报错“无法获取屏幕截图”。更糟的是,当某天UI改版——那个你写了30行代码定位的“提交按钮”从ID #submit-btn 变成了 button[data-action="confirm"],整套逻辑就废了。

我就是这么踩坑踩到第7次之后,决定彻底推倒重来。不碰图像识别,不依赖元素选择器,不写一行GUI控件操作代码。核心思路非常朴素:人怎么操作桌面,我就让程序怎么操作桌面——用最原始的方式记录和回放:坐标、按键、时间戳。 这套工具不是为开发人员写的,是为每天和Excel、浏览器、终端打交道的运营、测试、行政、财务写的。它没有“自动化平台”的架子,就是一个压缩包解压即用的文件夹:里面全是.txt.py,你能用记事本打开、用Excel排序、用Git对比差异、用手机备忘录临时改一行。coords.txt里写着login_button = 842, 416,你拿尺子量一下屏幕就知道它在哪;keymap.py'copy': ['ctrl', 'c'],小学生都能看懂;main.txtclick login_button这一行,比任何YAML配置都直白。它不解决“智能识别”,只解决“确定性复现”——只要你的鼠标能点到的位置,它就能点到;只要你的键盘能按出的组合键,它就能按出;只要你的终端能执行的命令,它就能粘贴执行。它不承诺“永远不坏”,但承诺“坏了立刻能修”:出问题?打开repeat.txt,删掉倒数第三行;坐标偏了?打开coords.txt,把842改成845;快捷键冲突?改keymap.py里那一行就行。整个系统像一台老式机械钟表,齿轮咬合清晰可见,发条松了自己拧紧,不需要送修厂。

关键词“桌面自动化”在这里不是技术术语,而是工作场景描述;“操作录制”不是AI捕捉行为模式,而是真实记录鼠标的每一次移动轨迹;“坐标点击”不是像素级暴力点击,而是通过coords.txt建立语义化坐标别名,让click download_iconclick 1280, 720可维护十倍;“快捷键模拟”不追求毫秒级同步,而是确保press alt_tab真正在前台切换窗口;“Python脚本”只是实现载体,你完全可以把它当成一个高级文本处理器——它的价值不在代码多炫酷,而在你改完main.txt保存后,双击__main__.py,它就真的开始干活了。

2. 整体架构与设计哲学:为什么是纯文本?为什么是Python?为什么拒绝“智能”

2.1 纯文本驱动:不是妥协,而是主动选择

很多人第一眼看到coords.txtmain.txtkeymap.py会疑惑:“为什么不做成图形界面配置?”答案很实在:图形界面配置的本质,是把复杂性从代码转移到UI控件上,但并没有消除复杂性。 一个带坐标的可视化编辑器,需要处理缩放适配、多显示器坐标映射、DPI感知、拖拽精度校准……这些工作量远超写一个文本解析器。而纯文本方案,把所有“状态”显式暴露出来:

  • coords.txt 是一张静态坐标地图:
    ```
    # 登录区域
    username_field = 520, 380
    password_field = 520, 425
    login_button = 640, 480

# 主页导航
reports_tab = 180, 120
export_btn = 1120, 85
`` 你看一眼就知道所有关键点的相对位置,用Excel排序可以快速发现reports_tabexport_btn的Y坐标差只有-35,说明它们在同一水平线附近;用Git diff能清晰看到昨天同事把export_btn1120, 85改成1125, 85`,因为高分屏缩放导致偏移了5像素。

  • main.txt 是一条线性操作流水线:
    wait 2000 click username_field type "admin" click password_field type "pass123" click login_button wait 3000 click reports_tab wait 1000 click export_btn
    它不是编程语言,而是一份操作说明书。wait 2000 意味着“等两秒,让页面加载完”,而不是“等待某个元素出现”——后者需要写XPath或CSS选择器,前者只需要你心里默数“1001、1002……”。

这种设计带来的直接好处是调试成本趋近于零。当流程卡在click reports_tab时,你不需要打开开发者工具查DOM结构,只需要打开coords.txt,确认reports_tab = 180, 120这个坐标在当前屏幕是否真的对应导航栏第一个标签。如果不对,改坐标;如果对,那问题一定出在窗口没激活或被遮挡——这是人眼能立刻判断的物理事实,不是代码逻辑谜题。

提示:coords.txt 支持注释(#开头)和空行,方便分组管理。我习惯按功能模块分段,比如# [文件操作]# [浏览器操作]# [终端操作],这样多人协作时不会互相覆盖坐标定义。

2.2 Python作为胶水层:轻量、跨平台、生态成熟

选Python不是因为它“适合AI”,而是因为它完美匹配这个项目的三个硬需求:轻量启动、跨平台兼容、生态工具链成熟。

  • 轻量启动__main__.py 双击即可运行,无需编译。Python解释器在Windows自带(Win10+)、Linux发行版预装率超95%、macOS也内置。用户不需要知道什么是venvpip install -r requirements.txt 这一行命令,30秒内就能装完所有依赖。对比Node.js需要装npm、Java需要配JDK、Rust需要cargo,Python的“开箱即用”属性无可替代。

  • 跨平台兼容:核心操作层做了明确隔离:

  • 鼠标/键盘底层调用:Windows用pywin32win32api/win32con),Linux用pynputController类),两者API高度一致,parser.py只需调用统一接口mouse.click(x, y),具体实现由platform_adapter.py(虽未在目录树列出,但实际存在于import/子模块中)动态加载。
  • 屏幕坐标获取:Windows用GetCursorPos,Linux用Xlib查询根窗口尺寸,recorder.py录制时自动适配当前平台,生成的坐标值直接写入coords.txt,无需二次转换。
  • 终端交互:linux-term.txt 的设计初衷就是绕过GUI自动化难点。它不尝试“控制终端窗口”,而是利用Linux的xdotoolwmctrl工具(需用户自行安装)将文本内容粘贴到指定窗口标题的终端中。copy-paste.txt 同理,用pyperclip读写系统剪贴板,完全脱离GUI框架。

  • 生态工具链成熟requirements.txt 里只有5个依赖:
    pynput==1.7.6 pyperclip==1.8.2 pywin32==306; sys_platform == 'win32' python-xlib==0.33; sys_platform == 'linux' watchdog==2.3.1
    全部是久经考验的稳定版本。watchdog用于监听main.txt变更实现热重载(test_run.py里演示),pynput提供跨平台输入模拟,pyperclip统一剪贴板操作。没有花哨的深度学习库,没有动辄几百MB的依赖树,整个虚拟环境装完不到15MB。

注意:setup.py 不是用于PyPI发布,而是提供python setup.py develop软链接安装,方便开发者修改源码后立即生效。普通用户直接运行__main__.py即可,setup.py对他们透明。

2.3 拒绝“智能”:确定性优于灵活性

这个项目最反直觉的设计,是主动放弃所有“智能”特性:不支持图像识别、不支持OCR文字提取、不支持动态等待(如“等待元素出现”)、不支持条件分支(if/else)。原因很简单:在日常办公场景中,“智能”带来的不确定性,远大于它节省的那几秒钟。

举个真实例子:某次给客户做表单填写自动化,用SikuliX识别“提交”按钮图标。上线第一天正常,第二天客户把按钮背景色从蓝色改成绿色,识别率暴跌到30%,流程卡死。而用本方案,coords.txtsubmit_btn = 920, 640,只要按钮还在那个物理位置,它就永远能点到。即使UI大改,你最多花2分钟重新录一次坐标,而不是花2小时调参、重训模型。

同理,“动态等待”看似优雅,实则埋雷。wait_for_element("div#loading", timeout=10) 在网络波动时可能等满10秒才继续,而wait 5000 明确告诉你“这里必须停5秒”,你可以根据实际网速调整成wait 3000wait 7000,一切尽在掌握。grammar.py 的语法解析器因此极其简单:它只认7种指令(click, type, press, wait, paste, run, include),每种指令参数规则固定,没有嵌套、没有表达式、没有变量作用域。parser.py 逐行读取main.txt,遇到click xxx就查coords.txt,遇到press yyy就查keymap.py,遇到include zzz.txt就递归加载——整个解析过程像读小学语文课本,没有任何歧义。

这种“笨办法”的终极优势是可预测性。你知道每一行代码执行后,屏幕上必然发生什么;你知道改哪一行,会影响哪个环节;你知道出问题时,该看哪个文件。它不试图理解世界,只忠实复现动作。这正是重复性任务最需要的品质:稳定、可靠、可审计。

3. 核心文件详解与实操要点:从录制到执行的完整闭环

3.1 recorder.py:如何用3分钟录下你的一次完整操作

recorder.py 是整个系统的“数据采集入口”,但它不是传统意义上的“录屏软件”。它不录画面,只录输入事件流:鼠标移动的坐标序列、鼠标点击的类型(左键/右键/滚轮)、键盘按键的扫描码和字符。它的设计理念是:最小化干扰,最大化可控性。

启动方式极其简单:

python recorder.py

运行后,终端会显示:

Recorder started. Press F12 to begin recording.
Press F12 again to stop and save to record_20240523_1422.txt
Press ESC to exit without saving.

实操要点:
- F12是唯一控制键:避免与应用快捷键冲突。按下F12后,屏幕右上角会出现半透明计时器(仅Windows,Linux无此UI,靠终端提示),此时所有鼠标键盘操作都被捕获。
- 录制内容精准到帧:鼠标移动事件默认每50ms采样一次(可在recorder.py顶部修改MOUSE_MOVE_INTERVAL = 0.05),确保拖拽轨迹平滑;点击事件记录精确到毫秒级时间戳,type操作会区分shift+a(大写A)和a(小写a)。
- 输出文件是结构化文本record_20240523_1422.txt 内容类似:
# Recorded on 2024-05-23 14:22:15 # Platform: win32 mouse_move 120.3 85.7 1682345120.123 mouse_click left down 120.3 85.7 1682345120.456 mouse_click left up 120.3 85.7 1682345120.458 key_press ctrl 1682345121.001 key_press c 1682345121.002 key_release ctrl 1682345121.003 key_release c 1682345121.004
时间戳单位为秒(含小数),便于后续分析操作节奏。

关键技巧:
- 手动清理冗余事件:录制完成后,不要直接用。用文本编辑器打开record_xxx.txt,删除中间误触的移动事件(比如你思考时无意识晃动鼠标产生的几十行mouse_move)。parser.py 对空行和注释完全忽略,你可以加# 这里是登录步骤分隔。
- 坐标标准化recorder.py 默认记录绝对屏幕坐标。如果你常在不同分辨率显示器间切换,建议开启“相对坐标模式”(需修改recorder.pyUSE_RELATIVE_COORDS = True),它会将坐标转换为相对于主显示器左上角的百分比(如0.42, 0.33),再由parser.py在运行时按当前屏幕尺寸还原。这对多显示器用户是刚需。
- 快捷键录制陷阱recorder.py 会记录ctrl+c为两个独立事件(key_press ctrl + key_press c),但keymap.py里定义的是['ctrl', 'c']组合。所以录制后,你需要手动将record_xxx.txt里的key_press ctrlkey_press c合并成一行press copycopykeymap.py里定义的别名)。这是刻意为之的设计——强制你确认快捷键语义,而非盲目复现。

提示:simple_test.py 包含一个最小化录制示例,运行它会自动生成一个test_record.txt,你可以对比学习格式。

3.2 coords.txt:坐标不是数字,是语义化标签

coords.txt 是整个系统的“地理信息系统”。它把冰冷的像素坐标,变成有业务含义的标签。它的语法极其简单:标签名 = x, y,支持空格和注释。

标准结构示例:

# ====== [登录流程] ======
username_field = 520, 380
password_field = 520, 425
login_button = 640, 480

# ====== [报表导出] ======
reports_tab = 180, 120
date_picker = 320, 210
export_format_dropdown = 480, 210
export_btn = 1120, 85

# ====== [文件管理] ======
explorer_window = 100, 100
rename_menu_item = 220, 340

为什么必须用标签,而不是直接写坐标?
想象你要批量重命名100个文件。流程是:打开资源管理器 → 右键第一个文件 → 点“重命名” → 输入新名字 → 回车 → 右键第二个文件……如果main.txt里写click 220, 340,那么当资源管理器窗口大小改变,220, 340可能指向空白处。而用click rename_menu_item,你只需在coords.txt里更新一次坐标,所有引用它的脚本自动生效。

实操技巧:
- 坐标获取三步法
1. 打开画图工具(Windows自带)或gnome-screenshot(Linux),截取当前桌面;
2. 用画图的“选择”工具框选目标区域,左下角显示坐标(Windows)或用gthumb查看图片属性(Linux);
3. 将坐标填入coords.txt,标签名用下划线连接的业务名词(rename_menu_item),禁用驼峰(renameMenuItem)和空格(rename menu item),避免解析错误。
- 多显示器适配:如果主屏是2560x1440,副屏是1920x1080且位于右侧,那么副屏上坐标100, 100的实际屏幕坐标是2560+100, 100 = 2660, 100coords.txt里直接写2660, 100parser.py运行时会自动识别多显示器布局。
- 动态坐标预留:对于需要计算的坐标(如“表格第5行第3列单元格”),coords.txt不支持表达式,但你可以用# TODO: 计算第5行Y坐标注释,然后在main.txt里用click 520, {calculated_y}占位,由你手动填入。这比让程序猜更可靠。

3.3 keymap.py:快捷键不是魔法,是可配置的字符串数组

keymap.py 是一个纯Python字典,定义快捷键组合与名称的映射:

KEYMAP = {
    'copy': ['ctrl', 'c'],
    'paste': ['ctrl', 'v'],
    'select_all': ['ctrl', 'a'],
    'save': ['ctrl', 's'],
    'switch_tab': ['ctrl', 'tab'],
    'close_tab': ['ctrl', 'w'],
    'open_devtools': ['f12'],
    'alt_tab': ['alt', 'tab'],
}

设计逻辑:
parser.py 解析到press copy时,查KEYMAP['copy']得到['ctrl', 'c'],然后调用底层API依次按下ctrlc、释放c、释放ctrl。顺序和释放时机严格遵循真实键盘行为,避免ctrl+c被识别为ctrl+c两个独立按键。

实操要点:
- 组合键顺序很重要['ctrl', 'c']['c', 'ctrl'] 效果完全不同。前者是标准复制,后者可能触发其他应用的快捷键(如Chrome里c是“打开控制台”)。务必按你真实按键顺序书写。
- 特殊键名规范pynputpywin32对特殊键命名略有差异,keymap.py已做统一抽象。常用键名:'enter', 'esc', 'tab', 'space', 'backspace', 'delete', 'home', 'end', 'page_up', 'page_down', 'f1''f12'。Linux下'super'对应Win键,Windows下'lwin'/'rwin'
- 自定义组合键:你可以定义'open_calc': ['ctrl', 'alt', 't'],然后在main.txt里写press open_calc。这比记住Ctrl+Alt+T更符合认知习惯。
- 防冲突设计keymap.py里不要定义与系统全局快捷键冲突的组合(如['ctrl', 'alt', 'del']),否则可能意外调出任务管理器打断流程。

3.4 main.txtrepeat.txt:指令脚本的编写艺术

main.txt 是主执行脚本,repeat.txt 是循环执行脚本(常用于批量操作)。它们共享同一套语法,由grammar.py解析。

核心指令集(共7个):
| 指令 | 语法 | 示例 | 说明 |
|------|------|------|------|
| click | click <label> | click login_button | 点击coords.txt中定义的坐标点 |
| type | type <text> | type "Hello World" | 输入文本,支持中文、符号、空格 |
| press | press <keyname> | press copy | 触发keymap.py中定义的快捷键 |
| wait | wait <ms> | wait 2500 | 等待指定毫秒数,确保页面加载或动画结束 |
| paste | paste | paste | 将剪贴板内容粘贴到当前焦点窗口 |
| run | run <command> | run notepad.exe | 在Windows下启动程序(Linux用xdotool模拟) |
| include | include <file.txt> | include linux-term.txt | 导入并执行另一个指令文件 |

编写原则:
- 线性优先:脚本是顺序执行的,没有跳转、没有循环(repeat.txt靠外部调用实现循环)。main.txt应该像一份操作说明书,从上到下阅读即知全流程。
- 粒度适中:不要把10个动作写成一行type "abc" press tab type "def" ...。拆成多行,每行一个原子操作,便于调试。type "abc"失败?删掉这行重试;press tab没反应?检查keymap.pytab定义是否正确。
- 等待策略wait不是越多越好。我的经验是:页面跳转后wait 2000-3000,弹窗出现后wait 1000,输入框聚焦后wait 500。过度等待会让流程变慢,不足则导致后续操作失败。test_run.py里提供了--profile参数,可输出每行指令执行耗时,帮你精准优化wait值。
- repeat.txt 的妙用:它本身不包含循环语法,而是靠__main__.py-r参数实现。例如repeat.txt内容:
click first_file press f2 type "new_name_{index}" press enter click next_file
运行python __main__.py -r repeat.txt -n 100{index}会被自动替换为1100,实现100次重命名。{index}是唯一支持的变量,避免引入复杂模板引擎。

注意:playlist.txt 是一个高级用法示例,它包含多行include xxx.txt,用于组织大型自动化流程(如“每日日报生成”= include login.txt + include data_pull.txt + include export_pdf.txt),实现模块化。

4. 实操过程与核心环节实现:从零开始搭建一个“网页表单自动填写”流程

4.1 场景设定与准备工作

我们以一个真实高频场景为例:每天登录公司内部CRM系统,填写销售线索表单并提交。 表单字段包括:姓名(文本框)、电话(文本框)、公司名称(下拉选择)、行业(下拉选择)、备注(多行文本框)、提交按钮。

所需准备:
- 一台Windows电脑(已安装Python 3.8+)
- CRM系统网页(假设URL为https://crm.internal/login
- Chrome浏览器(已登录,确保Cookie有效)

第一步:环境安装

# 解压项目包,进入目录
cd self_driving_desktop

# 创建虚拟环境(推荐,避免污染全局)
python -m venv venv
venv\Scripts\activate.bat  # Windows
# venv/bin/activate      # Linux

# 安装依赖
pip install -r requirements.txt

# 验证基础功能
python simple_test.py  # 应输出"Test passed: mouse moved to center"

第二步:录制基础坐标
1. 打开Chrome,访问https://crm.internal/login
2. 确保登录页面完全加载(地址栏显示绿锁图标)
3. 运行python recorder.py,按F12开始录制
4. 用鼠标依次点击:
- 用户名输入框(稍作停顿)
- 密码输入框(稍作停顿)
- “登录”按钮
5. 按F12停止录制,得到record_login.txt

第三步:提取并整理坐标
用文本编辑器打开record_login.txt,找到关键点击事件:

mouse_click left down 520.0 380.0 1682345120.456
mouse_click left up 520.0 380.0 1682345120.458
mouse_click left down 520.0 425.0 1682345121.102
mouse_click left up 520.0 425.0 1682345121.104
mouse_click left down 640.0 480.0 1682345122.201
mouse_click left up 640.0 480.0 1682345122.203

将坐标填入coords.txt

# ====== [CRM登录] ======
crm_username_field = 520, 380
crm_password_field = 520, 425
crm_login_button = 640, 480

# ====== [CRM线索表单] ======
crm_name_field = 320, 210
crm_phone_field = 320, 260
crm_company_dropdown = 320, 310
crm_industry_dropdown = 320, 360
crm_remark_area = 320, 450
crm_submit_btn = 640, 520

第四步:编写main.txt主脚本

# CRM线索自动填写流程
# 步骤1:登录
wait 1000
click crm_username_field
type "sales_user"
wait 500
click crm_password_field
type "secure_pass"
wait 500
click crm_login_button
wait 5000  # 等待主页加载

# 步骤2:导航到线索页面
click crm_nav_leads  # 假设已定义此坐标
wait 2000

# 步骤3:填写表单
click crm_name_field
type "张三"
wait 300
click crm_phone_field
type "13800138000"
wait 300
click crm_company_dropdown
wait 1000
type "ABC科技有限公司"
wait 300
press down  # 选择下拉项(简化示例)
press enter
wait 300
click crm_industry_dropdown
wait 1000
type "信息技术"
press down
press enter
wait 300
click crm_remark_area
type "来自官网咨询,意向明确"
wait 300
click crm_submit_btn
wait 2000

# 步骤4:验证成功
press f5  # 刷新页面,准备下一次

第五步:定义快捷键(keymap.py补充)

KEYMAP = {
    # ...原有定义
    'down': ['down'],      # 方向键下
    'enter': ['enter'],    # 回车键
    'f5': ['f5'],          # 刷新
}

第六步:执行与调试

# 直接运行主脚本
python __main__.py

# 或启用调试模式(输出详细日志)
python __main__.py --debug

# 若中途失败,查看最后执行的指令,检查对应坐标是否偏移
# 例如发现`crm_name_field`点击到了空白处,则打开coords.txt,将520改成525

第七步:加入循环(批量提交)
创建repeat_crm.txt

click crm_name_field
type "客户_{index}"
click crm_phone_field
type "13800138{index:03d}"
click crm_submit_btn
wait 1500

运行10次:

python __main__.py -r repeat_crm.txt -n 10

4.2 Linux终端交互专项:linux-term.txt 的实战配置

Linux用户常需自动化终端操作,如批量部署、日志分析。linux-term.txt 的设计哲学是:不控制终端,只向终端发送内容。

前提条件:
- Linux系统已安装xdotoolsudo apt install xdotoolsudo yum install xdotool
- 终端窗口标题需唯一(如设置为CRM_DEPLOY

linux-term.txt 示例:

# 确保终端窗口激活
run xdotool search --name "CRM_DEPLOY" windowactivate
wait 500

# 发送命令序列
paste "cd /opt/crm/deploy"
press enter
wait 1000
paste "./deploy.sh --env prod --version 2.3.1"
press enter
wait 15000  # 等待部署完成
paste "tail -n 20 /var/log/crm/deploy.log"
press enter

关键点:
- run xdotool ... 是Linux特有指令,Windows下被忽略(parser.py有平台判断)。
- paste 指令在此处发挥核心作用:它将字符串写入剪贴板,再用press enter模拟回车,比直接调用subprocess.Popen更安全(避免Shell注入)。
- wait 时间需根据命令实际耗时调整。deploy.sh可能耗时10-20秒,tail命令瞬间完成,所以wait 15000后立即执行tail

5. 常见问题与排查技巧实录:那些文档里不会写的坑

5.1 坐标偏移:为什么明明点了(520,380),却点到了别处?

这是新手遇到最多的“灵异事件”。根本原因只有三个,按概率排序:

原因诊断方法解决方案
DPI缩放未适配(Win10/11高分屏)右键桌面→显示设置→缩放比例是否>100%?coords.txt中使用相对坐标(0.42, 0.33),或在parser.py中启用DPI补偿(搜索scale_factor变量,设为1.25等)
多显示器主次序变化运行python -c "import screeninfo; print(screeninfo.get_monitors())"确认coords.txt中坐标基于哪个显示器。主显示器索引为0,副屏为1,坐标需加上主屏宽度
窗口未激活/被遮挡执行前手动点击目标窗口标题栏,再运行脚本main.txt开头添加run notepad.exe(Windows)或run gnome-terminal(Linux)强制激活,或用xdotool激活特定窗口

实测心得:我在27寸4K屏(缩放150%)上,绝对坐标(520,380)实际对应物理像素(780,570)。用screeninfo库获取当前DPI缩放因子1.5,然后在parser.pyclick函数里加一行x, y = int(x * scale), int(y * scale),问题立解。scale值可从screeninfo动态获取,无需硬编码。

5.2 快捷键失效:press copy 没反应,但手动Ctrl+C正常

90%的情况是焦点丢失pynput模拟的按键,只会发送到当前活动窗口。如果脚本运行时,你手动切走了窗口,或者某个弹窗抢了焦点,press copy就会发给错误的程序。

排查三步法:
1. 确认焦点:在main.txtpress copy前加一行wait 500,然后手动把鼠标移到目标窗口(如Chrome),再运行。
2. 检查快捷键冲突:某些应用(如微信、钉钉)会劫持Ctrl+C。临时退出这些应用再试。
3. 验证底层API:运行python -c "from pynput.keyboard import Controller; c=Controller(); c.press('c'); c.release('c')",看是否触发了系统“蜂鸣声”(表示按键被接收)。如果没有,说明pynput权限被系统阻止(Linux需sudo,Windows需以管理员身份运行)。

终极解决方案:main.txt中,press copy前强制激活目标窗口:

# Windows下激活Chrome
run powershell -Command "Add-Type -AssemblyName System.Windows.Forms; [System.Windows.Forms.SendKeys]::SendWait('%{TAB}')"
wait 300
press copy

5.3 录制的type中文乱码:输入的是“你好”,却打出“浣уソ”

这是Windows下pywin32的编码坑。pywin32默认用ANSI编码发送字符串,而中文系统用UTF-16。解决方案有两个:

  • 推荐:改用pynputtype方法(已在platform_adapter.py中封装)。pynput原生支持Unicode,type("你好")直接输出正确。
  • 备用:在recorder.py中,对type事件的文本内容做UTF-16编码转换:
    python # recorder.py 中 if event.event_type == keyboard.KEY_DOWN: if hasattr(event, 'name') and event.name == 'space': text += ' ' elif hasattr(event, 'char') and event.char: # 强制UTF-16编码 try: encoded = event.char.encode('utf-16-le') # 后续处理... except: pass

5.4 repeat.txt 循环次数不准:-n 100 只执行了98次

这是因为{index}变量在parser.py中是从1开始递增的整数,但如果某次执行失败(如网络超时),脚本会中断,{index}不会回退。所以98次失败后,第99次{index}已是99,但脚本已退出。

规避策略:
- 前置校验:在repeat.txt开头加wait 100,确保环境稳定。
- 失败重试__main__.py支持--retry 3参数,对单次失败的指令重试3次。
- 日志追踪:启用--log repeat_log.txt,生成执行日志,失败时查看最后成功的{index}值,手动从该值继续。

5.5 跨平台兼容性终极检查表

问题现象Windows检查点Linux检查点
鼠标不移动检查pywin32是否安装(pip show pywin32检查python-xlib是否安装,DISPLAY环境变量是否设置(echo $DISPLAY
键盘无响应检查杀毒软件是否拦截pywin32检查pynput权限(sudo usermod -a -G input $USER,需重启)
坐标错乱检查DPI缩放设置检查xrandr输出,确认主显示器是HDMI-1还是DP-2
终端命令不执行run指令在Windows下仅支持.exerun指令在Linux下需xdotool,且窗口标题必须匹配

个人经验:我用一台双系统笔记本(Win11 + Ubuntu 22.04)做全链路测试。每次功能更新,必在两个系统上各跑3遍test_run.py,用git diff对比日志。真正的跨平台不是“能跑”,而是“行为一致”。

6. 进阶技巧与扩展方向:让这套工具真正融入你的工作流

6.1 与Excel联动:用VBA调用Python脚本实现“一键自动化”

很多财务、行政同事的终极梦想:在Excel里点一个按钮,自动完成报销单填报。这完全可行:

  1. 在Excel VBA中插入模块:
    vb Sub RunCRM_Automation() Dim shell As Object Set shell = VBA.CreateObject("WScript.Shell") ' 调用Python脚本,传入Excel当前单元格值 shell.Run "cmd /c cd /d ""C:\path\to\self_driving_desktop"" && python __main__.py --data """ & ActiveCell.Value & """", 0, True End Sub
  2. __main__.py中解析--data参数,将其写入临时temp_data.txt
  3. 修改main.txt,用include temp_data.txt读取动态数据。

这样,Excel里A1单元格写“张三”,点按钮就自动填充CRM姓名字段。

6.2 定时任务集成:告别手动双击

  • Windows:用任务计划程序,触发python C:\path\to\__main__.py
  • Linux:用crontab -e添加:
    0 9 * * 1-5 /usr/bin/python3 /home/user/self_driving_desktop/__main__.py >> /home/user/crm_daily.log 2>&1
    每周一至周五上午9点自动执行日报流程。

6.3 错误恢复机制:让自动化真正“无人值守”

目前脚本是线性执行,一处失败全盘崩溃。可增加简单恢复逻辑:

  1. main.txt中,关键步骤后加check_window "CRM - Dashboard"(需在grammar.py中新增check_window指令,调用pygetwindow库检查窗口标题);
  2. 如果检查失败,执行run "C:\path\to\recovery.bat"(重启浏览器等);
  3. recovery.bat内容:
    bat taskkill /f /im chrome.exe timeout /t 2 start chrome.exe https://crm.internal/login

6.4 未来可扩展性:为什么它值得你持续投入

这套工具的扩展性不在于代码有多复杂,而在于它的边界是开放的

  • 新指令:想支持“截图保存”?在grammar.py中加capture <filename>指令,调用PIL.ImageGrab.grab()
  • 新数据源:想从数据库读取客户列表?在parser.py中加db_query <sql>指令,用sqlite3执行;
  • 新输出:想把执行结果发邮件?在__main__.py中加--email参数,调用smtplib

它的核心价值,是把你从“学习自动化工具”中解放出来,直接进入“解决业务问题”的快车道。你不需要成为Python专家,只需要会改几行文本;你不需要理解事件循环,只需要知道click login_button就是点登录按钮。当你的同事还在研究Selenium的WebDriverWait怎么写时,你已经用coords.txt完成了10个自动化流程,并把main.txt发给了团队共享。

我个人在实际使用中发现,最高效的用法不是“全自动”,而是“半自动”:让脚本处理80%的重复点击和输入,剩下20%需要人工判断的环节(比如审核弹窗内容),由脚本暂停并提示“请确认,按F12继续”。这种人机协同模式,既保证了效率,又保留了人的决策权,这才是桌面自动化在现实世界中的正确打开方式。

本文还有配套的精品资源,点击获取 menu-r.4af5f7ec.gif

简介:这个工具用Python写成,不依赖图形界面开发框架,靠几个简单文本文件就能驱动整套自动化流程。操作录制器recorder.py能捕获鼠标移动、点击、键盘输入并保存为可编辑的脚本;parser.py负责读取main.txt、repeat.txt等指令文件,按顺序执行动作;coords.txt存屏幕坐标点,实现精准点击和拖拽;keymap.py定义常用快捷键组合,比如Ctrl+C、Alt+Tab;copy-paste.txt和linux-term.txt分别处理剪贴板内容与Linux终端命令交互。所有逻辑由grammar.py语法解析器统一调度,main.py提供命令行入口,setup.py和requirements.txt确保环境一键安装。测试文件如simple_test.py、test_run.py和playlist.txt方便快速验证功能,test目录里还包含多场景用例。整个方案轻量、透明、易调试,适合批量重命名、网页表单填写、UI操作预演、重复性办公任务等日常需求,Windows和Linux基础操作都覆盖,不需要编程经验,改几行文本就能调整行为。


本文还有配套的精品资源,点击获取
menu-r.4af5f7ec.gif

本文章已经生成可运行项目
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值