When I resume my app, sometimes it loses its images. I can reproduce this even in trivial apps.
This manifests in two different ways, depending on where the image came from:
- If I did something like
<Image Source="/Assets/Logo.png"/>
(i.e., loading an image from my app package by URI), the image will disappear briefly, and then reload. This is easier to see when the screen contains many images; they reload in sequence, so I can watch the image loading ripple across the screen. - If I created a
WriteableBitmap
and bound it to Image.Source, then the bitmap disappears entirely, never to return.
I could probably live with this if it was just reloading images (though the ripple effect is unpleasant), but I do quite a bit of dynamic image generation, and it's not cool for all my WriteableBitmaps to disappear.
This doesn't happen every time the app suspends and resumes, only sometimes. I haven't nailed down a reliable repro case, but it seems that the longer it's suspended, and the more other things I'm doing in the interim (surfing the web in desktop Chrome, playing fullscreen DirectX games like TapTiles and Microsoft Minesweeper), the more likely it is that, when I switch back to my app, the images will be lost. (The app is not getting terminated and re-launched -- it's still the same app instance.)
I wonder if it's something to do with images getting flushed from video memory. But I have no idea how to test this hypothesis, so at this point it's just a guess.
So far, I haven't found any way for my program to even tell that WriteableBitmaps are being lost. The sequence of events is identical to a normal suspend and resume:
- Window.Current.Activated fires with args.WindowActivationState == Deactivated
- Window.Current.VisibilityChanged fires with args.Visible == false
- Application.Suspending fires
- (time passes)
- Application.Resuming fires
- Window.Current.VisibilityChanged fires with args.Visible == true
- Window.Current.Activated fires with args.WindowActivationState == CodeActivated
I haven't had any luck finding an "and by the way, all your images went away" event. WriteableBitmap has no events. Image has ImageOpened and ImageFailed events, but those only fire when I load an image from a URI -- they never fire when Source is a WriteableBitmap.
I've been able to reproduce this in trivial apps, so it's not caused by some third-party library. A blank page with an Image loaded by URI will fire ImageOpened again (and the image will flicker briefly before it finishes reloading) if the app has been suspended for a while and then you resume it. A blank page with an image initialized to a WriteableBitmap will disappear if the app has been suspended for a while and then you resume it.
How can I fix the loss of WriteableBitmaps (and, if possible, content-URI images too)? Is there any way that I can prevent the images from getting lost in the first place? If not, is there any way I can detect that they've been lost, so I can re-create my WriteableBitmaps?
(For bonus points, I'd love to know why the images disappear, but that part is entirely optional. I've long since given up on expecting WinRT to make sense.)