2009-10-06 68 views
1

我有一个绑定到对象的BindingList的数据网格控件。对象类的其中一个属性是布尔值。我已将datagridview中的该列自定义为复选框类型。在datagrid视图中使用复选框列修复FormatException

当datagridview为从绑定列表中引入值的行加载时,事情正常工作。但是,当“新条目”行被绘制时,将在复选框单元格上引发System.FormatException。

确切的错误信息(相关部分):

以下异常发生在DataGridView:

System.FormatException: Value '' cannot be converted to type 'Boolean'. at System.Windows.Forms.Formatter.FormatObjects.... 

我的搜索表明,这可能发生在该复选框的真,假,以及不确定的值列未设置。
URL引用类似的问题矿:

http://social.msdn.microsoft.com/Forums/en-US/winformsdatacontrols/thread/c29427ff-18be-4fb0-a0a7-d1940e1cd817

但是,我已设置这些值(在下面的代码示出)。除此之外,我找不到与我的问题相关的任何其他信息。我相当确定问题是本地化的复选框的使用,因为当我将列类型更改为简单的文本框时,我没有得到任何异常错误,只是显示“新条目”行的真/假列没有价值。

的DataGridView代码:

// 
     // dataGridView1 
     // 
     this.dataGridView1.AllowUserToResizeRows = false; 
     dataGridViewCellStyle1.BackColor = System.Drawing.SystemColors.Control; 
     dataGridViewCellStyle1.ForeColor = System.Drawing.SystemColors.WindowText; 
     dataGridViewCellStyle1.NullValue = null; 
     dataGridViewCellStyle1.SelectionBackColor = System.Drawing.SystemColors.Highlight; 
     dataGridViewCellStyle1.SelectionForeColor = System.Drawing.SystemColors.HighlightText; 
     this.dataGridView1.AlternatingRowsDefaultCellStyle = dataGridViewCellStyle1; 
     this.dataGridView1.AutoSizeColumnsMode = System.Windows.Forms.DataGridViewAutoSizeColumnsMode.Fill; 
     this.dataGridView1.AutoSizeRowsMode = System.Windows.Forms.DataGridViewAutoSizeRowsMode.DisplayedCells; 
     this.dataGridView1.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize; 
     this.dataGridView1.Columns.AddRange(new System.Windows.Forms.DataGridViewColumn[] { 
     this.columnDescription, 
     this.columnExpedite, 
     this.columnId, 
     this.columnQuantity, 
     this.columnEntryDate, 
     this.columnUpdateDate}); 
     this.dataGridView1.Location = new System.Drawing.Point(3, 5); 
     this.dataGridView1.Name = "dataGridView1"; 
     this.dataGridView1.SelectionMode = System.Windows.Forms.DataGridViewSelectionMode.FullRowSelect; 
     this.dataGridView1.Size = new System.Drawing.Size(1015, 241); 
     this.dataGridView1.TabIndex = 0; 
     // 
     // columnDescription 
     // 
     this.columnDescription.DataPropertyName = "Description"; 
     this.columnDescription.FillWeight = 200F; 
     this.columnDescription.HeaderText = "Description"; 
     this.columnDescription.Name = "columnDescription"; 
     // 
     // columnExpedite 
     // 
     this.columnExpedite.DataPropertyName = "Expedite"; 
     this.columnExpedite.FalseValue = "false"; 
     this.columnExpedite.HeaderText = "Expedited"; 
     this.columnExpedite.Name = "columnExpedite"; 
     this.columnExpedite.Resizable = System.Windows.Forms.DataGridViewTriState.True; 
     this.columnExpedite.SortMode = System.Windows.Forms.DataGridViewColumnSortMode.Automatic; 
     this.columnExpedite.TrueValue = "true"; 
     this.columnExpedite.IndeterminateValue = "false"; 
     // 
     // columnId 
     // 
     this.columnId.DataPropertyName = "Id"; 
     this.columnId.HeaderText = "Id"; 
     this.columnId.Name = "columnId"; 
     this.columnId.Visible = false; 
     // 
     // columnQuantity 
     // 
     this.columnQuantity.DataPropertyName = "Quantity"; 
     this.columnQuantity.HeaderText = "Quantity"; 
     this.columnQuantity.Name = "columnQuantity"; 
     // 
     // columnEntryDate 
     // 
     this.columnEntryDate.DataPropertyName = "EntryDateTime"; 
     dataGridViewCellStyle2.Format = "g"; 
     dataGridViewCellStyle2.NullValue = null; 
     this.columnEntryDate.DefaultCellStyle = dataGridViewCellStyle2; 
     this.columnEntryDate.HeaderText = "Entry Date/Time"; 
     this.columnEntryDate.Name = "columnEntryDate"; 
     this.columnEntryDate.ReadOnly = true; 
     this.columnEntryDate.Resizable = System.Windows.Forms.DataGridViewTriState.True; 
     this.columnEntryDate.SortMode = System.Windows.Forms.DataGridViewColumnSortMode.NotSortable; 
     // 
     // columnUpdateDate 
     // 
     this.columnUpdateDate.DataPropertyName = "UpdateDateTime"; 
     this.columnUpdateDate.HeaderText = "Last Update Date/Time"; 
     this.columnUpdateDate.Name = "columnUpdateDate"; 
     this.columnUpdateDate.ReadOnly = true; 
     this.columnUpdateDate.Resizable = System.Windows.Forms.DataGridViewTriState.True; 
     this.columnUpdateDate.SortMode = System.Windows.Forms.DataGridViewColumnSortMode.NotSortable; 

编辑补充: 一对夫妇更多的事情,我已经试过:

  • 使用DefaultValueNeeded事件未遂。当我“接触”新的输入行时加载缺省值,但在此之前触发异常,而当“新输入”行实际上是绘画时。

  • 尝试使用 dataGridView1.Columns [“columnExpedite”]。DefaultCellStyle.NullValue =“false”; ,结果相同。

如何解决此异常?

回答

1

我可能会读这个错误,但这听起来像是一个操作顺序问题。我没有看到将项目添加到列表中的代码,因此我不能100%确定他的项目,但我猜想您将新对象添加到列表中,然后修改值

您需要确保布尔值不为空。如果你正在添加一个新项目,您将需要填写之前添加到列表中的对象的值。确保这一点的一种可能方式是设置默认值为false或true,或者在构造函数中设置它。

编辑 - 添加

我没有这个测试自己,但我希望它会为你工作。

你可以钩入DataGridView的DefaultValuesNeeded事件吗?该事件应该在抛出异常之前触发,这应该解决问题...

+0

这是一个很好的观点。我应该解决这个问题,我的绑定语句发生在表单加载。此外,我的构造函数确实为布尔成员设置了默认值。当我点击“新条目”行时,默认值被拉入(我也设置了默认日期)。当“新条目”行被绘制到屏幕上时出现问题。 – Allen 2009-10-06 21:08:04

+0

我尝试过这个事件,并设置了一个值...并且它确实填充,但是直到我单击新条目时......新条目行描绘时发生异常。在那个单元格上画了字面上的停顿。 – Allen 2009-10-06 21:46:15

1

是的。 试试这个代码:

private void dataGridViewEpizode_DefaultValuesNeeded(object sender, DataGridViewRowEventArgs e) 
    { 
     try 
     { 
      e.Row.Cells[22].Value = false; 
     } 
     catch (Exception ex) 
     { 
      mainForm.staticvar.logger.Write(ex); 
     } 
    }