2014-04-09 63 views
1

我在Windows窗體中試驗數據綁定,發現一個我無法解釋的小故障。我在這裏發佈這個問題,希望社區中的某個人能夠拿出一個合理的答案。Windows窗體上的數據綁定屬性時發生故障

我試圖想出的結合依賴於操作其它值只讀值一個聰明的辦法,並自動更新它時,相關值的變化。

我創建了一個表格3個文本框,我想要的前2的總和出現在第三文本框。

下面的代碼應該工作,但沒有,至少不正確:

public class Model : INotifyPropertyChanged 
{ 
    private int m_valueA; 
    private int m_valueB; 

    public int ValueA 
    { 
     get { return m_valueA; } 
     set { m_valueA = value; RaisePropertyChanged("ValueA"); } 
    } 

    public int ValueB 
    { 
     get { return m_valueB; } 
     set { m_valueB = value; RaisePropertyChanged("ValueB"); } 
    } 

    public event PropertyChangedEventHandler PropertyChanged; 

    private void RaisePropertyChanged(string propertyName) 
    { 
     var handler = PropertyChanged; 
     if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName)); 
    } 
} 

public class DynamicBindingProperty<T> : INotifyPropertyChanged 
{ 
    private Func<T> m_function; 
    private HashSet<string> m_properties; 

    public DynamicBindingProperty(Func<T> function, INotifyPropertyChanged container, IEnumerable<string> properties) 
    { 
     m_function = function; 
     m_properties = new HashSet<string>(properties); 
     container.PropertyChanged += DynamicBindingProperty_PropertyChanged; 
    } 

    public T Property { get { return m_function(); } } 

    void DynamicBindingProperty_PropertyChanged(object sender, PropertyChangedEventArgs e) 
    { 
     if (!m_properties.Contains(e.PropertyName)) return; 
     if (PropertyChanged == null) return; 
     PropertyChanged(this, new PropertyChangedEventArgs("Property")); 
    } 

    public event PropertyChangedEventHandler PropertyChanged; 
} 

public partial class Form1 : Form 
{ 
    public Form1() 
    { 
     InitializeComponent(); 
     InitializeDataBinding(); 
    } 

    private void InitializeDataBinding() 
    { 
     Model model = new Model(); 
     DynamicBindingProperty<int> tmp = new DynamicBindingProperty<int>(() => model.ValueA + model.ValueB, model, new[] {"ValueA", "ValueB"}); 

     textBox1.DataBindings.Add("Text", model, "ValueA"); 
     textBox2.DataBindings.Add("Text", model, "ValueB"); 
     textBox3.DataBindings.Add("Text", tmp, "Property"); 

     tmp.PropertyChanged += (sender, args) => Console.WriteLine(args.PropertyName); 
    } 
} 

經歷過了一段時間後,我試圖重新命名DynamicBindingProperty <牛逼> .Property到別的東西(如DynamicProperty)和一切都按預期工作!。現在,我期待通過將Model.ValueA重命名爲Property來破解某些內容,但它沒有,並且仍然無懈可擊。

這是怎麼回事?

回答

2

我做了一些調試,它看起來像一個bug(或要求「的屬性不能被命名爲房產」我不知道)。如果您有

PropertyChanged(this, new PropertyChangedEventArgs(null)); 

更換

PropertyChanged(this, new PropertyChangedEventArgs("Property")); 

它仍然無法正常工作 - null或空字符串是指任何財產可能已經改變。這表明問題不在於處理更改通知,而是綁定尚未正確建立。

如果添加第二個屬性Property2DynamicBindingProperty<T>,做同樣的Property並將其綁定到第四個文本框,然後文本框將得到正確更新,如果你有一個空字符串進行變更通知,null"Property2"。如果您有"Property"執行變更通知雙方文本框將得到正確更新。這表明綁定到Property並未完全中斷,並且更改通知有些中斷。

可悲的是我無法牽制確切位置不如意的事情,但如果你投入足夠的時間,通過優化框架源代碼步進你或許可以找到答案。與屬性名Property2與屬性名Property的情況下與外殼之間的差別最早處理更改通知時,我能確定是OnValueChanged()內部類System.ComponentModel.ReflectPropertyDescriptor。在一種情況下,基礎實現在另一種情況下被跳過時調用 - 至少如果調試器不欺騙我,但在優化代碼中很難說明。

相關問題