ComboBox items.count doesn't match DataSource

20,552

Solution 1

If anyone experiences this problem on a dynamically added combobox, the answer is to ensure that you add the combobox to the controls of a container in the form.

By adding "this.Controls.Add(cbo);" to the code before setting the datasource, the problem goes away.

Solution 2

Did you check the Count immediately or at a later time? There is the possibility that the ComboBox does not actually update it's contents until there is an operation such as a UI refresh and hence the count will be off until that time.

On case where this may happen is if you update the DataSource before the Handle is created for the ComboBox. I dug through the code a bit on reflector and it appears the items will not be updated in this case until the ComboBox is actually created and rendered.

Solution 3

I've found the cause...

I took out the cbo.Datasource = null line.. and added a cbo.Invalidate() at the end. This has solved the problem.

Thanks all for the advice.

Solution 4

cbo.DataSource = null; 
cbo.DataSource = cbos; 
cbo.DisplayMember = "Title"; 
cbo.ValueMember = "Value"; 

Now before setting cbo.SelectedValue, or relying on Items to be up-to-date, call

cbo.CreateControl ;

and Items will be re-calculated.

The problem is that SelectedValue/SelectedIndex, which are WinForms properties, only accept the values that are legal according to the Items list, but that one is built only after GUI interaction, i.e. after instantiating a "real" Windows GUI combo box, i.e. after obtaining a Windows handle for the combobox.

CreateControl forces the creation of the Windows handle, no matter what.

Solution 5

 ComboBox cbNew = new ComboBox();
    cbNew.Name = "cbLine" + (i+1);
    cbNew.Size = cbLine1.Size;
    cbNew.Location = new Point(cbLine1.Location.X, cbLine1.Location.Y + 26*i);
    cbNew.Enabled = false;
    cbNew.DropDownStyle = ComboBoxStyle.DropDownList;
    cbNew.DataSource = DBLayer.GetTeams(lineName).Tables[0];
    cbNew.DisplayMember = "teamdesc";
    cbNew.ValueMember = "id";
    Console.WriteLine("ComboBox {0}, itemcount={1}", cbNew.Name, cbNew.Items.Count);
        // The output displays itemcount = 0 for run-time created controls
        // and >0 for controls created at design-time
    gbLines.Controls.Add(cbNew);

TO

 ComboBox cbNew = new ComboBox();
    cbNew.Name = "cbLine" + (i+1);
    cbNew.Size = cbLine1.Size;
    cbNew.Location = new Point(cbLine1.Location.X, cbLine1.Location.Y + 26*i);
    cbNew.Enabled = false;
    cbNew.DropDownStyle = ComboBoxStyle.DropDownList;
    Console.WriteLine("ComboBox {0}, itemcount={1}", cbNew.Name, cbNew.Items.Count);
        // The output displays itemcount = 0 for run-time created controls
        // and >0 for controls created at design-time
    gbLines.Controls.Add(cbNew);
    cbNew.DataSource = DBLayer.GetTeams(lineName).Tables[0];
    cbNew.DisplayMember = "teamdesc";
    cbNew.ValueMember = "id";

The DataSource, DisplayMember and ValueMember property must be set after the control has been added to its container.

Share:
20,552
Madeleine
Author by

Madeleine

As a Product Manager I have a broad role that encompasses the following responsibilities: Product Management which encompasses: Advising the Road Map Committee on the features required for the scheduled releases Market research Producing business requirements for the new features, enhancements, reports etc. Development Lead which encompasses Project managing the development of the releases (the full SDLC) Assist with producing the technical specifications Managing the fixing of errors and bugs in the system and the resultant hot-fix/service pack releases Managing the development team Software development Producing product documentation Consultant and support staff training (new people, new releases etc.) Setting the architectural and technical standards Customer Services which encompasses Assisting with issues that cannot be resolved by support and need to be escalated to development Client consulting to understand and resolve issues the customers have with BarnOwl Pre-Sales assistance to the sales team Client training on an ad-hoc basis

Updated on July 09, 2022

Comments

  • Madeleine
    Madeleine almost 2 years

    I have a ComboBox that is bound to a DataSource. I want to dynamically add items to the ComboBox based on certain conditions. So what I've done is add the options to a new list, and then change the DataSource of the ComboBox like so:

    cbo.DataSource = null;
    cbo.DataSource = cbos;
    cbo.DisplayMember = "Title";
    cbo.ValueMember = "Value";
    

    Then, I check cbo.Items.Count, and it has not incremented - it does not equal the count of the DataSource. Any ideas what I can do here?

    Note this is WinForms and not ASP.NET.

  • Madeleine
    Madeleine almost 15 years
    I'm checking the Items.Count property immediately after in code, because I need to then do some more logic at that point.
  • coder14
    coder14 almost 15 years
    Wouldn't it be simpler to check the number of items in your data source?
  • Madeleine
    Madeleine almost 15 years
    The problem is that I have to set the selected item, usually to the new one, and that index doesnt exist.
  • Jose Basilio
    Jose Basilio almost 15 years
    Found your own solution. Go ahead and accept your own answer. +1
  • Madeleine
    Madeleine over 14 years
    Came across this issue again somewhere else in code. The issue is that the combo box is being added at run time and therefore as Jared mentioned, no handle has been created for the combo box. By adding "this.Controls.Add(cbo);" the problem disappears.
  • Null Head
    Null Head almost 13 years
    You should have rather added this line before setting the datasource. cbo.Items.clear()
  • TheBlastOne
    TheBlastOne almost 13 years
    -1, untrue. It happens also if the ComboBox already is contained in a container that does not have a Windows handle yet.
  • Madeleine
    Madeleine almost 13 years
    I don't think that a -1 is fair here, just because you have found another reason that this occurs. This answer solved the problem in the stated example.
  • TheBlastOne
    TheBlastOne almost 13 years
    Unable to undo unless answer is edited. I keep wondering what kind of edititing rules are behind so's frontend...
  • Brad
    Brad over 8 years
    CreateControl did not fix the problem for me. Adding the control to the collection did.