Items loaded from memory block UI

9 posts, 1 answers
  1. Jandieg
    Jandieg avatar
    43 posts
    Member since:
    Feb 2012

    Posted 01 Mar 2012 Link to this post

    Hi,
    When loading a SlideView with images from streams it seems to block the UI and feels slow.

    I tried to improve it by doing:

    Picture pic;
    BitmapSource delayed;
    public ImageSource image
    {
        get
        {
            if (delayed == null)
            {
                System.Threading.ThreadPool.QueueUserWorkItem((d) =>
                {
                    Deployment.Current.Dispatcher.BeginInvoke(() =>
                    {
                        BitmapSource img = new BitmapImage();
                        img.SetSource(pic.getStream());
                        delayed = new WriteableBitmap(img);
                        NotifyPropertyChanged("image");
                    });
                });
            }
            return delayed == null ? new WriteableBitmap(100, 100) : delayed;
        }
    }


    It works a little smoother but causes an out of memory exception after some swiping.

    How to address this?
  2. Answer
    Todor
    Admin
    Todor avatar
    778 posts

    Posted 06 Mar 2012 Link to this post

    Hello Jandieg,

    Thank you for your question.

    The conversion to WriteableBitmap adds a lot of loading time, so you'd better skip it as it is not required. You can improve it by setting delayed directly to img, instead of new WriteableBitmap(img).

    Regarding your second question about the OutOfMemoryException, your application is allowed to use a specific amount of memory, so when you use big images it is normal that you will eventually run out of memory. My suggestion here is that you use a WeakReference, which allows referencing an object while still allowing that object to be reclaimed by garbage collection. Here is your image property after removing the WriteableBitmap and adding a WeakReference:
    private WeakReference delayed;
    public ImageSource image
    {
        get
        {
            if (delayed == null)
            {
                System.Threading.ThreadPool.QueueUserWorkItem((d) =>
                {
                    Deployment.Current.Dispatcher.BeginInvoke(() =>
                    {
                        try
                        {
                            BitmapImage img = new BitmapImage();
                            img.SetSource(Picture.GetImage());
     
                            delayed = new WeakReference(img);
                            NotifyPropertyChanged("image");
                        }
                        catch { }
                    });
                });
            }
            if(delayed == null)
            {
                return null;
            }
            return !delayed.IsAlive ? null : delayed.Target as ImageSource;
        }
    }

    You can try with your collection of images and let me know if the issue persists.

    Greetings,
    Todor
    the Telerik team
    Sharpen your .NET Ninja skills! Attend Q1 webinar week and get a chance to win a license! Book your seat now >>
  3. DevCraft banner
  4. Jandieg
    Jandieg avatar
    43 posts
    Member since:
    Feb 2012

    Posted 06 Mar 2012 Link to this post

    Thanks Todor. You rock!
  5. Todor
    Admin
    Todor avatar
    778 posts

    Posted 07 Mar 2012 Link to this post

    Hello Jandieg,

    I'm glad the solution helped. However, I realize now that you should probably add one additional check in the first if:
    if (delayed == null || !delayed.IsAlive)


    This would ensure that if the weak reference's target has been garbage-collected, it will be recreated.
    Regards,
    Todor
    the Telerik team
    Sharpen your .NET Ninja skills! Attend Q1 webinar week and get a chance to win a license! Book your seat now >>
  6. Jandieg
    Jandieg avatar
    43 posts
    Member since:
    Feb 2012

    Posted 07 Mar 2012 Link to this post

    Correct, something was causing some images to show blank after sliding a while...
  7. Todor
    Admin
    Todor avatar
    778 posts

    Posted 07 Mar 2012 Link to this post

    Hi,

    After sliding a while some of the objects are removed by the garbage collector, but the WeakReference instances that point to them are not. This means that after a while, you will run into the case when delayed is not null and delayed.IsAlive is false. In that case you need to create the image object again and by adding the additional check in the first if, we cover this scenario as well. If you want some more information about the WeakReferences, you can read this.

    If you notice another strange behavior, don't hesitate to write us back.

    Greetings,
    Todor
    the Telerik team
    Sharpen your .NET Ninja skills! Attend Q1 webinar week and get a chance to win a license! Book your seat now >>
  8. Jandieg
    Jandieg avatar
    43 posts
    Member since:
    Feb 2012

    Posted 07 Mar 2012 Link to this post

    Thanks. Since in this case the slideview is loading heavy images from storage, would removing the busy indicator help improve performance?
    If so, how to completely disable the busy animation?
  9. Todor
    Admin
    Todor avatar
    778 posts

    Posted 08 Mar 2012 Link to this post

    Hello Jandieg,

    Because of the virtualization in RadSlideView, you only have three instances of the BusyIndicator - one for the current, one for the next and one for the previous item, so disabling it would not make a dramatic change in the performance. Instead, it would have a negative impact on user experience, because if an image is not loaded the user would see a blank screen and they might wonder why. What the busy indicator does is it notifies the users that something is happening and they should wait for the image to load.

    I hope this information helps.

    Greetings,
    Todor
    the Telerik team
    Sharpen your .NET Ninja skills! Attend Q1 webinar week and get a chance to win a license! Book your seat now >>
  10. Jandieg
    Jandieg avatar
    43 posts
    Member since:
    Feb 2012

    Posted 08 Mar 2012 Link to this post

    Good. Thanks
Back to Top
DevCraft banner