diff --git a/repo/js/铁匠铺/assets/Picture/AmethystLump.png b/repo/js/铁匠铺/assets/Picture/AmethystLump.png index ed65d9e7..d6ce99c9 100644 Binary files a/repo/js/铁匠铺/assets/Picture/AmethystLump.png and b/repo/js/铁匠铺/assets/Picture/AmethystLump.png differ diff --git a/repo/js/铁匠铺/assets/Picture/CondessenceCrystal.png b/repo/js/铁匠铺/assets/Picture/CondessenceCrystal.png index 6f718d11..82030321 100644 Binary files a/repo/js/铁匠铺/assets/Picture/CondessenceCrystal.png and b/repo/js/铁匠铺/assets/Picture/CondessenceCrystal.png differ diff --git a/repo/js/铁匠铺/assets/Picture/CrystalChunk.png b/repo/js/铁匠铺/assets/Picture/CrystalChunk.png index 83b7ea1f..4b7f8cde 100644 Binary files a/repo/js/铁匠铺/assets/Picture/CrystalChunk.png and b/repo/js/铁匠铺/assets/Picture/CrystalChunk.png differ diff --git a/repo/js/铁匠铺/assets/Picture/IronChunk.png b/repo/js/铁匠铺/assets/Picture/IronChunk.png index 54606019..ee80acd8 100644 Binary files a/repo/js/铁匠铺/assets/Picture/IronChunk.png and b/repo/js/铁匠铺/assets/Picture/IronChunk.png differ diff --git a/repo/js/铁匠铺/assets/Picture/Starsilver.png b/repo/js/铁匠铺/assets/Picture/Starsilver.png index 879e8696..9213a9b8 100644 Binary files a/repo/js/铁匠铺/assets/Picture/Starsilver.png and b/repo/js/铁匠铺/assets/Picture/Starsilver.png differ diff --git a/repo/js/铁匠铺/assets/Picture/WhiteIronChunk.png b/repo/js/铁匠铺/assets/Picture/WhiteIronChunk.png index 33e592a2..74ae3296 100644 Binary files a/repo/js/铁匠铺/assets/Picture/WhiteIronChunk.png and b/repo/js/铁匠铺/assets/Picture/WhiteIronChunk.png differ diff --git a/repo/js/铁匠铺/main.js b/repo/js/铁匠铺/main.js index 19f4b245..301a9894 100644 --- a/repo/js/铁匠铺/main.js +++ b/repo/js/铁匠铺/main.js @@ -1,172 +1,185 @@ (async function () { - // 设置游戏基础参数 - setGameMetrics(1920, 1080, 1.25); // 设置编写脚本环境的游戏分辨率和DPI缩放 - await genshin.returnMainUi(); // 返回主界面 + // 设置游戏基础参数 + setGameMetrics(1920, 1080, 1.25); // 设置编写脚本环境的游戏分辨率和DPI缩放 + await genshin.returnMainUi(); // 返回主界面 - /// - // 读取用户配置 - /// - let smithyName = settings.smithyName || "枫丹铁匠铺"; - let ore = settings.ore || "水晶块"; + /// + // 读取用户配置 + /// + let smithyName = settings.smithyName || "枫丹铁匠铺"; + let ore = settings.ore || "水晶块"; - // 定义矿物名称和图片文件名的映射表 - const ingredientImageMap = { - 萃凝晶: "assets/Picture/CondessenceCrystal.png", + // 定义矿物名称和图片文件名的映射表 + const ingredientImageMap = { + 萃凝晶: "assets/Picture/CondessenceCrystal.png", + 紫晶块: "assets/Picture/AmethystLump.png", + 水晶块: "assets/Picture/CrystalChunk.png", + 星银矿石: "assets/Picture/Starsilver.png", + 白铁块: "assets/Picture/WhiteIronChunk.png", + 铁块: "assets/Picture/IronChunk.png", + }; - 紫晶块: "assets/Picture/AmethystLump.png", - 水晶块: "assets/Picture/CrystalChunk.png", - 星银矿石: "assets/Picture/Starsilver.png", - 白铁块: "assets/Picture/WhiteIronChunk.png", - 铁块: "assets/Picture/IronChunk.png", - }; + // Ore 映射为中文 + const OreChineseMap = { + 萃凝晶: "萃凝晶", + 紫晶块: "紫晶块", + 水晶块: "水晶块", + 星银矿石: "星银矿石", + 白铁块: "白铁块", + 铁块: "铁块", + // 添加其他加工设置的中文映射 + }; - // Ore 映射为中文 - const OreChineseMap = { - 萃凝晶: "萃凝晶", - 紫晶块: "紫晶块", - 水晶块: "水晶块", - 星银矿石: "星银矿石", - 白铁块: "白铁块", - 铁块: "铁块", - // 添加其他加工设置的中文映射 - }; + // 获取中文描述和图像路径 + const processingKey = settings.ore || "水晶块"; + const chineseDescription = OreChineseMap[processingKey]; + const imagePath = ingredientImageMap[processingKey]; - // 获取中文描述和图像路径 - const processingKey = settings.ore || "水晶块"; - const chineseDescription = OreChineseMap[processingKey]; - const imagePath = ingredientImageMap[processingKey]; + // 行列数的排列组合 + const rows = [1, 2, 3]; // 行数 + const cols = [1, 2, 3, 4, 5]; // 列数 + const gridCoordinates = []; - // 行列数的排列组合 - const rows = [1, 2, 3]; // 行数 - const cols = [1, 2, 3, 4, 5]; // 列数 - const gridCoordinates = []; - - // 计算每个行列组合的坐标 - for (const row of rows) { - for (const col of cols) { - const ProcessingX = Math.round(135 + (col - 1) * 145); - const ProcessingY = Math.round(245 + (row - 1) * 170); - gridCoordinates.push({ row, col, x: ProcessingX, y: ProcessingY }); - } - } - - // 图像识别函数 - function recognizeImage(imagePath, x, y, searchWidth, searchHeight) { - try { - let template = file.ReadImageMatSync(imagePath); - let recognitionObject = RecognitionObject.TemplateMatch( - template, - x, - y, - searchWidth, - searchHeight - ); - - // 设置识别阈值和通道 - recognitionObject.threshold = 0.9; // 设置识别阈值为 0.9 - recognitionObject.Use3Channels = true; // 使用三通道匹配 - - let result = captureGameRegion().find(recognitionObject); - return result.isExist() ? result : null; - } catch (error) { - log.error(`图像识别失败,路径: ${imagePath}, 错误: ${error.message}`); - return null; - } - } - - // 自动前往铁匠铺 - async function autoSmithy(smithyName) { - log.info(`自动前往 ${smithyName}`); - try { - let filePath = `assets/Pathing/${smithyName}.json`; - await pathingScript.runFile(filePath); - } catch (error) { - log.error(`执行 ${smithyName} 路径时发生错误`); - log.error(error.toString()); - } - } - - // 确认使用矿石 - function determineOre() { - if (ore == "水晶块") { - log.info("将使用 水晶块 锻造矿石"); - } else if (ore == "紫晶块") { - log.info("将使用 紫晶块 锻造矿石"); - } else if (ore == "萃凝晶") { - log.info("将使用 萃凝晶 锻造矿石"); - } else { - log.info("无指定矿石,将使用 水晶块 锻造矿石"); - } - } - - // 锻造矿石操作 - const forgeOre = async function (smithyName) { - await sleep(1000); - keyPress("F"); - await sleep(1000); // 开始交互 - await click(960, 600); - await sleep(1000); // 跳过第一个对话 - await click(960, 600); - await sleep(1000); // 跳过第一个对话 - await click(1375, 500); - await sleep(1000); - await click(960, 600); - await sleep(1000); // 跳过第二个对话 - await click(960, 600); - await sleep(1000); // 跳过第二个对话 - - log.info("已进入锻造界面,准备锻造"); - // 锻造领取 - await click(520, 140); - await sleep(1000); // 选择锻造队列 - await click(170, 1010); - await sleep(1000); // 领取全部 - await click(960, 900); - await sleep(1000); // 确认 - - click(220, 150); - await sleep(1000); // 点击"配方" - determineOre(); - - // 根据用户选择的矿石进行锻造 - if (!imagePath) { - log.error(`未找到矿石图像路径: ${chineseDescription}`); - } else { - log.info(`开始识别矿石: ${chineseDescription}`); - - // 左上角的偏移量 - const scanOffset = { x: -35, y: -35 }; - let foundIngredient = false; - for (const coordinate of gridCoordinates) { - const scanX = coordinate.x + scanOffset.x; - const scanY = coordinate.y + scanOffset.y; - - const imageResult = recognizeImage(imagePath, scanX, scanY, 70, 70); - if (imageResult) { - log.info(`通过图像识别找到矿石: ${chineseDescription}`); - imageResult.click(); - await sleep(2000); // 等待点击生效 - foundIngredient = true; - - // 点击“开始锻造”3次 - click(1645, 1015); - await sleep(3000); - click(1645, 1015); - await sleep(3000); - click(1645, 1015); - await sleep(3000); - break; // 找到矿石后退出循环 + // 计算每个行列组合的坐标 + for (const row of rows) { + for (const col of cols) { + const ProcessingX = Math.round(150 + (col - 1) * 145); + const ProcessingY = Math.round(230 + (row - 1) * 170); + gridCoordinates.push({ row, col, x: ProcessingX, y: ProcessingY }); } - } - if (!foundIngredient) { - log.error(`未能识别到矿石: ${chineseDescription}`); - } } - // 退出锻造界面 - log.info("锻造结束,退出界面"); - keyPress("ESCAPE"); - }; - await autoSmithy(smithyName); //寻路函数 - await forgeOre(smithyName); + // 图像识别函数 + function recognizeImage(imagePath, x, y, searchWidth, searchHeight) { + try { + let template = file.ReadImageMatSync(imagePath); + let recognitionObject = RecognitionObject.TemplateMatch( + template, + x, + y, + searchWidth, + searchHeight + ); + + // 设置识别阈值和通道 + recognitionObject.threshold = 0.9; // 设置识别阈值 + recognitionObject.Use3Channels = true; // 使用三通道匹配 + + let result = captureGameRegion().find(recognitionObject); + return result.isExist() ? result : null; + } catch (error) { + log.error( + `图像识别失败,路径: ${imagePath}, 错误: ${error.message}` + ); + return null; + } + } + + // 自动前往铁匠铺 + async function autoSmithy(smithyName) { + log.info(`自动前往 ${smithyName}`); + try { + let filePath = `assets/Pathing/${smithyName}.json`; + await pathingScript.runFile(filePath); + } catch (error) { + log.error(`执行 ${smithyName} 路径时发生错误`); + log.error(error.toString()); + } + } + + // 确认使用矿石 + function determineOre() { + if (ore == "水晶块") { + log.info("将使用 水晶块 锻造矿石"); + } else if (ore == "紫晶块") { + log.info("将使用 紫晶块 锻造矿石"); + } else if (ore == "萃凝晶") { + log.info("将使用 萃凝晶 锻造矿石"); + } else { + log.info("无指定矿石,将使用 水晶块 锻造矿石"); + } + } + + // 锻造矿石操作 + const forgeOre = async function (smithyName) { + await sleep(1000); + keyPress("F"); + await sleep(1000); // 开始交互 + await click(960, 600); + await sleep(1000); // 跳过第一个对话 + await click(960, 600); + await sleep(1000); // 跳过第一个对话 + await click(1375, 500); + await sleep(1000); + await click(960, 600); + await sleep(1000); // 跳过第二个对话 + await click(960, 600); + await sleep(1000); // 跳过第二个对话 + + log.info("已进入锻造界面,准备锻造"); + // 锻造领取 + await click(520, 140); + await sleep(1000); // 选择锻造队列 + await click(170, 1010); + await sleep(1000); // 领取全部 + await click(960, 900); + await sleep(1000); // 确认 + + click(220, 150); + await sleep(1000); // 点击"配方" + determineOre(); + + // 根据用户选择的矿石进行锻造 + if (!imagePath) { + log.error(`未找到矿石图像路径: ${chineseDescription}`); + } else { + log.info(`开始识别矿石: ${chineseDescription}`); + + // 左上角的偏移量 + const scanOffset = { x: -35, y: -35 }; + let foundIngredient = false; + for (const coordinate of gridCoordinates) { + const scanX = coordinate.x + scanOffset.x; + const scanY = coordinate.y + scanOffset.y; + + const imageResult = recognizeImage( + imagePath, + scanX, + scanY, + 70, + 70 + ); + if (imageResult) { + log.info(`通过图像识别找到矿石: ${chineseDescription}`); + imageResult.click(); + await sleep(2000); // 等待点击生效 + foundIngredient = true; + + // 点击“开始锻造”3次 + click(1645, 1015); + await sleep(1500); + click(1645, 1015); + await sleep(1500); + click(1645, 1015); + await sleep(1500); + break; // 找到矿石后退出循环 + } + } + if (!foundIngredient) { + log.error(`未能识别到矿石: ${chineseDescription}`); + } + } + + // 退出锻造界面 + log.info("锻造结束,退出界面"); + keyPress("ESCAPE"); + }; + await autoSmithy(smithyName); //寻路函数 + await forgeOre(smithyName); + + await genshin.returnMainUi(); // 返回主界面 + keyDown("S"); + await sleep(1000); + keyUp("S"); + await sleep(1000); })(); diff --git a/repo/js/铁匠铺/manifest.json b/repo/js/铁匠铺/manifest.json index dc804ea2..94fafcb3 100644 --- a/repo/js/铁匠铺/manifest.json +++ b/repo/js/铁匠铺/manifest.json @@ -1,13 +1,13 @@ { - "manifest_version": 1, - "name": "自动锻造魔矿", - "version": "1.1(2025.05.01版)", - "description": "自动选择铁匠铺和使用矿物去锻造魔矿。\n注1:默认选择枫丹铁匠铺,可选择其他地区铁匠铺。由于地图追踪功能不支持室内定位,所以不支持纳塔铁匠铺;\n注2:可选使用水晶矿(默认)、紫晶矿、萃凝晶。\n鸣谢:寒露,蜜柑魚", - "authors": [ - { - "name": "呱呱z" - } - ], - "settings_ui": "settings.json", - "main": "main.js" + "manifest_version": 1, + "name": "自动锻造魔矿(识图)", + "version": "1.2(2025.05.12版)", + "description": "自动选择铁匠铺和使用矿物去锻造魔矿。\n使用前请阅读“readme”文件\n鸣谢:寒露,蜜柑魚", + "authors": [ + { + "name": "呱呱z" + } + ], + "settings_ui": "settings.json", + "main": "main.js" } diff --git a/repo/js/铁匠铺/readme(25.05.12).md b/repo/js/铁匠铺/readme(25.05.12).md new file mode 100644 index 00000000..14960b3a --- /dev/null +++ b/repo/js/铁匠铺/readme(25.05.12).md @@ -0,0 +1,57 @@ +// ==UserScript== +// @name 自动锻造魔矿脚本 +// @version 1.2 +// @description 自动前往铁匠铺并锻造魔矿,通过识图模式自动选择矿石 +// @author 呱呱 z +// @match 原神版本:5.6;BGI 版本:0.45.1 +// ==/UserScript== + +/** + * === 重要免责声明 === + * 1. 使用风险 + * - 本脚本为开源学习项目,禁止用于商业用途或违反游戏条款的行为。 + * - 滥用可能导致游戏账号封禁,开发者不承担任何直接或间接责任。 + * + * 2. 责任限制 + * - 本脚本按“现状”提供,不承诺兼容性、安全性或功能完整性。 + * - 因使用本脚本导致的账号、数据、设备损失,开发者概不负责。 + * + * 3. 禁止条款 + * - 严禁逆向工程、恶意篡改或用于外挂等非法用途。 + * - 如游戏运营商提出要求,开发者保留随时停止维护的权利。 + * + * 使用即表示您已阅读并同意上述条款。 + * + * Last Updated: 2025-05-12 + */ + +# 自动锻造魔矿脚本 + +## 简介 +本脚本可自动前往铁匠铺并锻造魔矿,利用识图模式智能选择需要的矿石,让自定义操作更加便捷。 + +## 文件结构 +- **main.js**:负责核心业务逻辑,包括前往铁匠铺和执行锻造任务。 +- **manifest.json**:脚本配置文件,记录基本信息和设置。 +- **settings.json**:用户配置文件,用于选择目标铁匠铺和指定矿石。 + +## 使用方法 +1. 将脚本添加至调度器。 +2. 右键点击脚本以修改JS自定义配置。 +3. 在配置文件中选择目标城市的铁匠铺(默认选择枫丹铁匠铺),并设定所需矿石(默认:水晶矿)。 + - 注意:由于地图追踪功能尚不支持室内定位,故纳塔铁匠铺不可用。 + - 可选矿石: + - 默认:水晶矿 + - 其他:紫晶矿、萃凝晶 + - 如需使用“星银矿石”、“白铁块”或“铁块”,请打开 `settings.json`,删除对应矿石前的 `//` 注释后保存配置。 + +## 后言 +本脚本目前处于测试阶段,欢迎反馈问题至 QQ:1765137214。 + +## 更新日志 + +### 1.2 +- 修复选择“萃凝晶”时无法识别的 bug + +### 1.1 +- 优化矿石选取方式,改用识图模式