Несколько комбинированных ящиков с одним и тем же источником данных (С#)
ОБНОВЛЕНИЕ: теперь это разрешено, см. ответ ниже.
В одной из моих форм (в приложении Windows Forms) у меня есть 3 Combo Boxes. Эти комбинированные поля должны отображать список цен (в тексте с целочисленным исходным значением).
Все эти комбинированные поля используют один и тот же источник данных (A List < > типа TSPrice, с ValueMember, установленным в Price и DisplayMember, который установлен в Описание).
Моя проблема в том, что... Каждый раз, когда я выбираю вариант цены из одного из выпадающих списков, они ВСЕ изменяются до одного значения... Это что-то связано с тем, что все они связаны с одним и тем же источником данных?
Вот как я их связываю:
var priceList = new List<TSPrice>
{
new TSPrice(0, ""),
new TSPrice(0, "Half Day"),
new TSPrice(0, "Full Day"),
new TSPrice(0, "1 + Half"),
new TSPrice(0, "2 Days"),
new TSPrice(0, "Formal Quote Required")
};
objInsuredPrice.DataSource = priceList;
objTPPrice.DataSource = priceList;
objProvSum.DataSource = priceList;
objInsuredPrice.ValueMember = "Price";
objTPPrice.ValueMember = "Price";
objProvSum.ValueMember = "Price";
objInsuredPrice.DisplayMember = "Description";
objTPPrice.DisplayMember = "Description";
objProvSum.DisplayMember = "Description";
objInsuredPrice.SelectedIndex = 0;
objTPPrice.SelectedIndex = 0;
objProvSum.SelectedIndex = 0;
//objInsuredPrice.DataSource = objTPPrice.DataSource = objProvSum.DataSource = priceList;
//objInsuredPrice.ValueMember = objTPPrice.ValueMember = objProvSum.ValueMember = "Price";
//objInsuredPrice.DisplayMember = objTPPrice.DisplayMember = objProvSum.DisplayMember = "Description";
//objInsuredPrice.SelectedIndex = objTPPrice.SelectedIndex = objProvSum.SelectedIndex = 0;
Изменить: проблема заключалась в том, что все они были связаны с тем же источником данных, что и подтвержденным Saurabh. Вот как я это решил.
var priceList = new List<TSPrice>
{
new TSPrice(0, ""),
new TSPrice(1, "Half Day"),
new TSPrice(2, "Full Day"),
new TSPrice(3, "1 + Half"),
new TSPrice(4, "2 Days"),
new TSPrice(5, "Formal Quote Required")
};
var insuredList = new TSPrice[5];
var TPList = new TSPrice[5];
var provList = new TSPrice[5];
priceList.CopyTo(insuredList);
priceList.CopyTo(TPList);
priceList.CopyTo(provList);
objInsuredPrice.DataSource = insuredList;
objTPPrice.DataSource = TPList;
objProvSum.DataSource = provList;
objInsuredPrice.ValueMember = objTPPrice.ValueMember = objProvSum.ValueMember = "Price";
objInsuredPrice.DisplayMember = objTPPrice.DisplayMember = objProvSum.DisplayMember = "Description";
objInsuredPrice.SelectedIndex = objTPPrice.SelectedIndex = objProvSum.SelectedIndex = 0;
Ответы
Ответ 1
Я знаю, что вы не просили об этом, но могу ли я предложить вам немного реорганизовать ваш последний код: -)
private List<TSPrice> GetPriceList()
{
return new List<TSPrice>
{
new TSPrice(0, ""),
new TSPrice(0, "Half Day"),
new TSPrice(0, "Full Day"),
new TSPrice(0, "1 + Half"),
new TSPrice(0, "2 Days"),
new TSPrice(0, "Formal Quote Required")
};
}
private void BindPriceList(ComboBox comboBox, List<TSPrice> priceList)
{
comboBox.DataSource = priceList();
comboBox.ValueMember = "Price";
comboBox.DisplayMember = "Description";
comboBox.SelectedIndex = 0;
}
BindPriceList(objInsuredPrice, GetPriceList());
BindPriceList(objTPPrice, GetPriceList());
BindPriceList(objProvSum, GetPriceList());
Ответ 2
возможно, вы также можете попробовать это решение, просто назначьте новый контекст ко второму поле со списком:
combobox1.DataSource = results;
combobox1.DisplayMember = "DisplayValue";
combobox1.ValueMember = "Value";
combobox2.BindingContext = new BindingContext(); //create a new context
combobox2.DataSource = results;
combobox2.DisplayMember = "DisplayValue";
combobox2.ValueMember = "Value";
Спасибо
Ответ 3
Я не понимаю, почему это должно быть так сложно... вы можете просто связать их с клонами того же источника данных..., что решает проблему. Все, что вам нужно сделать, это
objInsuredPrice.DataSource = new List<TSPrice>(priceList);
objTPPrice.DataSource = new List<TSPrice>(priceList);
objProvSum.DataSource = new List<TSPrice>(priceList);
Кстати, это именно то, что делает код VVS.
Тем не менее, странное поведение... это просто ошибка, imo.
Ответ 4
Да, вы абсолютно правы, так как вы привязываетесь к одному и тому же источнику, поэтому выбор в одном будет применен к остальной части combox
для преодоления этой проблемы необходимо вручную удалить другой обработчик combobox в событии с измененным событием slectedindex, а затем установить выбранный индекс, а затем снова добавить обработчики для ввода кода, просто см. ниже
ComboBox c1 = new ComboBox();
ComboBox c2 = new ComboBox();
c1.SelectedIndexChanged += new EventHandler(c1_SelectedIndexChanged);
c2.SelectedIndexChanged += new EventHandler(c2_SelectedIndexChanged);
void c2_SelectedIndexChanged(object sender, EventArgs e)
{
c1.SelectedIndexChanged -= c1_SelectedIndexChanged;
c2.SelectedIndex = 2;
c1.SelectedIndexChanged += c1_SelectedIndexChanged;
}
void c1_SelectedIndexChanged(object sender, EventArgs e)
{
c2.SelectedIndexChanged -= c2_SelectedIndexChanged;
c1.SelectedIndex = 2;
c2.SelectedIndexChanged += c2_SelectedIndexChanged;
}
Ответ 5
Бет Масси написала статью, объясняющую эту проблему и правильное решение: https://web.archive.org/web/20190114100843/https://blogs.msdn.microsoft.com/bethmassi/2007/09/19/binding- множественный комбо-боксы-к-же-данные источник /
У нее есть ряд других видео о привязке данных, на которые она также ссылается.
Я прочитал предыдущие ответы и могу подтвердить, что, к сожалению, ни один из них не сработал, когда я их попробовал.
Создание нового BindingContext в выпадающем списке просто, кажется, нарушает его. Я предлагаю сделать так, как объясняет Бет: сделать совершенно новую настройку BindingSource.
Ответ 6
Это работает для меня, и мне не нужно копировать источник.
List<string> days = GetDays();
List<string> months = GetMonths();
List<string> years = GetYears();
Son1DDLDay.DataSource = days;
Son1DDLDay.DataBind();
Son1DDLMonth.DataSource = months;
Son1DDLMonth.DataBind();
Son1DDLYear.DataSource = years;
Son1DDLYear.DataBind();
Son2DDLDay.DataSource = days;
Son2DDLDay.DataBind();
Son2DDLMonth.DataSource = months;
Son2DDLMonth.DataBind();
Son2DDLYear.DataSource = years;
Son2DDLYear.DataBind();