我如何添加一个DisplayMember和ValueMember到一个单独的ComboBox项目,有一个分配的DataSource? [英] How can I add a DisplayMember and ValueMember to a single ComboBox Item that has an assigned DataSource?

查看:546
本文介绍了我如何添加一个DisplayMember和ValueMember到一个单独的ComboBox项目,有一个分配的DataSource?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在成功地将显示/值对添加到如下所示的组合框:

  List< Student& BRstudents = 
studentsList.Where(h => h.EnrolledInAYttFM)
.Where(i =>
i.RecommendedNextTalkTypeID.Equals(BIBLE_READING_TALK_TYPE))
.OrderBy => j.WeekOfLastAssignment)
.ToList();
comboBoxBR.DataSource = BRstudents;
comboBoxBR.DisplayMember =FullName;
comboBoxBR.ValueMember =StudentID;

...但我在某些情况下想要向comboBoxBR添加另一个项目不存在于BRStudents列表中。如果我尝试这样做:

  AssignmentHistory ah = AYttFMConstsAndUtils.AssignmentHistList 
.FirstOrDefault(i => i。 WeekOfAssignment == currentWeek&& i.TalkType == 1);
string fullName = AYttFMConstsAndUtils.GetStudentFullNameForID(ah.StudentID_FK);
comboBoxBR.Items.Add(fullName);

...我得到,当DataSource属性设置时,项目集合不能被修改。 / p>

真的,我想做这样的事情:

  comboBoxBR。 Items.Add(fullName,ah.StudentID_FK); 

是否有办法将两个结果(学生和单个AssignmentHistory的列表)字典或某些此类集合,然后将分配作为comboBoxBR的数据源?



为了充分公开,下面是Student和AssignmentHistory的定义:

  public class Student 
{
public int StudentID {get;组; }
public int FamilyID {get;组; }
public bool EnrolledInAYttFM {get;组; }
public DateTime DateEnrolledOrHiatusAYttFM {get;组; }
public bool GivesBibleReading {get;组; }
public bool PresentsICRVBS {get;组; }
public bool IsHouseholder {get;组; }
public bool IsMale {get;组; }
public string FirstName {get;组; }
public string LastName {get;组; }
public string EmailAddr {get;组; }
public DateTime WeekOfLastAssignment {get;组; }
public int RecommendedNextTalkTypeID {get;组; }
public int NextCounselPoint {get;组; }
public string FullName => ${FirstName} {LastName};
}

public class AssignmentHistory
{
public DateTime WeekOfAssignment {get;组; }
public int TalkType {get;组; }
public int StudentID_FK {get;组; }
public int AssistantID_FK {get;组; }
public int CounselPoint {get;组; }
public bool HasBeenEmailed {get;组; }
public bool SlipHasBeenPrinted {get;组; }
}


解决方案

组合的Items集合(如果你已经设置了DataSource,不可能)第一件事就是添加元素到 List< Students> 本身作为DataSource,但是这没有达到你的目标,因为没有机制来通知ComboBox DataSource有一个新的元素。您不能看到添加的元素,除非将列表重新绑定到组合框。要做到这一点你首先需要解除绑定以前的DataSource,然后再次重新绑定列表。

  //假设你的学生很多类,希望明确的意图
BRStudents.Add(new Student(){newName =ANewStudent,ID = 1});
comboBoxBR.DataSource = null;
comboBoxBR.DataSource = BRstudents;
comboBoxBR.DisplayMember =FullName;
comboBoxBR.ValueMember =StudentID;但是,有一个更好的解决方案,它是类 msdn.microsoft.com/en-us/library/ms132679(v=vs.110).aspxrel =nofollow> BindingList(T)

此类可以刷新



所以当你第一次绑定combo时,你必须写

  BindingList< Student> bl = new BindingList< Student>(BRstudents); 
comboBoxBR.DataSource = bl;
comboBoxBR.DisplayMember =FullName;
comboBoxBR.ValueMember =StudentID;

,当您要向列表中添加一个新元素时

(如果需要,在全局范围移动bl)

  bl.Add(new Student(){newName =ANewStudent,ID = 1}); 

文档声明你应该调用ResetBindings来强制刷新控件,总是需要...


I am successfully adding Display/Value pairs to a combobox like this:

List<Student> BRStudents =
        studentsList.Where(h => h.EnrolledInAYttFM)
            .Where(i =>     
    i.RecommendedNextTalkTypeID.Equals(BIBLE_READING_TALK_TYPE))
            .OrderBy(j => j.WeekOfLastAssignment)
            .ToList();
    comboBoxBR.DataSource = BRStudents;
    comboBoxBR.DisplayMember = "FullName";
    comboBoxBR.ValueMember = "StudentID";

...but I then (in some instances) want to add another item to comboBoxBR, one which is not present in the BRStudents list. If I try to do this:

AssignmentHistory ah = AYttFMConstsAndUtils.AssignmentHistList
    .FirstOrDefault(i => i.WeekOfAssignment == currentWeek && i.TalkType == 1);
string fullName = AYttFMConstsAndUtils.GetStudentFullNameForID(ah.StudentID_FK);
comboBoxBR.Items.Add(fullName);

...I get, "Items collection cannot be modified when the DataSource property is set."

Really, I want to do something like this:

comboBoxBR.Items.Add(fullName, ah.StudentID_FK);

Is there a way to combine the two results (the list of Student and the single AssignmentHistory) into a Dictionary or some such collection, and then assign that as the DataSource for comboBoxBR?

For full disclosure, here are the definitions of Student and AssignmentHistory:

public class Student
{
    public int StudentID { get; set; }
    public int FamilyID { get; set; }
    public bool EnrolledInAYttFM { get; set; }
    public DateTime DateEnrolledOrHiatusAYttFM { get; set; }
    public bool GivesBibleReading { get; set; }
    public bool PresentsICRVBS { get; set; }
    public bool IsHouseholder { get; set; }
    public bool IsMale { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string EmailAddr { get; set; }
    public DateTime WeekOfLastAssignment { get; set; }
    public int RecommendedNextTalkTypeID { get; set; }
    public int NextCounselPoint { get; set; }
    public string FullName => $"{FirstName} {LastName}";
}

public class AssignmentHistory
{
    public DateTime WeekOfAssignment { get; set; }
    public int TalkType { get; set; } 
    public int StudentID_FK { get; set; }
    public int AssistantID_FK { get; set; } 
    public int CounselPoint { get; set; }
    public bool HasBeenEmailed { get; set; }
    public bool SlipHasBeenPrinted { get; set; }        
}

解决方案

Instead of adding elements to the Items collection of the combo (not possible if you have set the DataSource) the first thing that comes to mind is adding elements to the List<Students> itself used as DataSource, but this doesn't reach your objective because there is no mechanism in place to inform the ComboBox that the DataSource has a new element. You can't see the added element unless you rebind the List to the combobox. To do this you first need to unbind the previous DataSource and then rebind the list again.

// Assuming a lot about your student class, hope it's clear the intention
BRStudents.Add(new Student() { newName = "ANewStudent", ID = 1} );
comboBoxBR.DataSource = null;
comboBoxBR.DataSource = BRStudents;
comboBoxBR.DisplayMember = "FullName";
comboBoxBR.ValueMember = "StudentID";

However, there is a better solution and it is the class BindingList(T)
This class is capable to refresh the object at which you bind an instance of it.

So when you bind the combo for the first time you have to write

BindingList<Student> bl = new BindingList<Student>(BRStudents);
comboBoxBR.DataSource = bl;
comboBoxBR.DisplayMember = "FullName";
comboBoxBR.ValueMember = "StudentID";

and when you want to add a new element to the list you write
(move bl at the global scope if needed)

bl.Add(new Student() { newName = "ANewStudent", ID = 1} );

The documentation states that you should call ResetBindings to force a refresh of the control but this doesn't seems always required...

这篇关于我如何添加一个DisplayMember和ValueMember到一个单独的ComboBox项目,有一个分配的DataSource?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆