我有一个绑定到List [of Parts]的DataGridView。列表中的最后一项始终是“虚拟部分”,用于在网格中创建额外的行,以便用户可以开始键入第一个单元格以将部件添加到列表中。 一旦用户在该特定单元格中输入了超过x个字符,带有搜索结果的新DataGridView就会出现在他正在键入的单元格下面(稍微查看Google的建议),并且他可以选择其中一个匹配项来将该部分添加到清单。
我通过处理EditControlShowing事件来执行此操作,该事件将“编辑控件”分配给具有TextChanged处理程序的TextBox变量。
错误:
如果用户点击向下箭头键,我希望焦点更改为第二个DataGridView(搜索结果)。 EditControlShowing处理程序第一次工作正常,将焦点移动到第二个DataGridView并使第一个DataGridView处于“看似”功能状态,即所有其他事件处理程序工作。但第二次触发EditControlShowing处理程序时,DataGridView会在InitializeEditingControlValue上抛出NullReferenceException。 因为它是DataGridView自己的调用抛出错误,调试器将我带到我的代码中的“Application.Run”,这没有用。 但是,我确定导致DataGridView进入该状态的调用以及抛出异常的点是当我通过在第二个DataGridView(或任何其他控件)上调用Focus()从第一个DataGridView窃取焦点时那件事)。 但是,如果我让用户将焦点更改为DataGridView(例如,通过单击鼠标),则DataGridView保持正常。
有没有人知道为什么在EditControlShowing的处理程序期间从DataGridView中窃取焦点会导致它之后表现不同?
我尝试过CancelEdit,Refresh,Enable / Disable等...
有关帮助我了解DataGridView中发生了什么的任何建议吗?通过在断点之前和之后检查它,我无法发现任何明显的东西。我甚至不知道如何找出哪个对象为null,因为它是DataGridView自己的代码......
非常感谢。
答案 0 :(得分:0)
好的,我在TextChanged事件处理程序中使用BeginInvoke解决了这个问题(代码在Boo中,但应该有意义):
//The event handler
private def CellAsTextBoxTextChanged(sender as object, e as EventArgs):
...
self.BeginInvoke(ShowPartSelectionArea, currentCell, _CellAsTextBox.Text)
//The method which amongst other things, sets the focus to another control
private def ShowPartSelectionArea(currentCell as DataGridViewCell, searchString as string):
...
AnotherDataGridView.Focus()
...
我之前曾尝试直接在另一个控件上调用Focus()时使用BeginInvoke,如下所示:
private def CellAsTextBoxTextChanged(sender as object, e as EventArgs):
...
ShowPartSelectionArea(currentCell, _CellAsTextBox.Text)
private def ShowPartSelectionArea(currentCell as DataGridViewCell, searchString as string):
...
self.BeginInvoke(AnotherDataGridView.Focus())
...
但是后者没有用,可能是因为第一种方式实际上允许DataGridView的单元格完成它所做的一切,而第二种方式却没有。
因此,对于任何面临同样问题的人,我建议您使用BeginInvoke来调用调用堆栈中的位置。