自动发帖软件

标题: 代理模式简书自动流程 [打印本页]

作者: 发帖软件    时间: 3 小时前
标题: 代理模式简书自动流程
代理模式简书自动流程
代理模式简书自动流程 群发软件发帖工具


  1. // AIWROK 完整自动化流程:启动简书 → 我的 → 写文章 → 输入内容 → 发布
  2. // 代理模式简书自动流程





  3. print.log("===== 简书写文章流程启动 =====");
  4. print.time();

  5. // ========== 工具函数 ==========
  6. function 执行Shell(命令) {
  7.     var 结果 = agent.shell(命令);
  8.     if (!结果) return "";
  9.    
  10.     var 结果字符串 = "";
  11.     if (typeof 结果 === "string") {
  12.         结果字符串 = 结果;
  13.     } else if (结果.toString) {
  14.         结果字符串 = 结果.toString();
  15.     } else {
  16.         结果字符串 = "" + 结果;
  17.     }
  18.    
  19.     var startIdx = -1;
  20.     if (typeof 结果字符串.indexOf === "function") {
  21.         startIdx = 结果字符串.indexOf("successMsg:");
  22.     }
  23.    
  24.     if (startIdx !== -1) {
  25.         var afterSuccess = 结果字符串.substring(startIdx + 11);
  26.         var errorIdx = afterSuccess.indexOf(",errorMsg:");
  27.         if (errorIdx !== -1) {
  28.             var content = afterSuccess.substring(0, errorIdx);
  29.             var endMarker = content.indexOf("UI hierchary dumped to:");
  30.             if (endMarker !== -1) {
  31.                 content = content.substring(0, endMarker);
  32.             }
  33.             return "" + content.trim();
  34.         }
  35.         return "" + afterSuccess.trim();
  36.     }
  37.    
  38.     return "" + 结果字符串;
  39. }

  40. function 获取UI() {
  41.     var 临时文件 = "/sdcard/ui_dump.xml";
  42.     agent.shell("uiautomator dump --compressed " + 临时文件 + " 2>/dev/null");
  43.     var 结果 = agent.shell("cat " + 临时文件);
  44.    
  45.     if (!结果) return "";
  46.    
  47.     var 结果字符串 = "";
  48.     if (typeof 结果 === "string") {
  49.         结果字符串 = 结果;
  50.     } else if (结果.toString) {
  51.         结果字符串 = 结果.toString();
  52.     } else {
  53.         结果字符串 = "" + 结果;
  54.     }
  55.    
  56.     var startIdx = -1;
  57.     if (typeof 结果字符串.indexOf === "function") {
  58.         startIdx = 结果字符串.indexOf("successMsg:");
  59.     }
  60.    
  61.     var content = "";
  62.     if (startIdx !== -1) {
  63.         var afterSuccess = 结果字符串.substring(startIdx + 11);
  64.         var errorIdx = afterSuccess.indexOf(",errorMsg:");
  65.         if (errorIdx !== -1) {
  66.             content = afterSuccess.substring(0, errorIdx);
  67.             var endMarker = content.indexOf("UI hierchary dumped to:");
  68.             if (endMarker !== -1) {
  69.                 content = content.substring(0, endMarker);
  70.             }
  71.         } else {
  72.             content = afterSuccess;
  73.         }
  74.         content = content.trim();
  75.     } else {
  76.         content = 结果字符串;
  77.     }
  78.    
  79.     return "" + content;
  80. }

  81. function 字符串长度(str) {
  82.     if (typeof str.length === "function") {
  83.         return str.length();
  84.     }
  85.     return str.length || 0;
  86. }

  87. function 获取当前包名() {
  88.     var uiXml = 获取UI();
  89.     var m = uiXml.match(/package="([^"]+)"/);
  90.     if (m) {
  91.         return "" + m[1];
  92.     }
  93.     return "";
  94. }

  95. function 查找包含文字的节点(xml, 关键词) {
  96.     var 节点列表 = [];
  97.     for (var i = 0; i < 关键词.length; i++) {
  98.         var 词 = 关键词[i];
  99.         var pos = 0;
  100.         while (true) {
  101.             pos = xml.indexOf('text="' + 词 + '"', pos);
  102.             if (pos < 0) break;
  103.             var boundsStart = xml.indexOf('bounds="', pos);
  104.             if (boundsStart >= 0) {
  105.                 var boundsEnd = xml.indexOf('"', boundsStart + 8);
  106.                 if (boundsEnd >= 0) {
  107.                     var boundsStr = xml.substring(boundsStart + 8, boundsEnd);
  108.                     var m = boundsStr.match(/\[(\d+),(\d+)\]\[(\d+),(\d+)\]/);
  109.                     if (m) {
  110.                         var node = {
  111.                             text: 词,
  112.                             x1: parseInt(m[1]),
  113.                             y1: parseInt(m[2]),
  114.                             x2: parseInt(m[3]),
  115.                             y2: parseInt(m[4]),
  116.                             cx: (parseInt(m[1]) + parseInt(m[3])) / 2,
  117.                             cy: (parseInt(m[2]) + parseInt(m[4])) / 2
  118.                         };
  119.                         节点列表.push(node);
  120.                     }
  121.                 }
  122.             }
  123.             pos += 字符串长度(词);
  124.         }
  125.     }
  126.     return 节点列表;
  127. }

  128. function 查找包含资源ID的节点(xml, 资源ID关键词) {
  129.     var 节点列表 = [];
  130.     for (var i = 0; i < 资源ID关键词.length; i++) {
  131.         var 关键词 = 资源ID关键词[i];
  132.         var pos = 0;
  133.         while (true) {
  134.             pos = xml.indexOf('resource-id="', pos);
  135.             if (pos < 0) break;
  136.             var idEnd = xml.indexOf('"', pos + 13);
  137.             if (idEnd >= 0) {
  138.                 var resourceId = xml.substring(pos + 13, idEnd);
  139.                 if (resourceId.indexOf(关键词) !== -1) {
  140.                     var boundsStart = xml.indexOf('bounds="', pos);
  141.                     if (boundsStart >= 0) {
  142.                         var boundsEnd = xml.indexOf('"', boundsStart + 8);
  143.                         if (boundsEnd >= 0) {
  144.                             var boundsStr = xml.substring(boundsStart + 8, boundsEnd);
  145.                             var m = boundsStr.match(/\[(\d+),(\d+)\]\[(\d+),(\d+)\]/);
  146.                             if (m) {
  147.                                 var node = {
  148.                                     resourceId: resourceId,
  149.                                     x1: parseInt(m[1]),
  150.                                     y1: parseInt(m[2]),
  151.                                     x2: parseInt(m[3]),
  152.                                     y2: parseInt(m[4]),
  153.                                     cx: (parseInt(m[1]) + parseInt(m[3])) / 2,
  154.                                     cy: (parseInt(m[2]) + parseInt(m[4])) / 2
  155.                                 };
  156.                                 节点列表.push(node);
  157.                             }
  158.                         }
  159.                     }
  160.                 }
  161.             }
  162.             pos = idEnd + 1;
  163.         }
  164.     }
  165.     return 节点列表;
  166. }

  167. function 输入文本(文本, 点击X, 点击Y) {
  168.     if (!点击X) 点击X = 0.2;
  169.     if (!点击Y) 点击Y = 0.2;
  170.    
  171.     agent.clickPercent(点击X, 点击Y);
  172.     sleep.millisecond(毫秒 = 500);
  173.    
  174.     agent.shell("service call clipboard 4 i32 1 s16 '" + 文本 + "' i32 0");
  175.     sleep.millisecond(毫秒 = 300);
  176.     agent.shell("service call clipboard 3 i32 1 s16 '" + 文本 + "' i32 0");
  177.     sleep.millisecond(毫秒 = 300);
  178.    
  179.     try {
  180.         Clipboard.copy(文本);
  181.         sleep.millisecond(毫秒 = 300);
  182.     } catch (e) {}
  183.    
  184.     print.log("✓ 剪贴板已设置内容");
  185.    
  186.     agent.shell("input keyevent 279");
  187.     sleep.second(秒 = 1);
  188. }

  189. function 查找WebView节点(xml) {
  190.     var 节点列表 = [];
  191.     var pos = 0;
  192.     while (true) {
  193.         pos = xml.indexOf('class="android.webkit.WebView"', pos);
  194.         if (pos < 0) break;
  195.         var boundsStart = xml.indexOf('bounds="', pos);
  196.         if (boundsStart >= 0) {
  197.             var boundsEnd = xml.indexOf('"', boundsStart + 8);
  198.             if (boundsEnd >= 0) {
  199.                 var boundsStr = xml.substring(boundsStart + 8, boundsEnd);
  200.                 var m = boundsStr.match(/\[(\d+),(\d+)\]\[(\d+),(\d+)\]/);
  201.                 if (m) {
  202.                     var node = {
  203.                         x1: parseInt(m[1]),
  204.                         y1: parseInt(m[2]),
  205.                         x2: parseInt(m[3]),
  206.                         y2: parseInt(m[4]),
  207.                         cx: (parseInt(m[1]) + parseInt(m[3])) / 2,
  208.                         cy: (parseInt(m[2]) + parseInt(m[4])) / 2
  209.                     };
  210.                     节点列表.push(node);
  211.                 }
  212.             }
  213.         }
  214.         pos += 25;
  215.     }
  216.     return 节点列表;
  217. }

  218. // ========== 配置区 ==========
  219. var APP包名 = "com.jianshu.haruki";

  220. var 循环次数 = 3;
  221. var 当前循环 = 0;

  222. var 文章标题 = "AI技术发展趋势";
  223. var 文章正文 = "人工智能技术正在飞速发展,改变着我们生活的方方面面。从机器学习到深度学习,从自然语言处理到计算机视觉,AI的应用场景越来越广泛。未来,AI将在更多领域发挥重要作用,推动社会进步和创新发展。";

  224. // ========== 获取设备信息 (agent模式) ==========
  225. var wm结果 = 执行Shell("wm size");
  226. var m = wm结果.match(/(\d+)x(\d+)/);
  227. var 屏幕宽 = m ? parseInt(m[1]) : 1080;
  228. var 屏幕高 = m ? parseInt(m[2]) : 2400;
  229. print.log("屏幕尺寸:" + 屏幕宽 + " x " + 屏幕高);
  230. print.log("代理状态:" + (agent.isOpen() ? "已开启" : "未开启"));
  231. print.log("目标APP:" + APP包名 + " (简书)");

  232. // ========================================
  233. // 主循环开始
  234. // ========================================
  235. for (当前循环 = 1; 当前循环 <= 循环次数; 当前循环++) {
  236.     print.log("\n======================================");
  237.     print.log("===== 第 " + 当前循环 + " / " + 循环次数 + " 次循环 =====");
  238.     print.log("======================================");

  239. // ========================================
  240. // 步骤1:启动简书APP
  241. // ========================================
  242. print.log("\n========== 步骤1:启动简书APP ==========");

  243. var 启动成功 = false;
  244. var 启动尝试次数 = 0;
  245. var 最大启动尝试 = 3;

  246. while (!启动成功 && 启动尝试次数 < 最大启动尝试) {
  247.     启动尝试次数++;
  248.     try {
  249.         agent.shell("monkey -p " + APP包名 + " -c android.intent.category.LAUNCHER 1");
  250.         print.log("✓ 第" + 启动尝试次数 + "次尝试启动简书");
  251.     } catch (e) {
  252.         print.log("⚠ 第" + 启动尝试次数 + "次启动失败:" + e.message);
  253.     }
  254.    
  255.     sleep.second(秒 = 5);
  256.    
  257.     var 当前页面包名 = 获取当前包名();
  258.     print.log("当前页面包名:" + 当前页面包名);
  259.    
  260.     if (当前页面包名 === APP包名) {
  261.         启动成功 = true;
  262.         print.log("✓ APP启动成功");
  263.     } else {
  264.         print.log("⚠ 当前页面不是简书,准备重新启动");
  265.     }
  266. }

  267. if (!启动成功) {
  268.     print.log("✗ 多次尝试启动失败,跳过本次循环");
  269.     continue;
  270. }

  271. // ========================================
  272. // 步骤2:设置ADB输入法(支持中文输入)
  273. // ========================================
  274. print.log("\n========== 步骤2:设置ADB输入法 ==========");

  275. try {
  276.     var 当前输入法 = 执行Shell("settings get secure default_input_method");
  277.     print.log("当前默认输入法:" + 当前输入法);
  278.    
  279.     var adbKeyboard = "com.android.adbkeyboard/.AdbIME";
  280.     if (当前输入法.indexOf("adbkeyboard") === -1) {
  281.         print.log("当前不是ADB输入法,尝试切换");
  282.         agent.shell("ime enable " + adbKeyboard);
  283.         sleep.millisecond(毫秒 = 300);
  284.         agent.shell("ime set " + adbKeyboard);
  285.         sleep.millisecond(毫秒 = 500);
  286.         print.log("✓ 已切换到ADB输入法");
  287.     } else {
  288.         print.log("✓ 当前已是ADB输入法");
  289.     }
  290. } catch (e) {
  291.     print.log("⚠ 设置ADB输入法失败:" + e.message);
  292.     print.log("提示:请手动安装ADB Keyboard并设置为默认输入法");
  293. }

  294. // ========================================
  295. // 步骤3:查找并点击写文章按钮(悬浮铅笔按钮)
  296. // ========================================
  297. print.log("\n========== 步骤3:查找写文章按钮(悬浮铅笔按钮)==========");

  298. function 查找悬浮按钮(xml) {
  299.     var 节点列表 = [];
  300.    
  301.     var fabClasses = [
  302.         'class="android.support.design.widget.FloatingActionButton"',
  303.         'class="com.google.android.material.floatingactionbutton.FloatingActionButton"',
  304.         'class="android.widget.ImageView"'
  305.     ];
  306.    
  307.     for (var c = 0; c < fabClasses.length; c++) {
  308.         var pos = 0;
  309.         while (true) {
  310.             pos = xml.indexOf(fabClasses[c], pos);
  311.             if (pos < 0) break;
  312.             var boundsStart = xml.indexOf('bounds="', pos);
  313.             if (boundsStart >= 0) {
  314.                 var boundsEnd = xml.indexOf('"', boundsStart + 8);
  315.                 if (boundsEnd >= 0) {
  316.                     var boundsStr = xml.substring(boundsStart + 8, boundsEnd);
  317.                     var m = boundsStr.match(/\[(\d+),(\d+)\]\[(\d+),(\d+)\]/);
  318.                     if (m) {
  319.                         var x1 = parseInt(m[1]);
  320.                         var y1 = parseInt(m[2]);
  321.                         var x2 = parseInt(m[3]);
  322.                         var y2 = parseInt(m[4]);
  323.                         var cx = (x1 + x2) / 2;
  324.                         var cy = (y1 + y2) / 2;
  325.                         var width = x2 - x1;
  326.                         var height = y2 - y1;
  327.                         if (cx > 屏幕宽 * 0.6 && cy > 屏幕高 * 0.75 && width > 50 && height > 50) {
  328.                             var node = {
  329.                                 x1: x1,
  330.                                 y1: y1,
  331.                                 x2: x2,
  332.                                 y2: y2,
  333.                                 cx: cx,
  334.                                 cy: cy
  335.                             };
  336.                             节点列表.push(node);
  337.                         }
  338.                     }
  339.                 }
  340.             }
  341.             pos += fabClasses[c].length;
  342.         }
  343.     }
  344.    
  345.     return 节点列表;
  346. }

  347. var 找到写文章按钮 = false;
  348. var 尝试次数3 = 0;
  349. var 最大尝试次数3 = 3;

  350. while (!找到写文章按钮 && 尝试次数3 < 最大尝试次数3) {
  351.     尝试次数3++;
  352.     var 首页UI = 获取UI();
  353.     var xml长度3 = 字符串长度(首页UI);
  354.    
  355.     print.log("第 " + 尝试次数3 + " 次尝试获取首页UI,长度:" + xml长度3);
  356.    
  357.     if (xml长度3 < 100) {
  358.         print.log("UI数据过短,重试");
  359.         sleep.second(秒 = 1);
  360.         continue;
  361.     }
  362.    
  363.     var 悬浮按钮列表 = 查找悬浮按钮(首页UI);
  364.    
  365.     if (悬浮按钮列表.length > 0) {
  366.         var 写文章按钮 = 悬浮按钮列表[0];
  367.         var 写文章X = 写文章按钮.cx / 屏幕宽;
  368.         var 写文章Y = 写文章按钮.cy / 屏幕高;
  369.         agent.clickPercent(写文章X, 写文章Y);
  370.         print.log("✓ 已点击悬浮铅笔按钮,百分比坐标:(" + 写文章X.toFixed(4) + ", " + 写文章Y.toFixed(4) + ")");
  371.         找到写文章按钮 = true;
  372.     } else {
  373.         var 编辑资源ID节点 = 查找包含资源ID的节点(首页UI, ["write", "create", "edit", "publish", "fab"]);
  374.         
  375.         if (编辑资源ID节点.length > 0) {
  376.             var 编辑按钮 = 编辑资源ID节点[0];
  377.             var 编辑X = (编辑按钮.x1 + 编辑按钮.x2) / 2 / 屏幕宽;
  378.             var 编辑Y = (编辑按钮.y1 + 编辑按钮.y2) / 2 / 屏幕高;
  379.             agent.clickPercent(编辑X, 编辑Y);
  380.             print.log("✓ 已点击写文章按钮(通过资源ID),百分比坐标:(" + 编辑X.toFixed(4) + ", " + 编辑Y.toFixed(4) + ")");
  381.             找到写文章按钮 = true;
  382.         } else {
  383.             var 写文章节点 = 查找包含文字的节点(首页UI, ["写文章", "创作", "编辑", "写", "发布"]);
  384.             
  385.             if (写文章节点.length > 0) {
  386.                 var 写文章按钮 = 写文章节点[0];
  387.                 var 写文章X = (写文章按钮.x1 + 写文章按钮.x2) / 2 / 屏幕宽;
  388.                 var 写文章Y = (写文章按钮.y1 + 写文章按钮.y2) / 2 / 屏幕高;
  389.                 agent.clickPercent(写文章X, 写文章Y);
  390.                 print.log("✓ 已点击「" + 写文章按钮.text + "」,百分比坐标:(" + 写文章X.toFixed(4) + ", " + 写文章Y.toFixed(4) + ")");
  391.                 找到写文章按钮 = true;
  392.             } else {
  393.                 print.log("✓ 使用默认坐标点击右下角悬浮按钮");
  394.                 agent.clickPercent(0.875, 0.91);
  395.                 找到写文章按钮 = true;
  396.             }
  397.         }
  398.     }
  399. }

  400. if (!找到写文章按钮) {
  401.     print.log("✗ 多次尝试未找到写文章按钮,跳过本次循环");
  402.     continue;
  403. }

  404. sleep.second(秒 = 3);

  405. // ========================================
  406. // 步骤4:输入文章标题(WebView编辑器)
  407. // ========================================
  408. print.log("\n========== 步骤4:输入文章标题 ==========");

  409. var 标题输入成功 = false;
  410. var 尝试次数4 = 0;
  411. var 最大尝试次数4 = 3;

  412. while (!标题输入成功 && 尝试次数4 < 最大尝试次数4) {
  413.     尝试次数4++;
  414.     var 编辑页面UI = 获取UI();
  415.     var xml长度4 = 字符串长度(编辑页面UI);
  416.    
  417.     print.log("第 " + 尝试次数4 + " 次尝试获取编辑页面UI,长度:" + xml长度4);
  418.    
  419.     if (xml长度4 < 100) {
  420.         print.log("UI数据过短,重试");
  421.         sleep.second(秒 = 1);
  422.         continue;
  423.     }
  424.    
  425.     var webView节点 = 查找WebView节点(编辑页面UI);
  426.    
  427.     if (webView节点.length > 0) {
  428.         var webView = webView节点[0];
  429.         var 点击X = (webView.x1 + webView.x2) / 2 / 屏幕宽;
  430.         var 点击Y = (webView.y1 + 200) / 屏幕高;
  431.         print.log("✓ 准备在WebView编辑区域输入标题,百分比坐标:(" + 点击X.toFixed(4) + ", " + 点击Y.toFixed(4) + ")");
  432.         
  433.         输入文本(文章标题, 点击X, 点击Y);
  434.         sleep.millisecond(毫秒 = 500);
  435.         agent.shell("input keyevent 66");
  436.         sleep.millisecond(毫秒 = 300);
  437.         print.log("✓ 标题输入完成");
  438.         标题输入成功 = true;
  439.     } else {
  440.         print.log("⚠ 未找到WebView节点,直接点击编辑区域");
  441.         输入文本(文章标题, 0.2, 0.6);
  442.         sleep.millisecond(毫秒 = 500);
  443.         agent.shell("input keyevent 66");
  444.         sleep.millisecond(毫秒 = 300);
  445.         print.log("✓ 标题输入完成");
  446.         标题输入成功 = true;
  447.     }
  448. }
  449. sleep.second(秒 = 2);

  450. // ========================================
  451. // 步骤5:输入文章正文(WebView编辑器)
  452. // ========================================
  453. print.log("\n========== 步骤5:输入文章正文 ==========");

  454. var 正文输入成功 = false;
  455. var 尝试次数5 = 0;
  456. var 最大尝试次数5 = 3;

  457. while (!正文输入成功 && 尝试次数5 < 最大尝试次数5) {
  458.     尝试次数5++;
  459.     var 编辑页面UI2 = 获取UI();
  460.     var xml长度5 = 字符串长度(编辑页面UI2);
  461.    
  462.     print.log("第 " + 尝试次数5 + " 次尝试获取编辑页面UI,长度:" + xml长度5);
  463.    
  464.     if (xml长度5 < 100) {
  465.         print.log("UI数据过短,重试");
  466.         sleep.second(秒 = 1);
  467.         continue;
  468.     }
  469.    
  470.     var webView节点2 = 查找WebView节点(编辑页面UI2);
  471.    
  472.     if (webView节点2.length > 0) {
  473.         var webView2 = webView节点2[0];
  474.         var 点击X2 = (webView2.x1 + webView2.x2) / 2 / 屏幕宽;
  475.         var 点击Y2 = (webView2.y1 + webView2.y2) / 2 / 屏幕高;
  476.         print.log("✓ 准备在WebView正文区域输入,百分比坐标:(" + 点击X2.toFixed(4) + ", " + 点击Y2.toFixed(4) + ")");
  477.         
  478.         输入文本(文章正文, 点击X2, 点击Y2);
  479.         sleep.millisecond(毫秒 = 500);
  480.         print.log("✓ 正文输入完成");
  481.         正文输入成功 = true;
  482.     } else {
  483.         print.log("⚠ 未找到WebView节点,尝试点击页面中间区域");
  484.         输入文本(文章正文, 0.3, 0.4);
  485.         sleep.millisecond(毫秒 = 500);
  486.         print.log("✓ 正文输入完成");
  487.         正文输入成功 = true;
  488.     }
  489. }
  490. sleep.second(秒 = 2);

  491. // ========================================
  492. // 步骤6:点击发布按钮
  493. // ========================================
  494. print.log("\n========== 步骤6:点击发布按钮 ==========");

  495. var 找到发布按钮 = false;
  496. var 尝试次数6 = 0;
  497. var 最大尝试次数6 = 3;

  498. while (!找到发布按钮 && 尝试次数6 < 最大尝试次数6) {
  499.     尝试次数6++;
  500.     var 编辑页面UI3 = 获取UI();
  501.     var xml长度6 = 字符串长度(编辑页面UI3);
  502.    
  503.     print.log("第 " + 尝试次数6 + " 次尝试获取编辑页面UI,长度:" + xml长度6);
  504.    
  505.     if (xml长度6 < 100) {
  506.         print.log("UI数据过短,重试");
  507.         sleep.second(秒 = 1);
  508.         continue;
  509.     }
  510.    
  511.     var 发布节点 = 查找包含文字的节点(编辑页面UI3, ["发布", "发布文章", "保存", "完成"]);
  512.    
  513.     if (发布节点.length > 0) {
  514.         var 发布按钮 = 发布节点[0];
  515.         var 发布X = (发布按钮.x1 + 发布按钮.x2) / 2 / 屏幕宽;
  516.         var 发布Y = (发布按钮.y1 + 发布按钮.y2) / 2 / 屏幕高;
  517.         agent.clickPercent(发布X, 发布Y);
  518.         print.log("✓ 已点击「" + 发布按钮.text + "」,百分比坐标:(" + 发布X.toFixed(4) + ", " + 发布Y.toFixed(4) + ")");
  519.         找到发布按钮 = true;
  520.     } else {
  521.         var 发布资源ID节点 = 查找包含资源ID的节点(编辑页面UI3, ["publish", "save", "done", "submit"]);
  522.         
  523.         if (发布资源ID节点.length > 0) {
  524.             var 发布按钮 = 发布资源ID节点[0];
  525.             var 发布X = (发布按钮.x1 + 发布按钮.x2) / 2 / 屏幕宽;
  526.             var 发布Y = (发布按钮.y1 + 发布按钮.y2) / 2 / 屏幕高;
  527.             agent.clickPercent(发布X, 发布Y);
  528.             print.log("✓ 已点击发布按钮(通过资源ID),百分比坐标:(" + 发布X.toFixed(4) + ", " + 发布Y.toFixed(4) + ")");
  529.             找到发布按钮 = true;
  530.         } else {
  531.             print.log("⚠ 未找到发布按钮,尝试点击右上角");
  532.             agent.clickPercent(0.9, 0.07);
  533.             print.log("✓ 使用默认坐标点击右上角");
  534.             找到发布按钮 = true;
  535.         }
  536.     }
  537. }

  538. if (!找到发布按钮) {
  539.     print.log("✗ 多次尝试未找到发布按钮");
  540. }

  541. sleep.second(秒 = 3);

  542. // ========================================
  543. // 步骤7:关闭APP
  544. // ========================================
  545. print.log("\n========== 步骤7:关闭APP ==========");
  546. try {
  547.     agent.shell("am force-stop " + APP包名);
  548.     print.log("✓ 已关闭简书");
  549. } catch (e) {
  550.     print.log("⚠ 关闭APP失败:" + e.message);
  551. }
  552. sleep.second(秒 = 10);

  553.     if (当前循环 < 循环次数) {
  554.         print.log("\n========== 等待下一次循环 ==========");
  555.         sleep.second(秒 = 10);
  556.     }
  557. }

  558. // ========================================
  559. // 结果汇总
  560. // ========================================
  561. print.timeEnd();
  562. print.log("\n======================================");
  563. print.log("===== 简书写文章流程执行完成 =====");
  564. print.log("文章标题:" + 文章标题);
  565. print.log("文章正文长度:" + 文章正文.length + " 字");
  566. print.log("======================================");
复制代码







欢迎光临 自动发帖软件 (http://www.fatiegongju.com/) Powered by Discuz! X3.2