Load the first playable slice
Group assets by the earliest moment they are needed: title and first scene, next level, then optional effects or cosmetics. Load and validate the first group before enabling the start action. For images used in a sudden scene transition, HTMLImageElement.decode() can resolve after an image is decoded, allowing the swap to happen without making that next draw wait for decoding.
Test on a constrained connection by delaying one required image and failing another. The progress indicator should advance only as named work completes, the failed asset should produce a recoverable message or fallback, and the start control should not promise a playable scene while a required dependency is missing.
Keep progress honest
When the set of tasks is known, show completed tasks out of the total or report a phase such as preparing the first level. Byte-based percentages are only meaningful when the relevant sizes are known; decoding, audio setup, and procedural initialization may take time after transfer completes.
Do not block the entire interface for assets that can arrive later. Use a low-cost placeholder for optional art, then replace it when its decoded image is ready. Verify that the placeholder remains legible at the intended canvas size and that a failed optional download does not strand the player on the loading state.
Questions about browser game asset loading
Is preloading every asset a good idea?
Usually not by default. Load what is needed for the first playable moment, then schedule other work based on when it will be used and how much memory it requires.
Does an image load event mean it is ready for smooth drawing?
The bytes may be available while decode work still affects presentation. MDN documents decode() as a promise for when an image is decoded and safe to append; measure whether that distinction matters in your scene.