round2: 看门狗礼仪F1(不重播/单句升级/idle-skip) + 分档归因F2 + 交接count-in/answer F3 + 教学看表现F4-F5 + 警报去叠F6 + 回绕F7 + 开场瘦身F8 + 10句新语音 + 测试全绿(6playtest零改动+guide52断言+资产终检)
This commit is contained in:
@@ -1,7 +1,9 @@
|
||||
/**
|
||||
* 《声命线》新手会话剧本:像真人一样等语音播完再动、偶尔走神(触发看门狗)、
|
||||
* 在非抉择节点试一次无效的左滑(触发向导纠错)、菜单进去逛一圈再出来、
|
||||
* 抉择点一律选左,一路打到结局。
|
||||
* 《声命线》新手会话剧本:像真人一样等语音播完再动、偶尔走神(触发看门狗,
|
||||
* 听到轻响后 5 秒内回应——round2 修正剧本失真:round1 的「干晾 85 秒」是剧本
|
||||
* 问题不是游戏问题)、在非抉择节点试一次无效的左滑(触发向导纠错)、中途演示
|
||||
* 一次语速 2.2 切换(F9:设置下一句即时生效,转写状态行可见语速档)、菜单逛
|
||||
* 一圈再出来、抉择点一律选左,一路打到结局。
|
||||
*/
|
||||
export function describe(game) {
|
||||
if (game.mode === 'MENU') return '菜单里:左滑重开、右滑或单击返回剧情、上滑听帮助';
|
||||
@@ -15,17 +17,21 @@ export async function session(ctx, mock) {
|
||||
const { game } = ctx;
|
||||
let invalidTried = false;
|
||||
let menuDone = false;
|
||||
let speedDemoDone = false;
|
||||
let speedBackDone = false;
|
||||
|
||||
// 开场:n00 全听完,愣一会儿——向导看门狗先说话
|
||||
await ctx.waitIdle();
|
||||
ctx.status('开场旁白播完了,屏幕黑着,有点不知所措');
|
||||
ctx.silence(8, '新手没反应过来');
|
||||
await ctx.waitVirtual(8600); // 触发看门狗:nudge + gd_continue
|
||||
ctx.status('听到一声轻响和「轻触屏幕,继续」,试着点一下');
|
||||
await ctx.gesture('tap');
|
||||
// 开场:gd_brief 先给操作口令(round2 F8),n00 全听完,再愣一会儿——看门狗 25s 才说话
|
||||
await ctx.waitCond(() => !game.voicePlaying); // 只等链播完(不空烧看门狗窗口)
|
||||
ctx.status('开场口令和旁白播完了,屏幕黑着,走神想剧情去了');
|
||||
ctx.silence(25, '在入戏,不是迷路(round2:剧情类等待默认低频)');
|
||||
await ctx.waitVirtual(25600); // 触发看门狗:nudge + gd_continue
|
||||
ctx.status('听到一声轻响和「轻触屏幕,继续」,马上点一下');
|
||||
await ctx.gesture('tap'); // 听到提示 ≤5s 内反应
|
||||
|
||||
for (let i = 0; i < 60 && !game.awaitingRestart && mock.now < 20 * 60 * 1000; i++) {
|
||||
await ctx.waitIdle(); // 等当前语音链播完(真人不会抢话)
|
||||
// 只等语音链播完(真人不会抢话)。不能裸 waitIdle——会把等待态看门狗的两级
|
||||
// 提醒整段空烧完才动手(round1 剧本失真根源),链一停就该轮到玩家了
|
||||
await ctx.waitCond(() => !game.voicePlaying);
|
||||
|
||||
if (game.awaitingRestart) break;
|
||||
|
||||
@@ -45,6 +51,27 @@ export async function session(ctx, mock) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// F9:演示一次语速切换——2.2 档对下一句即时生效,听两段再调回 1.0
|
||||
if (!speedDemoDone && game.nodeId === 'n10') {
|
||||
speedDemoDone = true;
|
||||
ctx.note('旁白有点慢,去设置把语速调到 2.2(下一句生效)');
|
||||
ctx.settings.set({ speed: 2.2 });
|
||||
if (game.choiceArmed) {
|
||||
ctx.note('选了左边(循声而去)——后面几步都是 2.2 档');
|
||||
await ctx.gesture('left'); // n10 抉择 → n11,2.2 倍速播
|
||||
} else {
|
||||
await ctx.gesture('tap');
|
||||
}
|
||||
await ctx.waitIdle();
|
||||
ctx.status('语速 2.2 听着赶趟');
|
||||
continue;
|
||||
}
|
||||
if (speedDemoDone && !speedBackDone && game.nodeId === 'n12') {
|
||||
speedBackDone = true;
|
||||
ctx.note('听了两段,把语速调回 1.0');
|
||||
ctx.settings.set({ speed: 1.0 });
|
||||
}
|
||||
|
||||
if (game.choiceArmed) {
|
||||
ctx.status('抉择点,提示音念完了');
|
||||
if (mock.now % 2 < 1) await ctx.waitVirtual(3000); // 偶尔犹豫一下
|
||||
@@ -59,19 +86,19 @@ export async function session(ctx, mock) {
|
||||
invalidTried = true;
|
||||
ctx.note('试着左滑了一下——这里用不上,向导纠正了我');
|
||||
await ctx.gesture('left');
|
||||
await ctx.waitIdle();
|
||||
await ctx.waitVirtual(2000); // 让纠错句播完(不空烧看门狗窗口)
|
||||
} else if (i % 4 === 2) {
|
||||
ctx.silence(8, '走神想剧情去了');
|
||||
await ctx.waitVirtual(8600); // 偶尔挂机,触发看门狗轻提醒
|
||||
ctx.status('又听到那声轻响,想起该点屏幕了');
|
||||
ctx.silence(25, '又走神想剧情去了');
|
||||
await ctx.waitVirtual(25600); // 偶尔挂机,触发看门狗轻提醒(25s 才响,不轰炸)
|
||||
ctx.status('又听到那声轻响,5 秒内想起该点屏幕了');
|
||||
}
|
||||
await ctx.gesture('tap');
|
||||
}
|
||||
|
||||
await ctx.waitIdle();
|
||||
await ctx.waitCond(() => !game.voicePlaying);
|
||||
ctx.status('结局');
|
||||
ctx.note('听完结局,单击重开一次看看别的走向');
|
||||
await ctx.gesture('tap'); // 结算态单击重开
|
||||
await ctx.waitIdle();
|
||||
await ctx.waitCond(() => !game.voicePlaying);
|
||||
ctx.status('回到开头,会话结束');
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user