My friends and family are under attack in Ukraine. Donate to protect them directly or help international organizations.

When garbage collection does more than you want

September 4th, 2009

I had an interesting Flex bug to solve a day before the project deadline. I was showing a progress bar while some images were preloading in the background. The application was only allowed to fireĀ applicationComplete event once these images have finished loading.

The client complained that the progress bar stalls the first time you run the app in the browser. Refreshing the page causes the application to start immediately, as if everything has been loaded. I reproduced the bug with bandwidth throttling. That made me think: "the assets are being fully loaded, but the progress bar doesn't seem to care".

With further investigation, I realized that I solved the same problem over a year ago. When one creates Loaders on the fly, such as in a loop, one often does not keep any reference to these Loaders outside of the scope of the function. Since it is a good habit to make event listeners weak, it is possible for the garbage collector to flag these Loaders for removal before they even have a chance to fire their complete event.

So to make sure that the progress bar does not stall, I needed to keep a reference to the Loader that I create within my loop. I simply pushed every Loader to an array. Once everything finished loading and the application started, I cleared the array to allow the garbage collector to take care of the rest.

Problem

Progress bar stalls while preloading images.

Cause

Loaders with weak event listeners and no references to them within the application.

Solution

Use an array to store references to the Loaders until all of them have finished loading.

Previous: PaperVision3D and JigLib Next: Simplify camera parameters in pv3d