views:

877

answers:

1

I am using a DataRepeater to show data from a business objects on the screen. I am using windows forms in C# to accomplish this. The datasource is not available at compile time so I want to bind the datasource at runtime.

Here is the simplified scenario. I'm using this business class:

public class Product
{

    private double _price;
    public double Price 
    { 
        get
        {
            return _price;
        }
        set
        {
            _price = value;
        }
    }
}

I have created a ProductDataSource with the VisualStudio interface and bound the price to a label. Now I filled the datasource of my repeater in code:

dataRepeater1.DataSource = _productDataAgent.GetProducts();

When I startup my application the prices are correctly filled in the labels. So far so good.

Now I want the price labels to be updated when the product is updated. The Visual Studio interface helps me, and let me choose a 'Data Source Update Mode'. So I choose "OnPropertyChanged".

Here comes the tricky part. How does the .NET runtime know that the price property is updated from the backend. So I modify my business class to implement INotifyPropertyChanged. Like this:

public class Product : INotifyPropertyChanged
{
    private double _price;

    public double Price 
    { 
        get
        {
            return _price;
        }
        set
        {
            _price = value;
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs("Price"));
            }
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

The problem is this doesn't work. When I update a product it remeanes un-updated in the interface. When I debug and change the property, I see that the PropertyChanged event is null so no one is listening.

Delving a little deeper in to the problem I found the following on the System.Windows.Forms.Binding Constructor page on MSDN:

An event named PropertyNameChanged.

So I tried using a (custom) PriceChanged event, but that did not work.

Am I doing something wrong here? I am comming from using WPF, so maybe this works a little different in Windows Forms? Is this because I am binding at runtime?

A: 

Jep found the sollution. Apparently you cannot simply bind to a list of products. You will see the products initially, but they will not be updated when a property is changed. Instead you need to statically bind to a BindingSource. Just create an object datasource using the Visual Studio (in the data menu). Code like this is generated:

private System.Windows.Forms.BindingSource beursProductDisplayBindingSource;
this.beursProductDisplayBindingSource = new System.Windows.Forms.BindingSource(this.components);
this.dataRepeater1.DataSource = this.beursProductDisplayBindingSource;

Now you can dynamically bind like this:

BindingSource productBinding = ((BindingSource)dataRepeater1.DataSource);
_productDataAgent.BeursProducts.ForEach(product => productBinding.Add(product));

Now when implementing INotifyPropertyChanged in your data object like I did is works like expected. Just forgot one step which is not needed when using WPF.

zwanz0r