WinForms ComboBox data binding Gotcha

stemmen
44

Neem aan dat je iets aan het doen zijn als het volgende

List<string> myitems = new List<string>
{
    Item 1,
    Item 2,
    Item 3
};

ComboBox box = new ComboBox();
box.DataSource = myitems;

ComboBox box2 = new ComboBox();
box2.DataSource = myitems

Dus nu hebben we 2 combodozen gebonden aan de matrix, en alles werkt prima. Maar als je de waarde van een keuzelijst veranderen, verandert BEIDE keuzelijsten aan degene die je geselecteerd hebt.

Nu, ik weet dat Arrays altijd worden doorgegeven door middel van verwijzing (geleerd dat als ik heb geleerd C: D), maar waarom op aarde zou de keuzelijsten veranderen samen? Ik geloof niet dat de keuzelijst controle is het wijzigen van de collectie helemaal.

Als een werk rond, dit niet zou funcionality dat wordt verwacht / gewenst te bereiken

ComboBox box = new ComboBox();
box.DataSource = myitems.ToArray();
De vraag is gesteld op 02/08/2008 om 17:09
bron van user
In andere talen...                            


3 antwoorden

stemmen
37

Dit heeft te maken met de manier waarop data bindingen worden opgezet in het DotNetFramework, vooral de BindingContext. Op een hoog niveau betekent dit dat als je niet anders hebt opgegeven elke vorm en alle controles van het formulier delen dezelfde BindingContext. Bij het instellen van het DataSourceterrein van het ComboBoxzal gebruik maken van de BindingContexteen te krijgen ConcurrenyMangagerdat de lijst wraps. Het ConcurrenyManagerhoudt bij zaken als de huidige geselecteerde positie in de lijst.

Bij het instellen DataSourcevan de tweede ComboBoxzal gebruik maken van dezelfde BindingContext(vormen) die een verwijzing zal opleveren dezelfde ConcurrencyManagerals hierboven gebruikt om de data bindingen.

Om een nadere toelichting te zien BindingContext .

antwoordde op 02/08/2008 om 18:18
bron van user

stemmen
20

Een betere oplossing (afhankelijk van de grootte van de gegevensbron) te verklaren twee BindingSourceobjecten (nieuw vanaf 2.00) binden het verzamelen die vervolgens binden die de comboboxes.

Hierbij stuur ik u een voorbeeld.

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;

namespace WindowsFormsApplication2
{
    public partial class Form1 : Form
    {
        private BindingSource source1 = new BindingSource();
        private BindingSource source2 = new BindingSource();

        public Form1()
        {
            InitializeComponent();
            Load += new EventHandler(Form1Load);
        }

        void Form1Load(object sender, EventArgs e)
        {
            List<string> myitems = new List<string>
            {
                "Item 1",
                "Item 2",
                "Item 3"
            };

            ComboBox box = new ComboBox();
            box.Bounds = new Rectangle(10, 10, 100, 50);
            source1.DataSource = myitems;
            box.DataSource = source1;

            ComboBox box2 = new ComboBox();
            box2.Bounds = new Rectangle(10, 80, 100, 50);
            source2.DataSource = myitems;
            box2.DataSource = source2;

            Controls.Add(box);
            Controls.Add(box2);
        }
    }
}

Als je jezelf wilt verwarren nog meer dan probeer altijd te verklaren bindingen in de constructor. Dat kan resulteren in een aantal echt nieuwsgierig bugs, dus ik binden altijd in de gebeurtenis Load.

antwoordde op 21/08/2008 om 15:48
bron van user

stemmen
2

Dit zou enkel een typo zijn, maar in de code die u op voorwaarde dat u alleen verwijzen naar de eerste keuzelijst bij het instellen van de gegevensbron:

ComboBox box = new ComboBox();
box.DataSource = myitems;

ComboBox box2 = new ComboBox();
**box**.DataSource = myitems

De gegevensbron voor box2is niet ingesteld.

antwoordde op 21/08/2008 om 18:12
bron van user

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more