0

I am Developing a winforms application. I have two datagrid views populated from two different bindingsources(control). I am using these to implement the master detail approach. My problem is that when the first datagridview is populated using the binding source I can't select the first row of it ,because the first element in the binding source is defaultly selected and can't be selected. Can any one provide me a solution for this

2
  • I don't understand your problem. You want to select the first row, but the problem is that it is selected? Clarify what is your problem. Commented Dec 14, 2016 at 10:06
  • I want to populate the second datagridview from the selection made on the first datagridview. So when the first datagridview is populated from a binding source control, I cannot select the first row in that datagridview(If I select the second row it's working, I could select forst row after selecting any other rows ) Commented Dec 14, 2016 at 10:13

1 Answer 1

1

As you say the first row is selected by default. So after populating the DataSource to your first GridView you can set the second GridView based on first entry. Later you check the selectionChanged Event to populate the second GridView based on selectedRow of your first one.

Code could look sth. like this:

private void PopulateDataSource()
{
    dataGridView1.DataSource = myBindingSource;

    DataRowView selectedRow;
    if (dataGridView1.SelectedRows.Count > 0)
        selectedRow = dataGridView1.SelectedRows[0] as DataRowView;

    if (selectedRow != null)
        dataGridView2.DataSource = myBindingSource2; //Set the BindingSource based on selectedRow in first Grid

}

private void dataGridView1_SelectionChanged(object sender, EventArgs e)
{
    DataRowView selectedRow;
    if (dataGridView1.SelectedRows.Count > 0)
        selectedRow = dataGridView1.SelectedRows[0] as DataRowView;

    if (selectedRow != null)
        dataGridView2.DataSource = myBindingSource2; //Set the BindingSource based on selectedRow in first Grid
}

If this doesn't work let me know but should do the job.

UDPATE

Here is a similar example using the events and methods of the bindingSource:

private void Initialize()
{
    RegisterBindingSourceEvents();
    dataGridView1.DataSource = bindingSource1;
    dataGridView2.DataSource = bindingSource2;
    bindingSource1.DataSource = myDataSource;
}

private void RegisterBindingSourceEvents()
{
    bindingSource1.DataSourceChanged += BindingSource1_DataSourceChanged;
    bindingSource1.CurrentChanged += BindingSource1_CurrentChanged;
}

private void BindingSource1_CurrentChanged(object sender, EventArgs e)
{
    DataRowView row = bindingSource1.Current as DataRowView;
    if (row != null)
        bindingSource2.DataSource = myDataSource2BasedOnRow;
}

private void BindingSource1_DataSourceChanged(object sender, EventArgs e)
{
    DataRowView row = bindingSource1.Current as DataRowView;
    if (row != null)
        bindingSource2.DataSource = myDataSource2BasedOnRow;
}

Further you maybe can use:

 bindingSource.MoveNext();
 bindingSource.MoveFirst();

To simulate focusing seconde row and directly first row. A bit ugly but i would guess this fires current_changed (untested). Better use first approach.

UDPATE-2

I'm sorry to tell you that this is not possible in a beautiful manner. The problem is that the Current Property of your bindingList is always set if your DataSource contains items. So if the user select the same row as the bindingSource Current Property contains your event won't get called. I found a solution which works in my example. You will need one gridEvent and maybe have to do some improvments but the idea should do the job. Sorry but without gridEvent i can't solve this:

Notice that iam using List as DataSource for my Testcase. You got DataTable and have to cast to DataRowView instead of Dummy for sure.

private bool _automatedRowChange;

        private void Initialize()
        {
            List<Dummy> dummies = new List<Dummy> { new Dummy { Id = 1, Text = "Test1" }, new Dummy { Id = 2, Text = "Test2" } };
            bindingSource1.DataSource = dummies;
            dataGridView1.DataSource = bindingSource1;

            //So the first row isn't focused but the bindingSource Current Property still holds the first entry
            //That's why it won't fire currentChange even if you click the first row. Just looks better for the user i guess
            dataGridView1.ClearSelection();

            bindingSource1.CurrentChanged += BindingSource1_CurrentChanged;
            dataGridView1.CellClick += DataGridView1_CellClick;
        }

        private void DataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            var clickedRow = dataGridView1.Rows[e.RowIndex].DataBoundItem as Dummy;
            var currentRow = bindingSource1.Current as Dummy;

            if (clickedRow != null &&
                currentRow != null &&
                clickedRow.Equals(currentRow))
            {
                _automatedRowChange = true;
                bindingSource1.MoveNext();

                _automatedRowChange = false; //MovePrevious is based on the click and should load the dataSource2
                bindingSource1.MovePrevious();
            }
        }

        private void BindingSource1_CurrentChanged(object sender, EventArgs e)
        {
            if (!_automatedRowChange) //Check if you jump to next item automatically so you don't load dataSource2 in this case
            {
                //Set the second DataSource based on selectedRow
            }
        }
Sign up to request clarification or add additional context in comments.

5 Comments

Thank you so much . But my problem is a bit different. I tried the above kind of solution earlier, it did not work. The problem(in my context) is with the binding source, if I check dataGridView1.SelectedRows.Count it shows 0. This is because when we bind the datagridview using a binding source the first element in the binding source is the current item (in the binding source) . So after loading the first data gridview i cannot invoke the current_changed event handler of binding source by selecting the first item. In this form I want to make use of the binding source events.
@VipinJacob I updated my answer to implement the behaviour using the bindingSource events and Methods.
it works, but I don't want to load the second datagridveiw initially. I just want to load the first datagridview and then the user has to decide about the selection to be made on the first datagridveiw . And based on that selection the second datagridview needs to be loaded. And I want to use exactly the binding source events.
@VipinJacob See my Update-2 post. Can't find a better solution for your issue. You need to do some improvements for example if your DataSource just contain one item. But else this works.
It works with 5% less satisfaction. As you told without a gridevent its not possible to make it as required. Appreciate your help :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.