fix: 鸡腿好感和盗宝团好感修复,使用新版exit_and_relogin action (#473)

* 盗宝团好感

* 避免计算出负数运行次数

* fix: 鸡腿好感修复
This commit is contained in:
秋云
2025-03-27 09:55:28 +08:00
committed by GitHub
parent 7262e64b36
commit ab7b485755
14 changed files with 291 additions and 297 deletions

View File

@@ -1,28 +0,0 @@
{
"info": {
"name": "两武士",
"type": "collect",
"author": "HZYgrandma",
"version": "1.0",
"description": "",
"bgiVersion": "0.35.1"
},
"positions": [
{
"id": 1,
"action": "",
"move_mode": "walk",
"type": "teleport",
"x": -2738.38671875,
"y": -3414.45703125
},
{
"id": 2,
"x": -2739.7236328125,
"y": -3400.15625,
"type": "path",
"move_mode": "walk",
"action": ""
}
]
}

File diff suppressed because one or more lines are too long

View File

@@ -1,109 +0,0 @@
(async function () {
const defaultExitDelay = 12;
const defaultLoadingDelay = 15;
function validateAndSetDefaults(exitDelay, loadingDelay) {
if (isNaN(exitDelay) || exitDelay <= 0) {
log.warn("你没有设置退出延迟将使用默认值12秒");
exitDelay = defaultExitDelay;
}
if (isNaN(loadingDelay) || loadingDelay <= 0) {
log.warn("你没有设置加载延迟将使用默认值15秒");
loadingDelay = defaultLoadingDelay;
}
return { exitDelay, loadingDelay };
}
async function runGameActionsMultipleTimes() {
await sleep(1000);
keyPress("ESCAPE");
await sleep(1000);
click(50, 1030);
await sleep(1000);
click(1000, 750);
await sleep(validatedExitDelay * 1000);
click(1000, 550);
await sleep(validatedLoadingDelay * 1000);
}
async function resetMap() {
log.info("重置地图大小...");
await sleep(1000);
keyPress("M");
await sleep(1000);
click(1840, 1010);
await sleep(1000);
click(1450, 460);
await sleep(1000);
click(1840, 1010);
await sleep(1000);
click(1450, 140);
await sleep(1000);
keyPress("M");
log.info("重置地图大小完成");
}
async function AutoPath(locationName) {
try {
let filePath = `assets/AutoPath/${locationName}.json`;
await pathingScript.runFile(filePath);
} catch (error) {
log.error(`执行 ${locationName} 路径时发生错误`);
}
await sleep(2000);
}
async function AutoFriendshipDev(times) {
await resetMap();
log.info(`清理原住民...`);
await AutoPath('清理原住民');
log.info(`自动好感开始...`);
for (let i = 0; i < times; i++) {
await AutoPath('两武士');
await runGameActionsMultipleTimes();
log.info(`自动好感当前次数:${i + 1}/${times}`);
await AutoPath('盗宝团');
logTimeTaken(startTime);
}
log.info('自动好感已完成');
}
function logTimeTaken(startTime) {
const currentTime = Date.now();
const totalTimeInSeconds = (currentTime - startTime) / 1000;
const minutes = Math.floor(totalTimeInSeconds / 60);
const seconds = totalTimeInSeconds % 60;
const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')}`;
log.info(`当前运行总时长:${formattedTime}`);
}
// 启用自动拾取的实时任务
const startTime = Date.now();
dispatcher.addTimer(new RealtimeTimer("AutoPick"));
setGameMetrics(1920, 1080, 1); // 设置游戏窗口大小和DPI
let exitdelay = Number(settings.exitdelay);
let loadingdelay = Number(settings.loadingdelay);
const { exitDelay: validatedExitDelay, loadingDelay: validatedLoadingDelay } = validateAndSetDefaults(exitdelay, loadingdelay);
const messages = [
'请确保当前队伍为好感度队伍',
'好感度队伍:用待刷好感角色替换战斗策略中的人物即可',
'随后将自动匹配到战斗策略脚本',
];
for (let message of messages) {
log.info(message);
await sleep(1000);
}
log.info('自动好感开始...');
log.info(`退出延迟: ${validatedExitDelay}秒, 加载延迟: ${validatedLoadingDelay}`);
//默认10次自动好感
await AutoFriendshipDev(10);
// 计算并输出总时长
const endTime = Date.now();
const totalTimeInSeconds = (endTime - startTime) / 1000;
const minutes = Math.floor(totalTimeInSeconds / 60);
const seconds = totalTimeInSeconds % 60;
const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')}`;
log.info(`自动好感运行总时长:${formattedTime}`);
})();

View File

@@ -1,13 +0,0 @@
{
"manifest_version": 1,
"name": "自动好感度",
"version": "1.0",
"description": "通过突发事件刷好感度,请配合好感度战斗脚本使用",
"authors": [
{
"name": "HZYgrandma & 愚溪",
}
],
"settings_ui": "settings.json",
"main": "main.js"
}

View File

@@ -1,12 +0,0 @@
[
{
"name": "exitdelay",
"type": "input-text",
"label": "退出延迟(秒)(选填)"
},
{
"name": "loadingdelay",
"type": "input-text",
"label": "加载延迟(秒)(选填)"
}
]

View File

@@ -10,43 +10,35 @@
"positions": [ "positions": [
{ {
"id": 1, "id": 1,
"x": -2740.609375, "x": -2740.60,
"y": -3410.6923828125, "y": -3410.69,
"action": "", "action": "",
"move_mode": "walk", "move_mode": "walk",
"type": "teleport" "type": "teleport"
}, },
{ {
"id": 2, "id": 2,
"x": -2739.4873046875, "x": -2739.48,
"y": -3437.853515625, "y": -3437.85,
"action": "", "action": "",
"move_mode": "walk", "move_mode": "walk",
"type": "path" "type": "path"
}, },
{ {
"id": 3, "id": 3,
"x": -2764.4423828125, "x": -2764.44,
"y": -3465.810546875, "y": -3465.81,
"action": "", "action": "",
"move_mode": "walk", "move_mode": "walk",
"type": "path" "type": "path"
}, },
{ {
"id": 4, "id": 4,
"x": -2771.2705078125, "x": -2771.27,
"y": -3453.2373046875, "y": -3453.23,
"action": "fight", "action": "fight",
"move_mode": "walk", "move_mode": "walk",
"type": "path" "type": "path"
},
{
"id": 5,
"x": -2776.25,
"y": -3454.6982421875,
"action": "",
"move_mode": "walk",
"type": "path"
} }
] ]
} }

View File

@@ -5,29 +5,45 @@
"author": "HZYgrandma", "author": "HZYgrandma",
"version": "1.0", "version": "1.0",
"description": "", "description": "",
"bgiVersion": "0.35.1" "bgiVersion": "0.43.4"
}, },
"positions": [ "positions": [
{ {
"id": 1,
"action": "",
"move_mode": "walk",
"type": "teleport",
"x": -2738.38,
"y": -3414.45
},
{
"id": 2,
"x": -2739.72,
"y": -3400.15,
"type": "path",
"move_mode": "walk",
"action": "exit_and_relogin"
},
{
"id": 3, "id": 3,
"x": -2739.7197265625, "x": -2739.71,
"y": -3399.060546875, "y": -3399.06,
"type": "path", "type": "path",
"move_mode": "walk", "move_mode": "walk",
"action": "" "action": ""
}, },
{ {
"id": 4, "id": 4,
"x": -2738.671875, "x": -2738.67,
"y": -3427.38671875, "y": -3427.38,
"type": "path", "type": "path",
"move_mode": "run", "move_mode": "run",
"action": "" "action": ""
}, },
{ {
"id": 5, "id": 5,
"x": -2756.6748046875, "x": -2756.67,
"y": -3467.6328125, "y": -3467.63,
"type": "path", "type": "path",
"move_mode": "walk", "move_mode": "walk",
"action": "fight" "action": "fight"

View File

@@ -0,0 +1,158 @@
(async function () {
const DEFAULT_RUNS = 10;
const DEFAULT_PERIOD = 25;
const DEFAULT_BASE_RUNS = 50;
const BENCHMARK_HOUR = "T04:00:00";
const TELEPORT_COORDS = { x: 2297.60, y: -824.45 };
// 执行 path 任务
async function AutoPath(locationName) {
try {
const filePath = `assets/AutoPath/${locationName}.json`;
await pathingScript.runFile(filePath);
} catch (error) {
log.error(`执行 ${locationName} 路径时发生错误: ${error.message}`);
}
await sleep(2000);
}
// 计算运行时长
function LogTimeTaken(startTimeParam) {
const currentTime = Date.now();
const totalTimeInSeconds = (currentTime - startTimeParam) / 1000;
const minutes = Math.floor(totalTimeInSeconds / 60);
const seconds = totalTimeInSeconds % 60;
const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')}`;
return formattedTime;
}
// 计算预估时间
function CalculateEstimatedCompletion(startTime, current, total) {
if (current === 0) return "计算中...";
const elapsedTime = Date.now() - startTime;
const timePerTask = elapsedTime / current;
const remainingTasks = total - current;
const remainingTime = timePerTask * remainingTasks;
const completionDate = new Date(Date.now() + remainingTime);
return `${completionDate.toLocaleTimeString()} (约 ${Math.round(remainingTime / 60000)} 分钟)`;
}
// 执行 N 次盗宝团任务并输出日志
async function AutoFriendshipDev(times) {
startFisrtTime = Date.now();
for (let i = 0; i < times; i++) {
await AutoPath('盗宝团');
const estimatedCompletion = CalculateEstimatedCompletion(startFisrtTime, i + 1, times);
const currentTime = LogTimeTaken(startFisrtTime);
log.info(`当前进度:${i + 1}/${times} (${((i + 1) / times * 100).toFixed(1)}%)`);
log.info(`当前运行总时长:${currentTime}`);
log.info(`预计完成时间:${estimatedCompletion}`);
}
log.info('盗宝团好感已完成');
}
// 验证输入是否是正整数
function isPositiveInteger(value) {
return Number.isInteger(value) && value > 0;
}
// 验证日期格式
function isValidDateFormat(dateStr) {
if (!dateStr) return false;
// 检查格式是否为 YYYY-MM-DD
const regex = /^\d{4}-\d{2}-\d{2}$/;
if (!regex.test(dateStr)) return false;
// 检查是否为有效日期
const date = new Date(dateStr);
return !isNaN(date.getTime());
}
function calculateWaitModeRuns(baseRuns, waitTimeModeDay, period) {
const now = new Date();
const benchmark = new Date(waitTimeModeDay + BENCHMARK_HOUR);
const timeDiff = now.getTime() - benchmark.getTime();
const daysDiff = Math.floor(timeDiff / (1000 * 60 * 60 * 24));
const daysNormalized = daysDiff >= 0 ? daysDiff : period - (Math.abs(daysDiff) % period);
const dayInCycle = (daysNormalized % period) + 1;
const baseRunsPerDay = Math.ceil(baseRuns / period);
return baseRunsPerDay * dayInCycle;
}
async function switchPartyIfNeeded(partyName) {
if (!partyName) {
await genshin.returnMainUi();
return;
}
try {
await genshin.tp(TELEPORT_COORDS.x, TELEPORT_COORDS.y);
await sleep(3000);
log.info(`正在尝试切换至:${partyName}`);
await genshin.switchParty(partyName);
log.info(`队伍切换成功,继续下一步任务`);
} catch (error) {
log.warn("队伍切换失败,可能处于联机模式或其他不可切换状态");
await genshin.returnMainUi();
}
}
// 启用自动拾取的实时任务
const startTime = Date.now();
dispatcher.addTimer(new RealtimeTimer("AutoPick"));
log.info(`'请确保队伍满员,并为队伍配置相应的战斗策略'`);
// 计算运行次数
let runTimes = Number(settings.runTimes);
if(!isPositiveInteger(runTimes) && !settings.waitTimeMode){
log.warn("请输入正确的次数,必须是正整数!");
log.warn(`运行次数重置为 ${DEFAULT_RUNS} 次!`);
runTimes = DEFAULT_RUNS;
}
if(settings.waitTimeMode){
if(!isPositiveInteger(runTimes)){
log.warn("运行次数必须是正整数,使用默认基准次数");
log.warn(`运行次数重置为 ${DEFAULT_BASE_RUNS} 次!`);
runTimes = DEFAULT_BASE_RUNS;
}
// 验证日期格式
const waitTimeModeDay = settings.waitTimeModeDay;
if (!isValidDateFormat(waitTimeModeDay)) {
log.error("基准日期格式错误,请检查后重试!");
log.error("参考格式2025-01-01");
log.error(`错误输入:${waitTimeModeDay}`);
await sleep(5000);
return;
}
let period = Number(settings.waitTimeModePeriod);
if(!isPositiveInteger(period) || period > runTimes){
period = DEFAULT_PERIOD < runTimes? DEFAULT_PERIOD : runTimes;
log.warn(`卡时间模式周期必须是 1-${runTimes} 之间的正整数!使用 ${period} 作为周期`);
}
runTimes = calculateWaitModeRuns(runTimes, waitTimeModeDay, period);
// 添加日志输出,提醒用户当前使用的基准日期和周期
log.info(`当前使用的基准日期: ${waitTimeModeDay}`);
log.info(`当前使用的周期: ${period}`);
log.info(`根据基准日期和周期计算,今日运行次数: ${runTimes}`);
} else {
log.info(`当前设置的运行次数: ${runTimes}`);
}
await switchPartyIfNeeded(settings.partyName);
log.info('盗宝团好感开始...');
// 清理丘丘人
if(settings.qiuQiuRen){
log.info(`清理原住民...`);
await AutoPath('清理原住民');
}
// 盗宝团好感循环开始
await AutoFriendshipDev(runTimes);
log.info(`盗宝团好感运行总时长:${LogTimeTaken(startTime)}`);
})();

View File

@@ -0,0 +1,13 @@
{
"manifest_version": 1,
"name": "盗宝团好感:自动好感度&刷盗宝团&卡时间",
"version": "1.1",
"description": "通过突发事件【岛上无贼】刷好感度,刷盗宝团材料,小怪锄地,卡时间等,请配合战斗脚本使用。在 HZYgrandma & 愚溪的原始脚本上改编。",
"authors": [
{
"name": "秋云"
}
],
"settings_ui": "settings.json",
"main": "main.js"
}

View File

@@ -0,0 +1,32 @@
[
{
"name": "qiuQiuRen",
"type": "checkbox",
"label": "是否清理丘丘人【默认否,选是会清理丘丘人之后再开始盗宝团好感】"
},
{
"name": "partyName",
"type": "input-text",
"label": "(选填)需要切换的队伍名称"
},
{
"name": "runTimes",
"type": "input-text",
"label": "(选填)运行次数【默认10次卡时间模式默认50次】"
},
{
"name": "waitTimeMode",
"type": "checkbox",
"label": "卡时间模式【基于运行次数、基准日期、周期确定需要运行次数】"
},
{
"name": "waitTimeModeDay",
"type": "input-text",
"label": "卡时间模式基准日期【格式参考2025-01-01】"
},
{
"name": "waitTimeModePeriod",
"type": "input-text",
"label": "(选填)卡时间模式周期【默认25天】"
}
]

View File

@@ -18,7 +18,7 @@
}, },
{ {
"id": 2, "id": 2,
"action": "", "action": "exit_and_relogin",
"move_mode": "walk", "move_mode": "walk",
"type": "target", "type": "target",
"x": -4529.2578125, "x": -4529.2578125,

View File

@@ -46,7 +46,7 @@
"y": -3084.009765625, "y": -3084.009765625,
"type": "target", "type": "target",
"move_mode": "walk", "move_mode": "walk",
"action": "" "action": "exit_and_relogin"
} }
] ]
} }

View File

@@ -1,157 +1,103 @@
(async function () { (async function () {
const TELEPORT_COORDS = { x: 2297.60, y: -824.45 };
const defaultExitDelay = 12; async function switchPartyIfNeeded(partyName) {
const defaultLoadingDelay = 15; if (!partyName) {
await genshin.returnMainUi();
function validateAndSetDefaults(exitDelay, loadingDelay) { return;
if (isNaN(exitDelay) || exitDelay <= 0) {
log.warn("你没有设置退出延迟将使用默认值12秒");
exitDelay = defaultExitDelay;
} }
if (isNaN(loadingDelay) || loadingDelay <= 0) {
log.warn("你没有设置加载延迟将使用默认值15秒"); try {
loadingDelay = defaultLoadingDelay; await genshin.tp(TELEPORT_COORDS.x, TELEPORT_COORDS.y);
await sleep(3000);
log.info(`正在尝试切换至:${partyName}`);
await genshin.switchParty(partyName);
log.info(`队伍切换成功,继续下一步任务`);
} catch (error) {
log.warn("队伍切换失败,可能处于联机模式或其他不可切换状态");
await genshin.returnMainUi();
} }
return { exitDelay, loadingDelay };
} }
async function ReopenTheGate() {
await sleep(1000);
keyPress("ESCAPE");
await sleep(1000);
click(50, 1030);
await sleep(1000);
click(1000, 750);
await sleep(validatedExitDelay * 1000);
click(1000, 550);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
click(1000, 750);
await sleep(1000);
await sleep(validatedLoadingDelay * 1000);
click(1000, 750);
await sleep(1000);
}
async function Feed() { async function Feed() {
await sleep(1000); await sleep(500);
keyPress("F");
await sleep(500);
keyPress("F"); keyPress("F");
await sleep(1000); await sleep(1000);
click(1010, 760); click(1010, 760);
await sleep(1000); await sleep(1000);
} }
async function resetMap() {
log.info("重置地图大小...");
await sleep(1000);
keyPress("M");
await sleep(1000);
click(1840, 1010);
await sleep(1000);
click(1450, 460);
await sleep(1000);
click(1840, 1010);
await sleep(1000);
click(1450, 140);
await sleep(1000);
keyPress("M");
log.info("重置地图大小完成");
}
async function AutoPath(locationName) { async function AutoPath(locationName) {
try { try {
let filePath = `assets/AutoPath/${locationName}.json`; const filePath = `assets/AutoPath/${locationName}.json`;
await pathingScript.runFile(filePath); await pathingScript.runFile(filePath);
} catch (error) { } catch (error) {
log.error(`执行 ${locationName} 路径时发生错误`); log.error(`执行 ${locationName} 路径时发生错误: ${error.message}`);
log.error(error.message);
} }
await sleep(2000); await sleep(2000);
} }
async function AutoFriendshipDev(times) { async function AutoFriendshipDev(times) {
await resetMap();
log.info(`导航至甜甜花位置`); log.info(`导航至甜甜花位置`);
await AutoPath('导航至甜甜花位置'); await AutoPath('导航至甜甜花位置');
log.info(`自动好感开始...`); log.info(`自动好感开始...`);
const startFirstTime = Date.now();
await ReopenTheGate();
for (let i = 0; i < times; i++) { for (let i = 0; i < times; i++) {
log.info(`自动好感当前次数:${i + 1}/${times}`); log.info(`自动好感当前次数:${i + 1}/${times}`);
await AutoPath('从甜甜花到狗盆'); await AutoPath('从甜甜花到狗盆');
await Feed(); await Feed();
await AutoPath('从狗盆到甜甜花'); await AutoPath('从狗盆到甜甜花');
await ReopenTheGate(); const estimatedCompletion = CalculateEstimatedCompletion(startFirstTime, i + 1, times);
logTimeTaken(startTime); const currentTime = LogTimeTaken(startFirstTime);
log.info(`当前进度:${i + 1}/${times} (${((i + 1) / times * 100).toFixed(1)}%)`);
log.info(`当前运行总时长:${currentTime}`);
log.info(`预计完成时间:${estimatedCompletion}`);
} }
log.info('自动好感已完成'); log.info('自动好感已完成');
} }
function logTimeTaken(startTime) { function LogTimeTaken(startTimeParam) {
const currentTime = Date.now(); const currentTime = Date.now();
const totalTimeInSeconds = (currentTime - startTime) / 1000; const totalTimeInSeconds = (currentTime - startTimeParam) / 1000;
const minutes = Math.floor(totalTimeInSeconds / 60); const minutes = Math.floor(totalTimeInSeconds / 60);
const seconds = totalTimeInSeconds % 60; const seconds = totalTimeInSeconds % 60;
const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')}`; const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')} `;
log.info(`当前运行总时长:${formattedTime}`); return formattedTime;
}
// 计算预估时间
function CalculateEstimatedCompletion(startTime, current, total) {
if (current === 0) return "计算中...";
const elapsedTime = Date.now() - startTime;
const timePerTask = elapsedTime / current;
const remainingTasks = total - current;
const remainingTime = timePerTask * remainingTasks;
const completionDate = new Date(Date.now() + remainingTime);
return `${completionDate.toLocaleTimeString()} (约 ${Math.round(remainingTime / 60000)} 分钟)`;
} }
// 启用自动拾取的实时任务 // 启用自动拾取的实时任务
const startTime = Date.now(); const startTime = Date.now();
dispatcher.addTimer(new RealtimeTimer("AutoPick")); dispatcher.addTimer(new RealtimeTimer("AutoPick"));
setGameMetrics(1920, 1080, 1); // 设置游戏窗口大小和DPI
let exitdelay = Number(settings.exitdelay);
let loadingdelay = Number(settings.loadingdelay);
const { exitDelay: validatedExitDelay, loadingDelay: validatedLoadingDelay } = validateAndSetDefaults(exitdelay, loadingdelay);
const messages = [ const messages = [
'请确保有足够的鸡腿', '请确保有足够的鸡腿',
'请确保队伍满员', '请确保队伍满员',
'大约需要17分钟' `自动好感任务开始,运行:${settings.times}`,
]; ];
for (let message of messages) { for (let message of messages) {
log.info(message); log.info(message);
await sleep(1000); await sleep(500);
} }
await switchPartyIfNeeded(settings.partyName);
log.info('自动好感开始...'); log.info('自动好感开始...');
log.info(`退出延迟: ${validatedExitDelay}秒, 加载延迟: ${validatedLoadingDelay}`);
//默认10次自动好感 //默认10次自动好感
await AutoFriendshipDev(10); await AutoFriendshipDev(settings.times);
// 计算并输出总时长
const endTime = Date.now(); log.info(`自动好感运行总时长:${LogTimeTaken(startTime)}`);
const totalTimeInSeconds = (endTime - startTime) / 1000;
const minutes = Math.floor(totalTimeInSeconds / 60);
const seconds = totalTimeInSeconds % 60;
const formattedTime = `${minutes}${seconds.toFixed(0).padStart(2, '0')}`;
log.info(`自动好感运行总时长:${formattedTime}`);
})(); })();

View File

@@ -1,12 +1,12 @@
[ [
{ {
"name": "exitdelay", "name": "times",
"type": "input-text", "type": "input-text",
"label": "退出延迟(秒)(选填)" "label": "(选填)运行次数【默认10为避免失败可以酌情添加次数】"
}, },
{ {
"name": "loadingdelay", "name": "partyName",
"type": "input-text", "type": "input-text",
"label": "加载延迟(秒)(选填)" "label": "(选填)需要切换的队伍名称【前往设置的七天神像切换好感队】"
} }
] ]