Databinding/PropertyChanged Notification on object reassignement (Silverlight 4/C#)
I have a textblock bound to an object. The 2-way binding works well and as expected.
In the code-behind:
txtNumberOfPlayers.DataContext = tournament.ChipSet;
In the .xaml:
<toolkit:NumericUpDown x:Name="txtNumberOfPlayers" Value="{Binding NumberOfPlayers, Mode=TwoWay, NotifyOnValidationError=true, ValidatesOnExceptions=true}" />
In the Chipset class I raise a change notification when the NumberOfPlayers is set (OnPropertyChanged("NumberOfPlayers");)
But... when I completely reassign the object it does not update the UI unless I call the datacontext assignment again. For example, lets say I load a different chipset object.
Chipset newChipSet = LoadChipset();
tournament.ChipSet = newChipSet;
This does not update the txtNumberOfPlayers when the assignement is made. It only works if I do this:
Chipset newChipSet = LoadChipset();
tournament.ChipSet = newChipSet;
//have to call this again which seems redundant
txtNumberOfPlayers.DataContext = tournament.ChipSet;
So I thought, maybe I have to put the change notification on the Chipset object like this:
private Chipset chipset;
public Chipset ChipSet
{
get { return chipset; }
set
{
if (chipset != value)
{
chipset = value;
OnPropertyChanged("ChipSet");
}
}
}
but that does not work.
So my questions is - how do I get the UI to update when I assign a开发者_如何学Go new object to the old one without rebinding the datacontext.
Thanks!
You should specify RelativeSource to your Binding:
Value={Binding NumberOfPlayers, Mode=TwoWay, NotifyOnValidationError=true, ValidatesOnExceptions=true, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type YourNamespace:YourTypeContainingChipsetProperty}}}
EDIT
Example of DependencyProperty in your case. Change YourCustomControl to class name of your control:
public static DependencyProperty ChipsetProperty =
DependencyProperty.Register("Chipset", typeof(Chipset),
typeof(YourCustomControl),
new FrameworkPropertyMetadata
(null,
FrameworkPropertyMetadataOptions
.
BindsTwoWayByDefault, ChipsetPropertyChangedCallback));
public Chipset Chipset
{
get { return (Chipset)GetValue(ChipsetProperty); }
set { SetValue(ChipsetProperty, value); }
}
private static void ChipsetPropertyChangedCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var yourCustomControl = d as YourCustomControl;
if (yourCustomControl != null)
{
//your logic on property changed goes here; don't raise OnPropertyChanged!
}
}
精彩评论