Unity中yield return new WaitForSeconds不等待问题求助
问题:WaitForSeconds在对话流程中部分步骤失效
问题概述
使用WaitForSeconds创建延迟事件切换对话步骤推进剧情,部分场景正常,部分场景失效。首次执行符合预期,但后续连续4个步骤会直接跳过延迟进入下一步,之后延迟功能才恢复正常并结束流程。
代码片段
float waitTime = currentStep.isSpoken ? currentStep.dialogueClip.length + 1.0f : 2.0f; selectedText = null; if(currentStep.speaker.ToString() != "Gui"){ StartCoroutine( ProgessStep(waitTime) ); } IEnumerator ProgessStep(float waitTime) { if(currentStep.stepName.Equals("S1-P1-1")) { yield break; } else if(currentStep.stepName.Equals("S2-P1-5-8")) { if(levelManager.fireAlarmTested) { SetStep("S2-P1-5-10"); yield break; } else { levelManager.fireAlarmTested = true; } } if(currentStep.nextStep.Equals("")) yield break; Debug.Log($"Waiting for {waitTime}s before moving to {currentStep.nextStep}"); yield return new WaitForSeconds(waitTime); Debug.Log($"Moving to {currentStep.nextStep}"); if(!currentStep.canRespond) SetStep(currentStep.nextStep); }
预期结果
执行完前置检查后,等待音频片段(若存在)播放完毕再进入下一个对话步骤。
实际结果
首次执行延迟正常,后续连续4个步骤直接跳过WaitForSeconds进入下一步,之后延迟功能恢复正常并结束流程。
已尝试方案
- 使用
Invoke和WaitForSecondsRealtime测试:Invoke问题更严重,WaitForSecondsRealtime无改善 - 为
waitTime设置固定默认值 - 添加
try/catch块,未捕获到异常 - 使用
Mathf.Ceil或CeilToInt处理waitTime的小数位
排查与解决建议
阻止协程重复启动
大概率是切换步骤时重复启动了协程,多个协程并行执行导致后续步骤的延迟被覆盖。给协程加个全局引用,启动前先停止之前的:private Coroutine _currentProgressCoroutine; // 替换原启动协程的代码 if(currentStep.speaker.ToString() != "Gui"){ if(_currentProgressCoroutine != null) StopCoroutine(_currentProgressCoroutine); _currentProgressCoroutine = StartCoroutine(ProgessStep(waitTime)); }缓存步骤参数避免被修改
协程挂起期间,currentStep可能被其他逻辑提前修改,导致后续操作指向了新步骤。在协程开头就缓存关键参数:IEnumerator ProgessStep(float waitTime) { // 缓存当前步骤的目标下一步和自动推进标记 string targetNextStep = currentStep.nextStep; bool shouldAutoProceed = !currentStep.canRespond; // 原有检查逻辑保留... if(targetNextStep.Equals("")) yield break; Debug.Log($"Waiting for {waitTime}s before moving to {targetNextStep}"); yield return new WaitForSeconds(waitTime); Debug.Log($"Moving to {targetNextStep}"); if(shouldAutoProceed) SetStep(targetNextStep); }检查时间缩放异常
虽然试过WaitForSecondsRealtime,但还是要确认是否有逻辑修改了Time.timeScale。在日志里加上时间缩放的输出,确认数值是否正常:Debug.Log($"Waiting for {waitTime}s (timeScale: {Time.timeScale}) before moving to {targetNextStep}");追踪步骤切换时机
在SetStep方法里添加日志,输出当前切换的步骤名称和调用栈,看看是否有逻辑在延迟结束前就强制切换了步骤。
内容的提问来源于stack exchange,提问作者Aidan H M
相关产品推荐
相关产品推荐

