2
votes

I want to have one:

BindingList XYZ = new BindingList();

and an Item of BindingList has data of a TextBox-Cell and a ComboBox-Cell of one row. If the user now changing data of the ComboBox, he wants to display it immediately on the screen. Can it be achieved with only one List which is directly bind to the datagridview:

DataSource_of_the_datagridview = XYZ;

Could it happen if there is a change on the ComboBox, that the underlying data of the BindingList and furthermore also the displayed data of the datagridview will be changed?

I want to use datagridtextboxcolumn and datagridcomboboxcolumn. What do i should do in my object which represents one row. I have already used this in the class for thes object-rows:

class Fahrzeug : INotifyPropertyChanged
{

public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(string propertyName){
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }

}
}
2

2 Answers

1
votes

I would suggest to raise "PropertyChanged" event on any desired property(ies) (in its setter), this will notify in realtime changes to binded objects, and UI will process them.

We use something like that in a base class: DataGridView.BindingList = new BindingList<object who inherits this>()

public void SetFieldValue<T>(T field, T value, params string[] propertyNames)
{
      Foreach var propName In PropertyNames
      {
            NotifyPropertyChanged(propName)
      }
}

then MAKE SURE you have ONY one REFERENCE on this BindingList, and modify any object, it will update itself in grid...

0
votes

I have done it like this tutorial:

http://www.timvw.be/2007/01/17/exploring-datagridviewcomboboxcolumn-databinding/

I only can give an overview:

There is one TypeCode which represents one Type of the ComboBox-Values. This is the Connection-point to my main BindingList XYZ. XYZ are data sets, which contains with one attribute the TypeCode. You can now easily Bind this XYZ list to your dataGridView. Important is for the Binding the PropertyName of each column.

One thing you should do, is to define the Columns in your visual studio explorer. You set manually in the datagridview the columns which you want to have vor the data. For example: define a column value1 with a textboxcolumn and value2 with a comboboxcolumn.

In your code you can now reference the column with your dataset XYZ:

this.valuetextboxcolumn.DataPropertyName = "value1";

now you can add values to your dataset XYZ. and finallay bind it with this:

this.XYZ_Binding_Source.DataSource = XYZ;
this.dataGridView1.DataSource = this.XYZ_Source;

you have to define all of this elements also in your code.

The value at the comboboxcolumn can now easily changed with this line:

XYZ.TypeCode = TypeCode.valuecode1;

You have to bind another list to the comboboxes which contains Types which can be chosen by the user.

this.DataGridViewComboBoxColumn.DataPropertyName = "TypeCode";
this.DataGridViewComboBoxColumn.DisplayMember = "Label";
this.DataGridViewComboBoxColumn.ValueMember = "TypeCode";

The DataPropertyName is the variable for the TypeCode of the Element from XYZ-List and the TypeCode of each element which you bind to your combobox. If you now type at the combobox button, you see the "Labels" of each element which you have bound to the combobox. And the value which contains the combobox is also the TypeCode. You can add now several list-items to the comboboxlist like this:

bindingList.Add(new Type(LabelText, TypeCode.valuecode1));// only an example

As you can see in the tutorial of timvw, you have to evaluate the user input with this event-method:

    void dataGridView1_EditingControlShowing(object sender, DataGridViewEditingControlShowingEventArgs e)
    {
        if (this.dataGridView1.CurrentCell.ColumnIndex == this.DataGridViewComboBoxColumn.Index)
        {
            BindingSource bindingSource = this.dataGridView1.DataSource as BindingSource;
            XYZ xyz = bindingSource.Current as XYZ;
            BindingList<Type> bindingList = this.add_all_data_sets_which_can_be_chosen();

            DataGridViewComboBoxEditingControl comboBox = e.Control as DataGridViewComboBoxEditingControl;

            comboBox.DataSource = bindingList;
            if (xyz.TypeCode != null)
            {
                comboBox.SelectedValue = xyz.TypeCode;
            }
            else
            {
                comboBox.SelectedValue = string.Empty;
            }

            comboBox.SelectionChangeCommitted -= this.comboBox_SelectionChangeCommitted;
            comboBox.SelectionChangeCommitted += this.comboBox_SelectionChangeCommitted;
        }
    }

    void comboBox_SelectionChangeCommitted(object sender, EventArgs e)
    {
        this.dataGridView1.EndEdit();
    }

A brief description of the code: If the user clicked at one dataset of the combobox, then a event rises and every dataset which can be chosen by the user can now be added. The data set of the Combobox is very dynamically. If the chosen dataset is added to the property "typecode" of the XYZ-list, the typecode is now displayed on the combobox. After this the endedit() method of the dataGridView1 is invoked automatically.