如何在Windows Phone 8 App的数据模板中释放图像的内存?

时间:2013-07-10 13:24:44

标签: windows-phone-8

我有一个longlistselector,我有一个数据模板,用于定义要添加到列表中的项目类型。数据模板具有Image控件,其源与动态路径绑定,因此列表中的每个项都具有关联的图像控件。我面临的问题是这些Image控件永远不会释放它们占用的内存,从而导致内存不足异常。在正常情况下我设置bitmapImage.UriSource = null来释放与位图关联的内存但是在这种情况下找不到这样做的方法。以下是longlistselector的xaml代码以及与之关联的数据模板..

数据模板

<phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Key="MediaItemTemplate">      
        <Canvas VerticalAlignment="Top">
            <Border BorderBrush="#FF4791CA" BorderThickness="3">
                <Image Height="100" Width="100" VerticalAlignment="Top" Grid.RowSpan="2" Stretch="UniformToFill">
                    <Image.Source> 
                          <BitmapImage UriSource="{Binding path}" CreateOptions="BackgroundCreation"  DecodePixelHeight="50" DecodePixelWidth="50"/>
                    </Image.Source>
                </Image>
             </Border>
             <Image Source="/Icons/check.png" Height="16" Width="16" Grid.Row="0" Grid.Column="0" VerticalAlignment="Top" Margin="80,7,7,0" Canvas.ZIndex="100" OpacityMask="Black" Visibility="{Binding visibility}" Name="checkImage" >    
             </Image>
          </Canvas> 
      </DataTemplate>
</phone:PhoneApplicationPage.Resources>

LonglistSelector

<phone:LongListSelector 
            Tap="ListMedia_Tap"
            x:Name="ListMedia"
            HorizontalAlignment="Left"
            Height="624" 
            VerticalAlignment="Top"
            Width="436"

背景= “透明”

ItemTemplate =“{StaticResource MediaItemTemplate}”   LayoutMode =“Grid”GridCellSize =“120,120”/&gt;

我对Windows手机编程很新,基本上我想做的是开发一种图像浏览器体验。请帮我解决释放内存的方法。如果我完全错误,请纠正我或建议更好的方法来实现相同的功能。 Thanx提前...

3 个答案:

答案 0 :(得分:2)

我发现处理这种情况的解决方案是制作一个自定义控件来自动将urisource设置为null:

public class SafePicture : System.Windows.Controls.ContentControl
{
    public SafePicture()
    {
        this.Unloaded += this.SafePictureUnloaded;
    }

    private void SafePictureUnloaded(object sender, System.Windows.RoutedEventArgs e)
    {
        var image = this.Content as System.Windows.Controls.Image;

        if (image != null)
        {
            image.Source = null;
        }
    }
}

然后,只需将所有照片包裹在该控件中:

<my:SafePicture>
    <Image Source="{Binding Path=path}" />
</my:SafePicture>

答案 1 :(得分:0)

默认情况下,Windows Phone会将从Uri下载的邮件存储在内存中,以免再次加载它们。 (这是一种粗略的缓存形式。)

要释放这些图像使用的内存,您需要明确释放对它们的所有引用。有关详细信息,请参阅MSDN: Image Tips for Windows Phone 7

答案 2 :(得分:0)

当您使用代码滚动(不使用已加载)时,图像会在向下滚动并返回列表顶部后丢失(速度无论如何)。使用Loaded时,滚动的wokrs可以:可以向下滚动并返回到顶部(调试器显示已调用Unloaded和Loaded),并且图像在那里。但是,当移动到另一个页面(我有主要细节页面)时,它们会混淆。