Windows Phone性能優化建議

  • 使用background thread解碼圖片

     在Windows Phone中支持的圖片格式有jpg和png,微軟建議使用jpg格式的圖片,由於jpg格式的圖片在解碼速度上要比png快。那麼咱們怎麼來控制用後臺線程來解碼圖片呢?看下面的代碼。html

<Image Height="100" Width="100" Margin="12,0,9,0">
  <Image.Source>
    <BitmapImage UriSource="{Binding ImgURL}" CreateOptions="BackgroundCreation"/>
  </Image.Source>
</Image>
var bi = new BitmapImage();
bi.CreateOptions = BitmapCreateOptions.BackgroundCreation;

     這兩段代碼都設置了BitmapImage的CreateOptions屬性,這樣作避免了在UI線程來對圖片解碼,在使用過程當中BackgroundCreation確實有效地提升了頁面的響應效率,尤爲是在圖片密集型的頁面。須要注意的是,圖片位置可能出現短暫的空白,不過這段時間咱們能夠經過一個圖片佔位符的方法來處理。CreateOptions屬性包括有四種:編程

  1. None                           不對CreateOptions作任何設置。
  2. DelayCreation             是BitmapImage的默認屬性,在必要時建立圖片。
  3. IgnoreImageCache      圖片將不啓用緩存,適合於頻繁須要更新的圖片。
  4. BackgroundCreation    圖片的解碼在後臺線程完成。
  • 減小沒必要要的PropertyChanged事件的觸發

     在MVVM模式的開發中,經過設置INotifyPropertyChanged接口使View做爲一個觀察者,可使咱們方便的經過DataBinding更新UI內容,這裏咱們要說的其實PropertyChanged事件是一個冗長的方法。若是你使用的是VS2012或更高的版本使用工具欄的Code Map按鈕能夠看到系統監聽的add_PropertyChanged事件,並且它在UI線程上執行。爲了減小沒必要要的PropertyChanged事件的觸發,咱們能夠採用下面這種方法來對value的值提早作出判斷。緩存

public string Text
{
    get { return _text;}
    set
        {
           if( _text == value) return;
           _text = value;
           RaisePropertyChanged("Text");
         }
}
  • 減小Databinding中Converter的使用

     在Databinding中咱們能夠建立一個繼承自IValueConverter的類實現Convert方法來對綁定的值作進一步處理,這個處理會直接影響到綁定的速度,並且這個轉換是在UI線程執行的,若是咱們把一個很重的方法放在了這個Converter裏,那綁定的速度就可想而知了。總之,對後臺數據的處理仍是在後臺線程中準備好以後在通知UI更新,儘可能避免由於Converter形成的UI阻塞。異步

  • 開啓集合控件的虛擬化

     在以前的一篇博客中咱們介紹了在Windows Phone中集合控件的使用VirtualizingStackPanel是一個重要的概念,在ListBox中默認的Itmes的容器就是VirtualizingStackPanel,這個容器是虛擬化的,不一樣於StackPanel。它只建立了大約屏幕可見的數量,而非將ListBox中的Items一次所有建立,隨着上下滾動再次建立剩下爲顯示在屏幕上的內容。這樣就大大節省了頁面首次渲染的時間。異步編程

     VirtualizingStackPanel還有一個比較重要的屬性,就是VirtualizationMode。這個屬性有兩個值。工具

  1. Standard 每次都會爲容器的Item建立新的VirtualizingStackPanel,並回收以前建立的容器。
  2. Recycling 重用以前建立的VirtualizingStackPanel

     顯然咱們開啓VirtualizingStackPanel的Recycling模式來重用容器,避免新的容器的建立。下面是一個ListBox的示例代碼。佈局

<ListBox ItemsSource="{StaticResource data}" 
         VirtualizingStackPanel.IsVirtualizing="True"
         VirtualizingStackPanel.VirtualizationMode="Recycling" />
  • 動態加載PivotItem

     在Windows Phone開發中軸心控件Pivot絕對是一個佈局很好的選擇。可是若是咱們的頁面的PivotItem比較多,會直接影響到咱們頁面的渲染時間,尤爲是在首頁的時候,等待的時間可能會更加長。這時候咱們能夠考慮動態的加載PivotItem的方法來減輕首次加載頁面的時間,咱們只須要在頁面定義空的PivotItem,再在OnLoadingPivotItem的事件中動態的建立UserControl並加入到相應的PivotItem的Content中便可。spa

<controls:Pivot x:Name="pivot" OnLoadingPivotItem="OnLoading">
          <controls:PivotItem x:Name="firstItem"/>
</controls:Pivot>                
public void OnLoading(PivotItem item)
{
    if(item.Content == null)
      {
           var userControl = new CustemControl();
           item.Content = userControl;
      }
}
  • 爲ObservableCollection添加AddRange方法

     ObservableCollection絕對是數據綁定過程當中重要的集合,使用這個集合能夠經過Add方法方便的更新集合。但當數據量大的狀況下咱們是否能夠考慮自定義一個AddRange方法,來替換掉每次Add的時候觸發的NotifyCollectionChangedAction.Add類型的事件。而改用NotifyCollectionChangedAction.Reset使整個頁面只刷新一次。那麼就來看看這個擴展類的寫法。線程

public class ObservableCollectionEx<T> : ObservableCollection<T>
{
    public void AddRange(IEnumerable<T> list)
    {
        foreach (T item in list)
        {
            Items.Add(item);
        }
        OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));
        OnPropertyChanged(「Count」);
    }
}
  • 使用Async、await、Task<TResult>異步編程
相關文章
相關標籤/搜索