Quick answer: Set op.allowSceneActivation = false. Drive your visible bar from op.progress / 0.9f clamped to 1. When that hits 1, set allowSceneActivation = true to flip the scene in.
Loading bar fills smoothly to 90% and freezes. Players think the game crashed. Unity holds at 0.9 by design until you allow activation.
The Symptom
op.progress climbs to 0.9 and stops. Scene activates anyway after a hitch. Or with allowSceneActivation = false, hangs at 0.9 forever.
The Fix
public class SceneLoader : MonoBehaviour
{
public Image bar;
public IEnumerator LoadAsync(string scene)
{
var op = SceneManager.LoadSceneAsync(scene);
op.allowSceneActivation = false;
while (op.progress < 0.9f)
{
bar.fillAmount = op.progress / 0.9f;
yield return null;
}
// Smoothly fill to 100% before activation
var t = 0f;
while (t < 0.4f)
{
t += Time.deltaTime;
bar.fillAmount = Mathf.Lerp(bar.fillAmount, 1f, t);
yield return null;
}
bar.fillAmount = 1f;
op.allowSceneActivation = true;
}
}
Bar fills 0→1 over the actual load duration plus a small finish lerp. Player sees full bar before activation.
Activation Hitch
Activation calls Awake on every scene root. Heavy Awake methods cause a freeze frame. Optimize Awake or split work into a coroutine triggered after activation.
Verifying
Add a print of op.progress per frame. Should climb to 0.9, hold, then activate. With activation: scene swaps. Bar reaches 100% in your UI before the swap.
“Scale to 0.9. Block activation. Smooth lerp to 100. Flip the switch.”
Related Issues
For Addressables async, see handle leak. For async unobserved exception, see async exceptions.
Scale progress. Block activation. Reveal at 100.