第六章 深入淺出話Binding 1、綁定的源可以是任意對象,並通過屬性公開自己的資料; 綁定的目標必須是依賴對象的相依性屬性。
2、INotifyPropertyChanged介面,當對象實現了這個介面的時候,當資料來源改變的時候可以通知UI同時實現改變, 實現原理:當為Binding設定了資料來源後,Binding會自動偵聽來自這個介面的事件。 public event PropertyChangedEventHandler PropertyChanged; protected void FirePropertyChanged(string propertyName) { if(PropertyChanged!=null) PropertyChanged(this,new PropertyChangedEventArgs(propertyName)); } 然後在屬性的Set訪問器重使用 set { if (_age != value) { _age = value; FirePropertyChanged("Age"); } } 3、相依性屬性:這類屬性的值可以通過Binding依賴在其他對象的屬性值上,被其他對象的屬性值所驅動。 4、綁定路徑(Path):需要綁定的值 (PropertyPath類型) bind.Path = new PropertyPath("Name");//設定資料繫結的路徑 還支援多級路徑:Text={Binding Path=Text.Length,ElementName=textBox1,Mode=OneWay} 5、繫結模式:OneTime(初始化時的綁定,後面不會再改變)、OneWay(資料來源改變UI改變,預設)TwoWay(雙向繫結) 6、資料來源(Source)的來源 a、普通CLR類型的單個對象:自訂的類或者.NET內建的類型; b、集合類型:數組、List<T>、ObservableCollection<T>等 c、ADO.NET資料對象:DataTable和DataView等(Win8和WP都不支援) d、使用XmlDataProvider把XML作為資料的來源(貌似win8不支援) e、依賴對象(既可以作為源有可以作為繫結目標) f、 把容器的DataContext指定為源:我們明知道從哪個屬性擷取資料,但是不知道具體把哪個對象作為Binding源。 g、ElementName作為資料來源:元素之間的綁定 h、使用Binding類的RelativeSource屬性:控制項內部綁定(支援本身但是不支援層級相對綁定) i、ObjectDataProvider對象指定為Source:當資料來源的資料不是通過屬性而是通過方法暴露給外界的時候。(貌似Win8不支援) k、把使用LINQ檢索得到的資料對象作為源。 7、轉換器IValueConverter Converter:從源到目標的轉換 ConverterBack:從目標到源的轉換 8、資料校正ValidationgRule 貌似win8和wp不支援,(如果有誰研究過,望回複一起研究下) 第七章 深入淺出話屬性 1、靜態欄位在記憶體中只有一個拷貝,非靜態欄位則是每一個執行個體擁有一個拷貝,但無論方法是靜態還是非靜態,在記憶體中只會有一份拷貝,區別只是你只能 通過類名或者執行個體名來訪問存放指令的記憶體 2、相依性屬性:一種可以自己沒有值,可以通過Binding從資料來源擷取得到值,擁有相依性屬性的對象稱為依賴對象, 節省執行個體對記憶體的開銷 屬性值通過Binding依賴在其他對象身上,既可以作為資料來源有可以作為資料繫結目標 3、相依性屬性對記憶體的使用方式:對象在建立的時候並不包含用於儲存資料的空間(即欄位所佔用的空間)、只保留在需要用到資料的時候能夠獲得預設值、借用 其他對象資料或即時分配空間的能力。 a、相依性屬性(DependencyProperty)必須以DependencyObject為宿主,通過它的SetValue和GetValue設定和擷取值, b、聲明必須以 public static readonly開頭 c、屬性成員變數的名字後面要加上Property,以表明他是一個相依性屬性 d、使用DependencyProperty.Register(string name, Type propertyType, Type ownerType, PropertyMetadata typeMetadata)建立而不是new, 第一個參數用來指明用哪個CLR屬性來作為這個相依性屬性的封裝器(封裝器以執行個體屬性暴露相依性屬性)。 第二個參數用來指明相依性屬性儲存什麼類型的值 第三個參數用來指明相依性屬性的宿主是什麼類型
//第一步:繼承DependencyObject class StudentDependency:DependencyObject { //第三步:使用CLR屬性作為相依性屬性的封裝器 public string Name { get { return (string)GetValue(NameProperty); } set { SetValue(NameProperty, value); } } //第二步:註冊相依性屬性 public static readonly DependencyProperty NameProperty = DependencyProperty.Register("Name", typeof(string), typeof(StudentDependency), new PropertyMetadata(null)); } 4、附加屬性:一個屬性本來不屬於某個對象,但是由於某種需求而被後來附加上,即把對象放入一個特定的環境後才具有的屬性。 作用就是將屬性與資料類型(宿主)解耦,讓資料類型設計更加靈活 本質還是相依性屬性,二者僅在封裝器和註冊上有點區別 //使用的是兩個方法對屬性進行賦值 public static int GetGrade(DependencyObject obj) { return (int)obj.GetValue(GradeProperty); } public static void SetGrade(DependencyObject obj, int value) { obj.SetValue(GradeProperty, value); } //使用的時RegisterAttached方法註冊 public static readonly DependencyProperty GradeProperty = DependencyProperty.RegisterAttached("Grade", typeof(int), typeof(SchoolAttachedProperty), new PropertyMetadata(0));