JS脚本:提瓦特自动钓鱼【更新】 (#1354)
This commit is contained in:
31
repo/js/AutoFishingTeyvat/READEME.md
Normal file
31
repo/js/AutoFishingTeyvat/READEME.md
Normal file
@@ -0,0 +1,31 @@
|
||||
脚本名称:提瓦特自动钓鱼(全流程+自选)
|
||||
|
||||
功能描述:支持自动追踪并垂钓bgi支持的全提瓦特垂钓点
|
||||
|
||||
## 核心功能
|
||||
|
||||
1. 可自选地区、鱼类、鱼饵
|
||||
2. 可直接钓取特定物品的兑换材料(例如渔获)
|
||||
3. 脚本会根据需要的鱼类自动调节时间,不需要的时段会跳过
|
||||
4. 支持部分地图追踪无法到达的钓鱼点(例如炽岩斗士急流鱼钓鱼点,枫丹廷东北钓鱼点、雷鸣仙垂钓点)
|
||||
5. 支持从特定的垂钓点继续任务(仅启用所有垂钓点时可用)
|
||||
6. 默认禁用需要战斗的路线,如有需要请在JS脚本配置内启用
|
||||
7. 支持自定义钓鱼超时时间
|
||||
8. 支持设置定时关闭(最多24小时)
|
||||
9. 4点自动领取月卡(可选)
|
||||
10. 自动记录垂钓点冷却时间(进入其他世界钓鱼时请关闭此功能)
|
||||
11. 启用自动拾取(可选)
|
||||
|
||||
## 注意事项
|
||||
|
||||
1. 部分点位涉及战斗,且队伍内不能有双风和跑步(不是冲刺)时加移速的角色
|
||||
2. 跑图位必须是少男体型(防止键鼠路线[GCM]出错)
|
||||
3. 同时选择鱼类和鱼饵的情况下按照以下逻辑选择路线: 所有被选的鱼类会被加入任务列表,如果选择的鱼饵中某个鱼饵不是已选的任何一个鱼类的对应的鱼饵,那么这个鱼饵对应的所有鱼类将被添加到任务列表
|
||||
4. JS脚本的设置内各设置项含有优先级,如果存在高优先级且选项不为默认,则只有最高优先级的设置项生效
|
||||
5. 部分钓鱼点为路径追踪+键鼠脚本(GCM)的混合模式,可能会出现因键鼠脚本误差卡死的情况,如果出现这种情况,请在JS脚本设置禁用键鼠路线来禁用所有包含键鼠脚本的钓鱼点
|
||||
|
||||
## 其它
|
||||
|
||||
作者:提瓦特钓鱼玳师
|
||||
|
||||
脚本反馈邮箱:hijiwos@hotmail.com
|
||||
@@ -1,4 +1,4 @@
|
||||
(async function () {
|
||||
(async function () { // 多人模式不计CD,CD读写仍有优化空间
|
||||
|
||||
const area_list = ['蒙德', '璃月', '稻妻', '须弥', '枫丹', '纳塔', '至冬', '层岩巨渊·地下矿区', '渊下宫']
|
||||
const fish_list = ['花鳉', '波波心羽鲈', '烘烘心羽鲈', '维护机关·水域清理者', '维护机关·态势控制者', '维护机关·澄金领队型', '海涛斧枪鱼', '维护机关·初始能力型', '维护机关·白金典藏型', '吹沙角鲀', '甜甜花鳉', '擒霞客', '水晶宴', '斗棘鱼', '炮鲀', '流纹褐蝶鱼', '锖假龙', '金赤假龙', '玉玉心羽鲈', '赤魔王', '长生仙', '苦炮鲀', '肺棘鱼', '流纹京紫蝶鱼', '琉璃花鳉', '伪装鲨鲨独角鱼', '繁花斗士急流鱼', '深潜斗士急流鱼', '晚霞翻车鲀', '青浪翻车鲀', '拟似燃素独角鱼', '炽岩斗士急流鱼', '蓝染花鳉', '鸩棘鱼', '流纹茶蝶鱼', '雪中君', '真果角鲀', '青金斧枪鱼', '暮云角鲀', '翡玉斧枪鱼', '沉波蜜桃', '雷鸣仙', '佛玛洛鳐', '迪芙妲鳐', '秘源机关·巡戒使']
|
||||
@@ -158,6 +158,95 @@
|
||||
// 存储本次任务中的所有鱼类,作为调节时间的关键参考
|
||||
let list_fish = [];
|
||||
|
||||
/**
|
||||
*
|
||||
* 将毫秒形式的字符串转换为更清晰的时间格式
|
||||
*
|
||||
* @param ms
|
||||
* @returns {string}
|
||||
*/
|
||||
function formatTimeDifference(ms) {
|
||||
ms = Number(ms);
|
||||
// 计算天、小时、分钟、秒
|
||||
const seconds = Math.floor(ms / 1000);
|
||||
const minutes = Math.floor(seconds / 60);
|
||||
const hours = Math.floor(minutes / 60);
|
||||
const days = Math.floor(hours / 24);
|
||||
|
||||
// 计算剩余的小时、分钟、秒
|
||||
const remainingHours = hours % 24;
|
||||
const remainingMinutes = minutes % 60;
|
||||
const remainingSeconds = seconds % 60;
|
||||
|
||||
// 返回格式化字符串
|
||||
return `${days}天 ${remainingHours}小时 ${remainingMinutes}分钟 ${remainingSeconds}秒`;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* 垂钓点CD存档写入
|
||||
*
|
||||
* @param {string} pathing_name 路径名称
|
||||
* @param {string} time_status 垂钓点时间状态(白天,夜晚)
|
||||
* @param {string} timestamp 时间戳
|
||||
* @param {string} user_id 原神UID
|
||||
*/
|
||||
function write_archive(pathing_name, time_status, timestamp, user_id) {
|
||||
let assets_dir = Array.from(file.readPathSync("assets"));
|
||||
let content = {};
|
||||
if (assets_dir.includes("assets\\archive.json")) {
|
||||
content = JSON.parse(file.readTextSync("assets/archive.json"));
|
||||
if (time_status === "全天") {
|
||||
content[user_id][pathing_name]["Daytime"] = timestamp;
|
||||
content[user_id][pathing_name]["Nighttime"] = timestamp;
|
||||
} else if (time_status === "白天") {
|
||||
content[user_id][pathing_name]["Daytime"] = timestamp;
|
||||
content[user_id][pathing_name]["Nighttime"] = Object.keys(content[user_id][pathing_name]).includes("Nighttime") ? content[user_id][pathing_name]["Nighttime"]: null;
|
||||
} else if (time_status === "夜晚") {
|
||||
content[user_id][pathing_name]["Daytime"] = Object.keys(content[user_id][pathing_name]).includes("Daytime") ? content[user_id][pathing_name]["Daytime"]: null;
|
||||
content[user_id][pathing_name]["Nighttime"] = timestamp;
|
||||
}
|
||||
|
||||
} else {
|
||||
content[user_id] = {};
|
||||
content[user_id][pathing_name] = {
|
||||
"Daytime": time_status === "白天" || time_status === "全天" ? timestamp : null,
|
||||
"Nighttime": time_status === "夜晚" || time_status === "全天" ? timestamp : null
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
file.WriteTextSync("assets/archive.json", JSON.stringify(content, null, 2), false);
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* 垂钓点CD存档读取
|
||||
*
|
||||
* @param {string} pathing_name 路径名称
|
||||
* @param {string} user_id 原神UID
|
||||
*
|
||||
* @return Daytime/Nighttime 字典
|
||||
*/
|
||||
function read_archive(pathing_name, user_id) {
|
||||
let assets_dir = Array.from(file.readPathSync("assets"));
|
||||
|
||||
if (assets_dir.includes("assets\\archive.json")) {
|
||||
let content = JSON.parse(file.readTextSync("assets/archive.json"));
|
||||
if (Object.keys(content).includes(user_id)) {
|
||||
if (Object.keys(content[user_id]).includes(pathing_name)) {
|
||||
return content[user_id][pathing_name];
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取路径包含的信息
|
||||
*
|
||||
@@ -298,7 +387,7 @@
|
||||
}
|
||||
}
|
||||
|
||||
async function run_file(path_msg, time_out_throw, time_out_whole, is_con, block_gcm, block_fight, block_tsurumi, auto_skip) {
|
||||
async function run_file(path_msg, time_out_throw, time_out_whole, is_con, block_gcm, block_fight, block_tsurumi, auto_skip, fishing_cd, uid = "default_user") {
|
||||
const base_path_pathing = "assets/pathing/";
|
||||
const base_path_gcm = "assets/KeyMouseScript/";
|
||||
const base_path_statues = "assets/pathing_statues/";
|
||||
@@ -408,7 +497,65 @@
|
||||
|
||||
log.info(`该钓鱼点的时间: ${fishing_time}`);
|
||||
|
||||
await pathingScript.runFile(base_path_pathing + file_name + ".json");
|
||||
// 检查垂钓点CD
|
||||
if (fishing_cd) {
|
||||
let current_cd = read_archive(file_name, uid);
|
||||
if (current_cd !== null) {
|
||||
const now = Date.now();
|
||||
if (fishing_time === "全天") {
|
||||
let daytime = true;
|
||||
if (current_cd["Daytime"] !== null) {
|
||||
let difference = now - current_cd["Daytime"];
|
||||
if (difference < 259200000) {
|
||||
log.info(`该垂钓点(白天)处于冷却状态,剩余时间: ${formatTimeDifference(259200000 - difference)}`);
|
||||
log.info(`${file_name}(白天) 已跳过...`);
|
||||
daytime = false;
|
||||
fishing_time = "夜晚";
|
||||
} else {
|
||||
log.info(`该垂钓点(白天)未处于冷却状态,闲置时间: ${formatTimeDifference(difference - 259200000)}`);
|
||||
}
|
||||
}
|
||||
if (current_cd["Nighttime"] !== null) {
|
||||
let difference = now - current_cd["Nighttime"];
|
||||
if (difference < 259200000) {
|
||||
log.info(`该垂钓点(夜晚)处于冷却状态,剩余时间: ${formatTimeDifference(259200000 - difference)}`);
|
||||
log.info(`${file_name}(夜晚) 已跳过...`);
|
||||
if (daytime) {
|
||||
fishing_time = "白天";
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
} else {
|
||||
log.info(`该垂钓点(夜晚)未处于冷却状态,闲置时间: ${formatTimeDifference(difference - 259200000)}`);
|
||||
}
|
||||
}
|
||||
} else if (fishing_time === "白天") {
|
||||
if (current_cd["Daytime"] !== null) {
|
||||
let difference = now - current_cd["Daytime"];
|
||||
if (difference < 259200000) {
|
||||
log.info(`该垂钓点(白天)处于冷却状态,剩余时间: ${formatTimeDifference(259200000 - difference)}`);
|
||||
log.info(`${file_name}(白天) 已跳过...`);
|
||||
return null;
|
||||
} else {
|
||||
log.info(`该垂钓点(白天)未处于冷却状态,闲置时间: ${formatTimeDifference(difference - 259200000)}`);
|
||||
}
|
||||
}
|
||||
} else if (fishing_time === "夜晚") {
|
||||
if (current_cd["Nighttime"] !== null) {
|
||||
let difference = now - current_cd["Nighttime"];
|
||||
if (difference < 259200000) {
|
||||
log.info(`该垂钓点(夜晚)处于冷却状态,剩余时间: ${formatTimeDifference(259200000 - difference)}`);
|
||||
log.info(`${file_name}(夜晚) 已跳过...`);
|
||||
return null;
|
||||
} else {
|
||||
log.info(`该垂钓点(夜晚)未处于冷却状态,闲置时间: ${formatTimeDifference(difference - 259200000)}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//await pathingScript.runFile(base_path_pathing + file_name + ".json");
|
||||
|
||||
// 执行键鼠脚本
|
||||
if (path_msg["addition"] === "GCM") {
|
||||
@@ -417,11 +564,15 @@
|
||||
|
||||
// 调用自动钓鱼
|
||||
// await genshin.autofishing(fishing_time_dic[fishing_time]["param"]);
|
||||
await dispatcher.runTask(new SoloTask("AutoFishing", {
|
||||
"fishingTimePolicy": fishing_time_dic[fishing_time]["param"],
|
||||
"throwRodTimeOutTimeoutSeconds": time_out_throw,
|
||||
"wholeProcessTimeoutSeconds": time_out_whole
|
||||
}));
|
||||
// await dispatcher.runTask(new SoloTask("AutoFishing", {
|
||||
// "fishingTimePolicy": fishing_time_dic[fishing_time]["param"],
|
||||
// "throwRodTimeOutTimeoutSeconds": time_out_throw,
|
||||
// "wholeProcessTimeoutSeconds": time_out_whole
|
||||
// }));
|
||||
|
||||
if (fishing_cd) {
|
||||
write_archive(file_name, fishing_time, Date.now(), uid);
|
||||
}
|
||||
}
|
||||
|
||||
async function main() {
|
||||
@@ -451,12 +602,33 @@
|
||||
const auto_pick = typeof(settings.auto_pick) === 'undefined' ? false : settings.auto_pick;
|
||||
// 读取4点自动领取月卡的设置
|
||||
const auto_skip = typeof(settings.auto_skip) === 'undefined' ? false : settings.auto_skip;
|
||||
// 读取垂钓点CD统计
|
||||
const fishing_cd = typeof(settings.fishing_cd) === 'undefined' ? false: settings.fishing_cd;
|
||||
// 读取终止时间
|
||||
const kill_hour = typeof(settings.time_kill_hour) === 'undefined' ? "无" : settings.time_kill_hour;
|
||||
const kill_minute = typeof(settings.time_kill_minute) === 'undefined' ? "无" : settings.time_kill_minute;
|
||||
const is_time_kill = kill_hour !== "无" && kill_minute !== "无"; // 判断是否启用
|
||||
let time_target = new Date();
|
||||
|
||||
// 获取当前用户UID
|
||||
let uid = "default_user";
|
||||
if (fishing_cd) {
|
||||
const ocrRo = RecognitionObject.Ocr(166, 198, 120, 22);
|
||||
|
||||
genshin.returnMainUi();
|
||||
await sleep(1000);
|
||||
keyPress("Escape");
|
||||
await sleep(1000);
|
||||
|
||||
let ocr = captureGameRegion().Find(ocrRo); // 当前页面OCR
|
||||
if (ocr.isExist()) {
|
||||
uid = ocr.text;
|
||||
}
|
||||
|
||||
keyPress("Escape");
|
||||
|
||||
}
|
||||
|
||||
if (is_time_kill) {
|
||||
let now = new Date();
|
||||
time_target.setHours(parseInt(kill_hour), 10);
|
||||
@@ -495,8 +667,7 @@
|
||||
}
|
||||
// 路径详细信息
|
||||
const path_msg = get_pathing_msg(path_filter[i]);
|
||||
try {
|
||||
await sleep(100);
|
||||
// try {
|
||||
let current_msg = `${path_msg["area"]}-${path_msg["detail"]}`
|
||||
log.info(`当前钓鱼点: ${current_msg}(进度: ${i + 1}/${path_filter.length})`);
|
||||
if (path_continue === current_msg) {
|
||||
@@ -509,11 +680,11 @@
|
||||
continue;
|
||||
}
|
||||
|
||||
await run_file(path_msg, time_out_throw, time_out_whole, is_con, block_gcm, block_fight, block_tsurumi, auto_skip);
|
||||
} catch (error) {
|
||||
const file_name = `${path_msg["area"]}-${path_msg["type"]}-${path_msg["detail"]}`;
|
||||
log.info(`路径: ${file_name} 执行时出错,已跳过...\n错误信息: ${error}`)
|
||||
}
|
||||
await run_file(path_msg, time_out_throw, time_out_whole, is_con, block_gcm, block_fight, block_tsurumi, auto_skip, fishing_cd, uid);
|
||||
// } catch (error) {
|
||||
// const file_name = `${path_msg["area"]}-${path_msg["type"]}-${path_msg["detail"]}`;
|
||||
// log.info(`路径: ${file_name} 执行时出错,已跳过...\n错误信息: ${error}`)
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,13 +1,12 @@
|
||||
{
|
||||
"manifest_version": 1,
|
||||
"name": "提瓦特自动钓鱼(全流程+自选)",
|
||||
"version": "2.1.0",
|
||||
"bgi_version": "0.45.0",
|
||||
"description": "脚本名称:提瓦特自动钓鱼(全流程+自选)\n功能描述:支持自动追踪并垂钓bgi支持的全提瓦特垂钓点\n核心功能------------------------------>\n1.可自选地区、鱼类、鱼饵\n2.可直接钓取特定物品的兑换材料(例如渔获)\n3.脚本会根据需要的鱼类自动调节时间,不需要的时段会跳过\n4.支持部分地图追踪无法到达的钓鱼点(例如炽岩斗士急流鱼钓鱼点,枫丹廷东北钓鱼点、雷鸣仙垂钓点)\n5.支持从特定的垂钓点继续任务(仅启用所有垂钓点时可用)\n6.默认禁用需要战斗的路线,如有需要请在JS脚本配置内启用\n7.支持自定义钓鱼超时时间\n8.支持设置定时关闭(最多24小时)\n9.4点自动领取月卡(可选)\n10.启用自动拾取(可选)\n注意事项------------------------------>\n1.部分点位涉及战斗,且队伍内不能有双风和跑步(不是冲刺)时加移速的角色\n2.跑图位必须是少男体型(防止键鼠路线[GCM]出错)\n3.同时选择鱼类和鱼饵的情况下按照以下逻辑选择路线: 所有被选的鱼类会被加入任务列表,如果选择的鱼饵中某个鱼饵不是已选的任何一个鱼类的对应的鱼饵,那么这个鱼饵对应的所有鱼类将被添加到任务列表\n4.JS脚本的设置内各设置项含有优先级,如果存在高优先级且选项不为默认,则只有最高优先级的设置项生效\n5.部分钓鱼点为路径追踪+键鼠脚本(GCM)的混合模式,可能会出现因键鼠脚本误差卡死的情况,如果出现这种情况,请在JS脚本设置禁用键鼠路线来禁用所有包含键鼠脚本的钓鱼点\n---------------------------------------->\n作者:提瓦特钓鱼玳师\n脚本反馈邮箱:hijiwos@hotmail.com",
|
||||
"version": "2.2.0",
|
||||
"bgi_version": "0.47.0",
|
||||
"description": "脚本名称:提瓦特自动钓鱼(全流程+自选)\n功能描述:支持自动追踪并垂钓bgi支持的全提瓦特垂钓点\n核心功能------------------------------>\n1.可自选地区、鱼类、鱼饵\n2.可直接钓取特定物品的兑换材料(例如渔获)\n3.脚本会根据需要的鱼类自动调节时间,不需要的时段会跳过\n4.支持部分地图追踪无法到达的钓鱼点(例如炽岩斗士急流鱼钓鱼点,枫丹廷东北钓鱼点、雷鸣仙垂钓点)\n5.支持从特定的垂钓点继续任务(仅启用所有垂钓点时可用)\n6.默认禁用需要战斗的路线,如有需要请在JS脚本配置内启用\n7.支持自定义钓鱼超时时间\n8.支持设置定时关闭(最多24小时)\n9.4点自动领取月卡(可选)\n10.自动记录垂钓点冷却时间(进入其他世界钓鱼时请关闭此功能)\n11.启用自动拾取(可选)\n注意事项------------------------------>\n1.部分点位涉及战斗,且队伍内不能有双风和跑步(不是冲刺)时加移速的角色\n2.跑图位必须是少男体型(防止键鼠路线[GCM]出错)\n3.同时选择鱼类和鱼饵的情况下按照以下逻辑选择路线: 所有被选的鱼类会被加入任务列表,如果选择的鱼饵中某个鱼饵不是已选的任何一个鱼类的对应的鱼饵,那么这个鱼饵对应的所有鱼类将被添加到任务列表\n4.JS脚本的设置内各设置项含有优先级,如果存在高优先级且选项不为默认,则只有最高优先级的设置项生效\n5.部分钓鱼点为路径追踪+键鼠脚本(GCM)的混合模式,可能会出现因键鼠脚本误差卡死的情况,如果出现这种情况,请在JS脚本设置禁用键鼠路线来禁用所有包含键鼠脚本的钓鱼点\n---------------------------------------->\n作者:提瓦特钓鱼玳师\n脚本反馈邮箱:hijiwos@hotmail.com",
|
||||
"authors": [
|
||||
{
|
||||
"name": "提瓦特钓鱼玳师",
|
||||
"links": "https://github.com/Hijiwos"
|
||||
"name": "提瓦特钓鱼玳师"
|
||||
}
|
||||
],
|
||||
"settings_ui": "settings.json",
|
||||
|
||||
@@ -2,7 +2,8 @@
|
||||
{
|
||||
"name": "show_info",
|
||||
"type": "input-text",
|
||||
"label": "下方输入的内容用空格隔开、括号内是优先级\n(只会执行当前非默认最高优先级的选项)"
|
||||
"label": "下方输入的内容用空格隔开、括号内是优先级\n(只会执行当前非默认最高优先级的选项)",
|
||||
"default": "该输入框无需输入内容"
|
||||
},
|
||||
{
|
||||
"name": "path_sort_area",
|
||||
@@ -127,22 +128,32 @@
|
||||
{
|
||||
"name": "time_out_throw",
|
||||
"type": "input-text",
|
||||
"label": "自动抛竿未上钩超时时间(秒) 默认: 10"
|
||||
"label": "自动抛竿未上钩超时时间(秒)",
|
||||
"default": 10
|
||||
},
|
||||
{
|
||||
"name": "time_out_whole",
|
||||
"type": "input-text",
|
||||
"label": "整个任务超时时间(秒) 默认: 300"
|
||||
"label": "整个任务超时时间(秒)",
|
||||
"default": 300
|
||||
},
|
||||
{
|
||||
"name": "auto_pick",
|
||||
"type": "checkbox",
|
||||
"label": "启用自动拾取(默认禁用)"
|
||||
"label": "启用自动拾取",
|
||||
"default": false
|
||||
},
|
||||
{
|
||||
"name": "auto_skip",
|
||||
"type": "checkbox",
|
||||
"label": "启用4点领取月卡(默认禁用)"
|
||||
"label": "启用4点领取月卡",
|
||||
"default": false
|
||||
},
|
||||
{
|
||||
"name": "fishing_cd",
|
||||
"type": "checkbox",
|
||||
"label": "启用垂钓点CD统计(自动跳过冷却中的垂钓点)",
|
||||
"default": true
|
||||
},
|
||||
{
|
||||
"name": "time_kill_hour",
|
||||
@@ -247,17 +258,20 @@
|
||||
{
|
||||
"name": "block_gcm",
|
||||
"type": "checkbox",
|
||||
"label": "禁用键鼠路线(默认启用键鼠路线)"
|
||||
"label": "禁用键鼠路线(启用前请自行了解队伍配置要求)",
|
||||
"default": false
|
||||
},
|
||||
{
|
||||
"name": "block_fight",
|
||||
"type": "checkbox",
|
||||
"label": "启用战斗路线(默认禁用战斗路线)"
|
||||
"label": "启用战斗路线(需要自行配置战斗策略)",
|
||||
"default": false
|
||||
},
|
||||
{
|
||||
"name": "block_tsurumi",
|
||||
"type": "checkbox",
|
||||
"label": "启用鹤观路线(默认禁用鹤观路线)"
|
||||
"label": "启用鹤观路线(请确保任务已经完成,小道具交互的点位尚不可用)",
|
||||
"default": false
|
||||
},
|
||||
{
|
||||
"name": "path_select",
|
||||
|
||||
Reference in New Issue
Block a user