Question

I'm trying to do a Data Binding in the C# code behind rather than the XAML. The XAML binding created in Expression Blend 2 to my CLR object works fine. My C# implementation only updates when the application is started after which subsequent changes to the CLR doesn't update my label content.

Here's the working XAML binding. First a ObjectDataProvider is made in my Window.Resources.

<ObjectDataProvider x:Key="PhoneServiceDS" 
    ObjectType="{x:Type kudu:PhoneService}" d:IsDataSource="True"/>

And the label content binding:

<Label x:Name="DisplayName" Content="{Binding 
    Path=MyAccountService.Accounts[0].DisplayName, Mode=OneWay, 
    Source={StaticResource PhoneServiceDS}}"/>

Works great. But we want this set up in C# so we can independently change the XAML (ie. new skins). My one time working C# as follows:

     Binding displayNameBinding = new Binding();
     displayNameBinding.Source = 
         PhoneService.MyAccountService.Accounts[0].DisplayName;
     displayNameBinding.Mode = BindingMode.OneWay;
     this.DisplayName.SetBinding(Label.ContentProperty, displayNameBinding);

This is inside my MainWindow after InitializeComponent();

Any insight why this only works on startup?

Was it helpful?

Solution

Your C# version does not match the XAML version. It should be possible to write a code version of your markup, though I am not familiar with ObjectDataProvider.

Try something like this:

Binding displayNameBinding = new Binding( "MyAccountService.Accounts[0].DisplayName" );
displayNameBinding.Source = new ObjectDataProvider { ObjectType = typeof(PhoneService), IsDataSource = true };
displayNameBinding.Mode = BindingMode.OneWay;
this.DisplayName.SetBinding(Label.ContentProperty, displayNameBinding);

OTHER TIPS

In the priginal code you have confused the source and path.

     Binding displayNameBinding = new Binding();
     displayNameBinding.Source = PhoneService;
     displayNameBinding.Path = "MyAccountService.Accounts[0].DisplayName";
     displayNameBinding.Mode = BindingMode.OneWay;
     this.DisplayName.SetBinding(Label.ContentProperty, displayNameBinding);

(I assume PhoneService is an object instance, otherwise perhaps PhoneService. MyAccountService.Accounts[0] should be the Source?)

From memory, you can pass the path as an argument to the constructor.

Write this inside Loaded event instead of Constructor. Hope you implmented INotifyPropertyChanged triggered on the DisplayName property setter?

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top