绑定的DataGridView是否可以设置绑定到另一个源的DGVComboCell的显示值

时间:2019-05-02 00:55:52

标签: c# winforms datagridview datagridviewcomboboxcell

我有一个绑定到列表的DGV。

Work是一个包含许多属性的类,其中包括一个int类型的status属性。我希望在映射到适当的显示值的DataGridViewComboBoxCell中具有该Status值。

所以映射看起来像

1 = Completed   
2 = In Progress   
3 = Errored   
4 = On Hold

我尝试将DataGridViewComboBoxCell绑定到一个包含状态的int和字符串值的列表。

我一直无法弄清楚如何使work.status在DataGridViewComboBoxCell中显示Statuses.DisplayName。

public class Work
{
    public int id {get; set;}
    public string name {get; set;}
    public int status {get; set;}
    public datetime created {get; set;}
    public datetime modified {get; set;}
}

public class Statuses
{
    public int id {get; set;}
    public string DisplayValue {get; set;}

}

如果可以做到,请告诉我。.

1 个答案:

答案 0 :(得分:0)

注释中建议的一种可能的解决方案是按照描述的方式“创建” DataGridViewComboBoxColumn,然后将其添加到网格中。在设置网格数据源之前,请执行此操作。使用组合列Work将此组合框列映射到DataPropertyName列表的“ WorkStatus”属性。将列DataPropertyName设置为“ WorkStatus”应该可以解决问题。

您可能会遇到的一个重要问题是,在设置组合框列之后,将“ 1-完成”,“ 2-正在进行…”等设置为“ int”值是“状态”中的值。 Work个项目的列表字段中……太好了!可能总是这样,但是,如果Status字段之一的值不是1、2、3或4…,则当此值映射到DataError时,网格将抛出DataError组合框列。在大多数情况下,直到读取数据和动臂崩溃,您才知道这一点。

重点是,如果您要设置组合框列,然后将数据源中的列“映射”到该列……则最好确保它没有任何无效的“状态”值。否则,将确保发生崩溃(数据错误)。无论如何,最好将Work连接起来。

鉴于此,似乎有必要至少“检查”以确保在将数据绑定到网格时不会发生类似情况。一种简单的解决方案是遍历所有数据(在将其绑定到网格之前)并“检查”每个public class Work { public int WorkID { get; set; } public string WorkName { get; set; } public int WorkStatus { get; set; } public DateTime DateCreated { get; set; } public DateTime DateModified { get; set; } } 项目的“状态”值。如果在数据中找到一个大于4或小于1的值,该怎么办呢?您不能像上面解释的那样随心所欲。该解决方案是简单地使用“未知”字符串值将值“添加”到组合框。这样至少可以“保证”您可以避免无效值引起的数据错误。

将它们放在一起可能会是这样……

下面是发布的Work类,但是我确实更改了一些变量名。这是绑定到网格的类。

Status

接下来是Status类,用于定义Equals对象。这用于组合框列。构造函数与重写的Contains方法一起添加。使用列表的public class Status : IEquatable<Status> { public int StatusID { get; set; } public string StatusString { get; set; } public Status(int statusID, string statusString) { StatusID = statusID; StatusString = statusString; } public override bool Equals(object obj) { if (obj.GetType() != GetType()) return false; return Equals(obj as Status); } public bool Equals(Status that) { return that != null && this.StatusID == that.StatusID; } public override int GetHashCode() { var hashCode = -1280899892; hashCode = hashCode * -1521134295 + StatusID.GetHashCode(); return hashCode; } } 属性,可以方便“检查”以查看列表中是否已存在“状态”值。

ListOfStatus

设置Work将需要遍历Status对象的列表,并“检查”每个状态值,以确保值介于1和4之间(包括1和4)。返回此列表的方法可能会派上用场,如下所示……首先创建“默认” Work值并将其添加到列表(1、2、3、4),然后循环遍历private List<Status> GetStatusList(List<Work> workItems) { List<Status> listOfStatus = new List<Status>(); // add the default values for the combo boxes Status curStatus = new Status(1, "Complete"); listOfStatus.Add(curStatus); curStatus = new Status(2, "In Progress"); listOfStatus.Add(curStatus); curStatus = new Status(3, "Errored"); listOfStatus.Add(curStatus); curStatus = new Status(4, "On Hold"); listOfStatus.Add(curStatus); // check to make sure the data (workItems) does NOT have any values in the Status field... // that are NOT one of the values above... (specifically 1, 2, 3 or 4) // if the value is NOT one of the values above... we will simply add it to the list Status unknownStatus; foreach (Work work in workItems) { if (work.WorkStatus < 1 || work.WorkStatus > 4) { unknownStatus = new Status(work.WorkStatus, "Unknown_" + work.WorkStatus); if (!listOfStatus.Contains(unknownStatus)) { listOfStatus.Add(unknownStatus); } } } return listOfStatus; } 项目中添加状态列表中尚未存在的所有值。

Status

现在我们有了一个Work对象的完整列表,我们可以继续创建组合框列,并将此列表用作组合列的数据源。给定DataGridViewComboBoxColumn对象的列表,我们就需要创建此列,而返回此DataPropertyName的方法可能类似于以下内容……。首先,我们从上述方法中获取状态列表,然后设置columns属性,并确保将Work列设置为与WorkStatus对象private DataGridViewComboBoxColumn GetComboColumn(List<Work> listOfWork) { List<Status> ListOfStatus = GetStatusList(listOfWork); DataGridViewComboBoxColumn comboCol = new DataGridViewComboBoxColumn(); comboCol.Name = "Status"; comboCol.DataPropertyName = "WorkStatus"; comboCol.DisplayMember = "StatusString"; comboCol.ValueMember = "StatusID"; comboCol.DataSource = ListOfStatus; return comboCol; } 属性匹配。如果不匹配,则该列将无法正确映射。添加的“状态”列将最终成为网格中的第一列,因此您可能需要更改其序数值。

private void Form1_Load(object sender, EventArgs e) {
  List<Work> ListOfWork = new List<Work>();
  FillListOfWork(ListOfWork);
  dataGridView1.Columns.Add(GetComboColumn(ListOfWork));
  dataGridView1.DataSource = ListOfWork;
}

private void FillListOfWork(List<Work> ListOfWork) {
  Work newWork;
  Random rand = new Random();
  for (int i = 0; i < 100; i++) {
    newWork = new Work();
    newWork.WorkID = i;
    newWork.WorkName = "Work Name " + i;
    newWork.WorkStatus = rand.Next(1, 5);
    newWork.DateCreated = DateTime.Now;
    newWork.DateModified = DateTime.Now;
    ListOfWork.Add(newWork);
  }
}

private void dataGridView1_DataError(object sender, DataGridViewDataErrorEventArgs e) {
  MessageBox.Show("DataError: " + e.Exception.Message);
}

下面是使用上述方法的示例。

{{1}}

我希望这会有所帮助。