2014-09-26 22 views
0

在設計時,我的控件應該公開數據源中可用的所有字段。例如,考慮數據源的下列結構在CurrencyManager中獲取數據源的屬性

List<Data> dataSource = new List<Data>() 
dataSource.add(new Data(){ Value = 1, Rect = new Rectangle(10, 10, 10, 10)}) 

我想將控制結合在如矩形的"Left"屬性的數據源的內部屬性。我用下面的代碼來實現這一點

var prop = this.BindingContext[dataSource]; 
ArrayList result = (ArrayList)GetPropertiesList(prop.Current, string.Empty); 

爲GetPropertiesList方法的代碼是下面

private IList GetPropertiesList(object source, string parent) 
     { 
      ArrayList result = new ArrayList(); 
      ArrayList innerProperties = new ArrayList(); 
      Type sourceType = source.GetType(); 
      PropertyInfo[] propertyInfo = sourceType.GetProperties(); 
      if (parent != string.Empty) 
       parent += "."; 
      foreach (PropertyInfo info in propertyInfo) 
      {     
       object value = info.GetValue(source, null);        
       if(value == null) 
        result.Add(parent + info.Name); 
       else if (value is string || value is DateTime || value.GetType().IsPrimitive) 
        result.Add(parent + info.Name); 
       else 
        innerProperties = (ArrayList)(GetPropertiesList(value, parent + info.Name)); 
      } 
      if(innerProperties.Count > 0) 
       result.AddRange(innerProperties); 
      return result; 
     } 

當在列表對象(dataSource)沒有添加的數據此代碼失敗。

請分享你的想法和意見

回答

0

我不想回答我的問題,但我認爲它可以幫助別人。

經過幾個小時的搜索,我發現使用屬性描述符我們可以獲得屬性名稱,類型,值,子屬性等,所以我只是修改了一些問題。

解決方案中的代碼將填充數據源中所有可用的基元,字符串和日期時間屬性(包括數據源中對象的基元,字符串和日期時間屬性)。所以使用這個我可以在我的設計器中顯示內部屬性。

在我的問題的數據源將在設計者如下:

Value 
Rect.Left 
Rect.Top 
Rect.Width 
Rect.Height 
...... 

解決方案:

PropertyDescriptorCollection members = dataSourceObject.GetItemProperties(); 
result = (ArrayList)GetPropertiesList(members, string.Empty); 

結果將在數組列表中的所有屬性。通過數組列表循環,我可以爲各個屬性獲得名稱功能GetPropertiesList

代碼:

private IList GetPropertiesList(PropertyDescriptorCollection collection, string parent) 
     { 
      ArrayList result = new ArrayList(); 
      if (parent != string.Empty) 
       parent += '.'; 
      foreach (PropertyDescriptor property in collection) 
      { 
       if (property.PropertyType == typeof(string) || property.PropertyType == typeof(DateTime) || property.PropertyType.IsPrimitive) 
        result.Add(parent + property.Name); 
       else 
       { 
        result.AddRange((ArrayList)GetPropertiesList(property.GetChildProperties(), parent+ property.Name)); 
       } 
      } 
      return result; 
     } 

注:

我只張貼代碼來顯示所有可用字段在數據源中。將字段綁定到控件的代碼是不同的。因爲,這與我不在這裏發佈的問題無關。