2

We are working on a windows phone 8 application (chat application). In the app, we need to show the images of the contacts on several pages. We are binding the ImageUri to the image source and using a converter to return a BitmapImage.

    BitmapImage image = new BitmapImage();

        try
        {
            var path = (Uri)value;

            if (!String.IsNullOrEmpty(path.ToString()))
            {
                using (var stream = LoadFile(path.ToString()))
                {
                    if (stream != null)
                    {
                        image.SetSource(stream);
                    }
                    else
                    {
                        image = new BitmapImage();

                        image.UriSource = (Uri)value;
                    }
                }
                return image;

            }
        }

In the LoadFile(), we search for the file in IsolatedStorage.

     private Stream LoadFile(string file)
    {
        Stream stream=null;

        using (var isoStore = IsolatedStorageFile.GetUserStoreForApplication())
        {
            if(isoStore.FileExists(file))
            stream = isoStore.OpenFile(file, System.IO.FileMode.Open, System.IO.FileAccess.Read);

        }

        return stream;
    }  

But when opening and closing some pages in the app it suddenly exists. We are not able to get a stack trace even when I run it in debug mode. I am just getting single line saying "A first chance exception of type System.OutOfMemoryException occurred". I searched on web to solve this and found some solutions. All of them are saying that loading so many bitmaps will cause this exception and I need to dispose it every time I stop using the resource. I wrote a behavior for my image control,

     void AssociatedObject_Unloaded(object sender, System.Windows.RoutedEventArgs e)
    {
        var image = sender as Image;

        if (image != null)
        {
            BitmapImage bitmapImage = image.Source as BitmapImage;

            bitmapImage.UriSource = null;

            using (var stream = LoadFile("Images/onebyone.png"))
            {
                if (stream != null)
                {
                    bitmapImage.SetSource(stream);
                }
            }
        }
    }

In the LoadFile(), method here, I am reading a 1x1 pixel image. Even after doing this I am still getting the same exception. How can I solve this? (Apart from loading too many controls will any other code cause OutOfMemoryException. If so, how can I know where exactly is my program causing this exception)

Typist
  • 1,464
  • 9
  • 14
Raj123
  • 971
  • 2
  • 12
  • 24

1 Answers1

1

If, on a single page, you are showing too many images, it will definitely consume significant amount of memory - proportionate to your image sizes.

May be change the way, you are doing it. Try to see if you can use Lazy loading with your list control and cleanup the resources when they go out of the view port.

Do memory profiling to see who is going out of band.

Update

This SO question should be helpful too.

Community
  • 1
  • 1
Typist
  • 1,464
  • 9
  • 14
  • I understand I have to cleanup the resources when I stop using them. My question is how to do it? Why is the behavior I wrote in the question not doing it? – Raj123 Jun 19 '14 at 09:55
  • If `AssociatedObject_Unloaded` is supposed to cleanup, why are you setting source of `bitmapImage` again? – Typist Jun 19 '14 at 09:57
  • Because I read on a accepted answer on stack overflow that this will solve my problem. BTW I don't know if AssociatedObject_Unloaded is supposed to cleanup the resource. – Raj123 Jun 19 '14 at 09:59