我创建了一个带有wx.grid.PyGridTableBase派生类的wx.grid.Grid来提供其数据。我还想控制桌子上使用的编辑器。为此,我定义了以下方法
def GetAttr(self, row, col, kind):
attr = wx.grid.GridCellAttr()
if col == 0:
attr.SetEditor( wx.grid.GridCellChoiceEditor() )
return attr
但是,每当我尝试在网格中创建编辑器时,这都会导致分段错误。我确实尝试事先创建编辑器并将其作为参数传递但收到错误:
TypeError: in method 'GridCellAttr_SetEditor', expected argument 2 of type
'wxGridCellEditor *'
我怀疑第二个错误是由GridCellAttr取消所有权然后销毁我的编辑器引起的。
我也尝试在wx.grid.Grid上使用SetDefaultEditor方法,但这有效,但自然不允许我有一个特定于列的编辑策略。
请参阅崩溃程序的完整示例:http://pastebin.com/SEbhvaKf
答案 0 :(得分:4)
我发现了问题:
wxWidgets代码假定从GetCellAttr始终返回相同的编辑器。每次我正在做的时候返回一个不同的编辑器会导致分段错误。
为了多次返回同一个编辑器,我还需要在编辑器上调用IncRef()以使其保持活动状态。
对于将来遇到同样问题的其他人,请参阅我的工作代码:
import wx.grid
app = wx.PySimpleApp()
class Source(wx.grid.PyGridTableBase):
def __init__(self):
super(Source, self).__init__()
self._editor = wx.grid.GridCellChoiceEditor()
def IsEmptyCell(self, row, col):
return False
def GetValue(self, row, col):
return repr( (row, col) )
def SetValue(self, row, col, value):
pass
def GetNumberRows(self):
return 5
def GetNumberCols(self):
return 5
def GetAttr(self, row, col, kind):
attr = wx.grid.GridCellAttr()
self._editor.IncRef()
attr.SetEditor( self._editor )
return attr
frame = wx.Frame(None)
grid = wx.grid.Grid(frame)
grid.SetTable( Source() )
frame.Show()
app.MainLoop()
答案 1 :(得分:0)
这应解决它:
import wx
import wx.grid as gridlib
并改变:
def GetAttr(self, row, col, kind):
attr = gridlib.GridCellAttr()
if col == 0:
attr.SetEditor( gridlib.GridCellChoiceEditor() )
return attr
Obs:我不知道为什么你需要这样做,因为:
>>> import wx
>>> attr = wx.grid.GridCellAttr()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'module' object has no attribute 'grid'
不要工作但是:
import wx.grid as gridlib
attr = gridlib.GridCellAttr()
有效......但是:
print attr
<wx.grid.GridCellAttr; proxy of <wx.grid.GridCellAttr; proxy of <Swig Object of type 'wxGridCellAttr *' at 0x97cb398> > >
它说:<wx.grid.GridCellAttr; proxy of <wx.grid.GridCellAttr>...>
!
Obs2:如果你在整个第0列上使用ChoiceEditor,你也可以在显示网格之前只定义一次:
attr.SetEditor( gridlib.GridCellChoiceEditor() )
yourGrid.SetColAttr(0, attr)
你可以从GetAttr方法中删除所有代码(我认为它应该更快 - 但我从来没有计时)。