2012-09-05 259 views
0

我有一個簡單的WPF複選框爲什麼我的屬性返回不是我設置的值?

<CheckBox Name="layerCheckBox" IsChecked="{Binding Path=IsSelected, Mode=TwoWay}" Grid.Column="0" /> 

,我結合我的自定義Layer類的的BindingList。

public BindingList<Layer> Layer 
    { 
     get { return _layer; } 
     set { _layer = value; } 
    } 

圖層類有一個屬性IsSelected。那就是我在我的複選框中使用的。正如你所看到的,我添加了一些輸出讀取和寫入屬性

public bool IsSelected 
{ 

get 
{ 
    System.Diagnostics.Debug.WriteLine("get"+_isSelected+this.GetHashCode()+ 
    "thread"+Thread.CurrentThread.ManagedThreadId); 
    return _isSelected; 
} 

set 
{ 
    System.Diagnostics.Debug.WriteLine("set" + value + this.GetHashCode() 
    + "thread" + Thread.CurrentThread.ManagedThreadId); 
    PropertyChanged.ChangeAndNotify(ref _isSelected, value,() => IsSelected); 
} 
} 

奇怪的是輸出。首先,我檢查複選框,並將該屬性設置爲true。之後我讀了房產,它說錯了?這是怎麼回事?它的同一個對象(哈希碼)和相同的線程...我不明白...而對於接下來的2個讀取,我猜想刷新,它是真的。最好的部分是 - 如果我取消選中該框,它將返回true。

屬性中的代碼是從這裏property notify

輸出

setTrue53182860thread1

getFalse53182860thread1

getTrue53182860thread1

getTrue53182860thread1

回答

2

可能的問題是ChangeAndNotify擴展方法。它會在提高屬性更改事件後設置您的字段的值。

當您提出事件時,所有訂閱者都會嘗試從該媒體資源中讀取。由於後臺字段尚未設置,它將返回原始值。

修復ChangeAndNotify擴展方法中的代碼,以便在引發屬性更改事件之前設置字段的值。

field = value; //<-- move to here 
if (vmExpression != null) 
{ 
    LambdaExpression lambda = Expression.Lambda(vmExpression); 
    Delegate vmFunc = lambda.Compile(); 
    object sender = vmFunc.DynamicInvoke(); 

    if(handler != null) 
    { 
     handler(sender, new PropertyChangedEventArgs(body.Member.Name)); 
    } 
} 

return true; 
+0

這是解決方案。我比其他答案更喜歡這個,因爲在這裏我只需要更改一行而不是很多客戶端代碼。謝謝 :) – steffan

2

在應用新值之前,您的set方法實際上會觸發'get'的調用。它這樣做是因爲在將它作爲函數參數傳遞給ChangeAndNotify的調用之前,它需要讀取IsSelected屬性。

我將其更改爲:

set { PropertyChanged.ChangeAndNotify(ref _isSelected, value,() => _isSelected); } 

(請注意,您不再調用傳遞作爲函數參數時,獲取屬性。)

相關問題