Windows Phone - Panorama搭配Binding無法補捉SelectionChanged事件
這篇文章真是個筆記阿,因為實作Panorama時我第一次遇到它搭配Binding之後,竟然無法補捉SelectionChanged事件。
根據相關的網路文獻<Windows Phone 8 Panorama SelectionChanged & Databinding>指出:
a. 這是Windows Phone 8 Panorama已知databinding的bug;
b. 需要將原有的DataSource重新利用new ObservableCollection<object>()來重建;
c. 既有的Model需要增加override Equals的方法做為轉換的識別值;
搭配一個簡單的例子說明:
今天實作了一個Model:image,需要藉由Panorama來顯示每張圖片,並標示目前有幾頁,例如:2/4的效果。
根據<Windows Phone 8 Panorama SelectionChanged & Databinding>的介紹,便來實作三個重點事件:
1. 先增加Model去override Equals的關鍵事件,如下:
public class image : INotifyPropertyChanged
{
public string imageId { get; set; }
private string gurl = string.Empty;
public string url
{
get { return gurl; }
set { gurl = value; }
}
public string imageDesc { get; set; }
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void OnPropertyChanged([CallerMemberName] string pPropertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(pPropertyName));
}
}
#region 實作當PanoramaItem搭配Data Binding時無法觸發SelectionChanged的事件
public override bool Equals(object obj)
{
if ((obj != null) && (obj.GetType() == typeof(PanoramaItem)))
{
var thePanoItem = (PanoramaItem)obj;
return base.Equals(thePanoItem.Header);
}
else
{
return base.Equals(obj);
}
}
public override int GetHashCode()
{
return base.GetHashCode();
}
#endregion
}
主要增加如下重點部分,為了就是在物件識別時可以知道目前被Binding上去的物件是否為PanoramaItem並加以識別:
#region 實作當PanoramaItem搭配Data Binding時無法觸發SelectionChanged的事件
public override bool Equals(object obj)
{
if ((obj != null) && (obj.GetType() == typeof(PanoramaItem)))
{
var thePanoItem = (PanoramaItem)obj;
return base.Equals(thePanoItem.Header);
}
else
{
return base.Equals(obj);
}
}
public override int GetHashCode()
{
return base.GetHashCode();
}
#endregion
2. 重新為DataBinding的DataContext給予new ObservableCollection<Cow>()的建立方式,如下:
private void UserControl_Loaded(object sender, RoutedEventArgs e)
{
//重新建立DataContext的物件結構,改由object取得原有的image
var tNewSources = new ObservableCollection<object>();
foreach (image tImg in ((imageSet)this.DataContext).ImgSources)
{
tNewSources.Add(tImg);
}
//重新給值
pn1.ItemsSource = tNewSources;
}
只要做二件事即能讓Panorama搭配DataBinding後正常觸發SelectionChanged的事件。真的非常奇妙。
======
我只能說這個問題真是個奇皅了。除非您真的寫到Panorama與Data Binding同時使用,不然真的不會注意到這個問題。
做個記錄,希望對大家有所幫助。謝謝。
References:
‧Windows Phone 8 Panorama SelectionChanged & Databinding
‧SelectionChanged Event for ListBox in panorama.ItemTemplate for Windows Phone?
‧WP8 Panorama with binding SelectionChanged doesnt fired. Bug?
‧[语法问题] panorama.ItemTemplate的SelectionChanged事件
‧Windows Phone 8全景的SelectionChanged和数据绑定