【问题标题】:Unable To set row visible false of a datagridview无法设置数据网格视图的行可见错误
【发布时间】:2013-09-27 07:58:15
【问题描述】:

我有一个DataGridView,我在其中设置了DataSource

taskerEntities te = new taskerEntities();
var OMsMasterDescriptiveIndicators = te.MyTable.Select(x => new lccls {Id = x.Id, name = x.name }).ToList();
MyGrid.DataSource = OMsMasterDescriptiveIndicators;

与我的class lccls 一样

public class lccls
    {
        public string Id { get; set; }
        public Nullable<decimal> name { get; set; }
    }

在某个事件中,我想让当前行不可见:

 MyGrid.Rows[5].Visible = false;

但我无法做到这一点。相反,会引发异常并显示以下错误消息:

无法创建与货币经理职位相关联的行 隐形

我怀疑原因与设置DataSource有关,但为什么呢?

【问题讨论】:

  • 你把代码MyGrid.Rows[e.RowIndex].Visible = false;放在哪里?奇怪的是,如果你使用任意的index,例如01,......它会成功隐藏该行。
  • 我已经更改了 e.rowindex 但它仍然无法正常工作
  • 您是否在运行时更改数据源(删除行)?
  • 我没有删除行我只是隐藏行
  • 是的,我明白了。我的意思是如果您在运行时更改数据源例如:启动数据源 1、2、3;并且您删除了记录 2;那么您打算使给定行在 DGV 中不可见。我已经阅读了您的答案,很可能这就是问题所在。最安全的方法是直接从 DGV 执行任何更新(或者,从数据源执行更新时,确保通过考虑所涉及的不同索引来考虑 DGV 中的变化)。

标签: c# datagridview datasource


【解决方案1】:

我试图在 CellFormating 事件中隐藏一行,但没有成功。看起来货币管理器不能为引发事件的行暂停,而不是我处理之前的行(第 0 行处理最后一行)

Private Sub DgView1_CellFormatting(sender As Object, e As DataGridViewCellFormattingEventArgs) Handles DgView1.CellFormatting
        If DgView1.Rows(e.RowIndex).Cells(e.ColumnIndex).OwningColumn.Name = CoID Then
            Dim k = If(e.RowIndex = 0, DgView1.RowCount - 1, e.RowIndex - 1)
            DgView1.Rows(k).Visible = Countries.Rows(k)("Ro")
        End If
End Sub

【讨论】:

    【解决方案2】:

    我知道这是一个老话题,但另一种解决方案(我的代码是 vb.net,但我认为它会翻译)

    If WO_DGV.CurrentCell.RowIndex = i Then
      'you cannot make invisible the row that is 'current'
      WO_DGV.CurrentCell = WO_DGV.Rows(i - 1).Cells("act") 
      'to get to this code I know that there is a row before i, which is why I can use i-1 as new focus
    End If
    WO_DGV.Rows(i).Visible = False 
    

    【讨论】:

      【解决方案3】:

      回答这个话题可能有点晚了,但我建议你使用 DataTable.DefaultView.RowFilter 属性来过滤您需要在有界 DataGridView 上显示的内容。请查看以下链接以获取更多信息: https://docs.microsoft.com/en-us/dotnet/api/system.data.dataview.rowfilter?redirectedfrom=MSDN&view=netframework-4.8#System_Data_DataView_RowFilter

      问候。

      【讨论】:

        【解决方案4】:

        例子

                foreach (DataGridViewRow rw in dataGridView1.Rows)
                {
        
                if (rw.Cells[14].Value.ToString() == "") // this Cell have a TEXT, 
                    {
                        CurrencyManager currencyManager1 = (CurrencyManager)BindingContext[dataGridView1.DataSource];
                        currencyManager1.SuspendBinding();
                        rw.Visible = false; 
                        currencyManager1.ResumeBinding();
        
                    }
                }
        

        仅显示单元格索引为 14 的行,如果为空或为空,则不显示整行

        【讨论】:

          【解决方案5】:

          经过大量搜索,我得到了solution

          CurrencyManager currencyManager1 = (CurrencyManager)BindingContext[MyGrid.DataSource];  
          currencyManager1.SuspendBinding();
          MyGrid.Rows[5].Visible = false;
          currencyManager1.ResumeBinding();
          

          【讨论】:

          • 非常感谢。我仍然很震惊,为什么隐藏行如此复杂?!?!?
          • 我必须将 CurrencyManager currencyManager1 = (CurrencyManager)BindingContext[MyGrid.DataSource]; 更改为 CurrencyManager currencyManager1 = (CurrencyManager)MyGrid.BindingContext[MyGrid.DataSource]; 才能正常工作
          • 是的,它确实有效。而且我想我知道为什么会遇到它,因为我正在使用多线程来填充作为我的网格数据源的列表。我的猜测是,当我开始尝试隐藏行时,并非所有线程都已完成。
          • @Lev:我仍然很震惊,为什么隐藏行如此复杂?!?!?只需设置CurrentCell = null..
          【解决方案6】:

          当前行索引时,无法将 yourDataGridView 行可见属性设置为 false 如果试图隐藏当前单元格会遇到这样的错误

          解决方案:

          当你的DataGridView数据源不为空时:

            CurrencyManager currencyManager1 = (CurrencyManager)BindingContext[yourDataGridView.DataSource];
                                 currencyManager1.SuspendBinding();
                                 yourDataGridView.Rows[Target Index].Visible = false;
                                 currencyManager1.ResumeBinding();
          

          当你的DataGridView数据源为空时:

           yourDataGridView.CurrentCell = null;
           yourDataGridView.Rows[Target Index].Visible = false;
          

          【讨论】:

          • +1 因为您的第二个解决方案对我有用。即使我绑定到 DataSet 并且 DataSource 不为空,第一个解决方案也 not 起作用!去图...
          【解决方案7】:

          我有一个 U 示例。我有一个可以多选行的 datagridview。当我单击按钮以显示所选的假行时。试试这个:

          foreach (DataGridViewRow row in dataGridView1.SelectedRows)
                  {
                      CurrencyManager currencyManager1 =(CurrencyManager)BindingContext[dataGridView1.DataSource];
                          currencyManager1.SuspendBinding();
                          dataGridView1.CurrentCell = null;
                          row.Visible = false;
                  }
                  dataGridView1.Refresh();
          

          记得设置属性 SelectionMode: FullRowSelect

          【讨论】:

          • 您忘记恢复 CurrencyManager 绑定。此外,您只需暂停 CurrencyManager 一次。您应该在更新循环之外暂停 CurrencyManager,并在循环后恢复它。您也不需要将 CurrentCell 设置为 null,并且这不应该在循环中完成。您无需调用 Refresh() - DataGridView 将自行处理屏幕更新。
          猜你喜欢
          • 1970-01-01
          • 2015-05-02
          • 1970-01-01
          • 2013-08-10
          • 1970-01-01
          • 2015-11-22
          • 2011-10-13
          • 2013-09-03
          • 2011-05-19
          相关资源
          最近更新 更多