Separate PNGs vs. large imageSheets (scene loading time)

Hey everybody,

I’m beginning to put the finishing touches on an app I’m hoping to release in the next month or so and part of my clean-up has been to consolidate all of my images (which I’d been keeping in separate PNGs during development) into image sheets: one sheet for each scene in the app. I use storyboard to manage my scenes, and only load a single scene into memory at a time - I call storyboard.removeAll in every scene’s “enterScene” function. On average, these image sheets contain anywhere from 20 to 30 images on them. (I’m using TexturePacker to prepare my image sheets.) My understanding, based on official Corona Labs documentation and blog posts, is that consolidating into image sheets will maximize texture memory usage and should result in zippier performance. And my project’s image folder gets considerably tidier and easier to manage, which is indeed a nice perk.

In practice, however, I’ve noticed that while my texture memory usage is indeed (slightly) lower because I’ve consolidated images, load times for my scenes have actually gotten noticeably longer - scenes that previously loaded with no noticeable lag on-device can now take up to a second or a two, during which time the app becomes unresponsive (while the new scene’s “createScene” function is being called). Once the scene is loaded, performance is no different than before, but the loading delay struck me as odd. At the end of the day, I can always add a spinning wheel or other “I’m loading” indicator to cover the slight delay, but I was surprised to find that performance seems to have taken a hit because of a step I took to improve performance. It sounds weird, but I may just go back to using separate PNGs because the app felt more responsive that way.

Has anybody else noticed this in their projects? Any ideas of how I can keep using image sheets instead of separate PNGs but get that faster load time back? I’d love to get any feedback on this.

Thanks,
Jason

Hi Jason,

Using the separate images method, did you previously load all of them when the scene entered? Or did you load some of them over time, when needed? This might explain why it’s occurring… if you previously loaded a few images here, a few images there, then it makes sense that the app would “load” faster, despite having higher texture memory usage because of the un-sheeted images. With the image sheet, you’ll save texture memory, but the scene will need to load the entire thing before it can proceed… just the nature of image sheets.

Hope this helps somewhat,

Brent

Thanks, Brent! I did pre-load most of my separate images in the createScene function, but I suppose there may have been some that were added procedurally. I figured that there wasn’t much else I could do, but it’s an interesting question of organized code/app structuring vs. app performance. I’ll probably stick with the image sheets and add some loading notifiers.

Thanks again!

I’ve noticed that on some Android devices loading large images can be really slow.  Apple devices seem much better able to handle massive textures.  I’m wondering if Corona is perhaps doing some auto image scaling on large textures when loading them on Android.  What devices/OS are you noticing the slow performance?  

One thing you could try is to move the 2 or 3 biggest images off the sheet into separate pngs.  That way you would still have most of the benefits of the sheet for the rest of the images, and perhaps, since the resulting sheet would be smaller, you might gain back the scene loading performance you once had.    

@HardBoiled: Oddly enough, the slow-down is happening on an iPad 3, which should be pretty capable of handling even large textures. My iPhone 5 is noticeably speedier, though. I haven’t tried it on Android yet - waiting to nail down my iOS implementation before tweaking it for Android. Sounds like I will definitely need a loading indicator for Android, based on what you say.

You might be onto something with the breaking out of the larger images (I do have at least one background image on most of the sheets). I’ll give it a try. Thanks again!

Is it possible to load textures on a separate thread?  When I worked with OpenGL directly prior to my dive into Corona, it was a huge pain to make work, but could be done using an EAGLShareGroup.  

Hi Jason,

Using the separate images method, did you previously load all of them when the scene entered? Or did you load some of them over time, when needed? This might explain why it’s occurring… if you previously loaded a few images here, a few images there, then it makes sense that the app would “load” faster, despite having higher texture memory usage because of the un-sheeted images. With the image sheet, you’ll save texture memory, but the scene will need to load the entire thing before it can proceed… just the nature of image sheets.

Hope this helps somewhat,

Brent

Thanks, Brent! I did pre-load most of my separate images in the createScene function, but I suppose there may have been some that were added procedurally. I figured that there wasn’t much else I could do, but it’s an interesting question of organized code/app structuring vs. app performance. I’ll probably stick with the image sheets and add some loading notifiers.

Thanks again!

I’ve noticed that on some Android devices loading large images can be really slow.  Apple devices seem much better able to handle massive textures.  I’m wondering if Corona is perhaps doing some auto image scaling on large textures when loading them on Android.  What devices/OS are you noticing the slow performance?  

One thing you could try is to move the 2 or 3 biggest images off the sheet into separate pngs.  That way you would still have most of the benefits of the sheet for the rest of the images, and perhaps, since the resulting sheet would be smaller, you might gain back the scene loading performance you once had.    

@HardBoiled: Oddly enough, the slow-down is happening on an iPad 3, which should be pretty capable of handling even large textures. My iPhone 5 is noticeably speedier, though. I haven’t tried it on Android yet - waiting to nail down my iOS implementation before tweaking it for Android. Sounds like I will definitely need a loading indicator for Android, based on what you say.

You might be onto something with the breaking out of the larger images (I do have at least one background image on most of the sheets). I’ll give it a try. Thanks again!

Is it possible to load textures on a separate thread?  When I worked with OpenGL directly prior to my dive into Corona, it was a huge pain to make work, but could be done using an EAGLShareGroup.