wxPython - grid.AutoSizeColumns() 不适用于索引列?

wxPython - grid.AutoSizeColumns() doesn't apply to the index column?

我在结果框中显示了一个分析结果网格,在创建网格后 object 我调用 grid.AutoSizeColumns() 使列适合数据内容。这对于包含数据的实际列来说效果很好,但是最左边的列('index' 列?)只包含行索引仍然相当宽——比需要的宽得多,因为只有四行。 我想做什么: - 删除最左边的列(仅包含行索引的灰色列),and/or -删除 actual“索引”列(带有 header“索引”),因为它是多余的,并缩小最左边的灰色列,或者 - 删除最左边的列和标有“索引”的列。

注意: 我知道 grid.DeleteCols(pos=0, numCols=1) 方法,但这总是会引发错误:

wx._core.wxAssertionError: C++ assertion ""Assert failure"" failed at ..\..\src\generic\grid.cpp(1471) in wxGridTableBase::DeleteCols(): Called grid table class function DeleteCols
but your derived table class does not override this function

而且我不确定如何“覆盖此功能”。如果有人可以向 me/how 解释错误以修复它以便 grid.DeleteCols() 起作用,那将是解决我的问题的一半(另一半缩小或删除灰色 far-left 列网格)

下面的最小代码示例,以及它当前的截图(取自实际程序,而不是最小代码)

在相关说明中,是否有一种简单的方法可以 right-justify 网格中的单元格值?我将结果格式化为具有相同的小数位数,我认为如果值是 right-justfied(甚至居中),它看起来会更整洁。

最小示例:

import wx
import wx.grid
import numpy as np
import pandas as pd

class StartFrame(wx.Frame):
    def __init__(self, parent):
        wx.Frame.__init__(self, parent=parent,
         id=wx.ID_ANY, title="title", size=wx.Size(900,600),
         style=wx.CAPTION|wx.CLOSE_BOX|wx.MINIMIZE_BOX|wx.SYSTEM_MENU|wx.RESIZE_BORDER)
        self.SetSizeHints(wx.DefaultSize, wx.DefaultSize)

        self.numarray=[[1,0.0000,0.071,3.535,3.313,0.22],
                       [10,1.000,0.071,3.535,3.888,-0.353],
                       [20,1.301,0.357,4.634,4.526,0.108],
                       [50,1.699,0.929,6.456,6.442,0.023]]
        self.df = pd.DataFrame(self.numarray, columns=['Parasites/ml','log_qty',
         'probability','probit','est. probit','residual'])

        self.table = DataTable(self.df)
        grid = wx.grid.Grid(self, -1)
        grid.SetTable(self.table, takeOwnership=True)
        grid.AutoSizeColumns()

        self.pnl = wx.Panel(self)
        self.vsizer = wx.BoxSizer(wx.VERTICAL)
        self.hsizer = wx.BoxSizer(wx.HORIZONTAL)

        self.hsizer.AddStretchSpacer()
        self.hsizer.Add(grid, 0, wx.CENTER)
        self.hsizer.AddStretchSpacer()
        self.vsizer.AddStretchSpacer()
        self.vsizer.Add(self.hsizer, wx.SizerFlags().Expand().Border(wx.ALL, 5))
        self.vsizer.AddStretchSpacer()
        self.pnl.SetSizerAndFit(self.vsizer)

class DataTable(wx.grid.GridTableBase):
    def __init__(self, printdata=None):
        wx.grid.GridTableBase.__init__(self)
        self.headerRows = 1
        if printdata is None: data = pd.DataFrame()
        self.data = printdata

    def GetNumberRows(self):
        return len(self.data)

    def GetNumberCols(self):
        return len(self.data.columns) + 1

    def GetValue(self, row, col):
        if col == 0: return self.data.index[row]
        return self.data.iloc[row, col - 1]

    def SetValue(self, row, col, value):
        self.data.iloc[row, col - 1] = value

    def GetColLabelValue(self, col):
        if col == 0:
            if self.data.index.name is None: return 'Index'
            else: return self.data.index.name
        return str(self.data.columns[col - 1])

def main():
    app = wx.App()
    frm = StartFrame(None)
    frm.Show()
    app.MainLoop()

if __name__ == "__main__":
    main()

您可以 Hide 列 and/or 行,因此这是处理错误的左侧列的简单方法。

Hide 对其他事情也很有用,例如grid.HideRowLabels(),将隐藏左侧那些讨厌的行号。

对齐问题可能可以通过使用 wx.grid.GridCellAttrProvider 来处理,或者您可以简单地遍历设置每个单元格的网格,就像我在下面为简单起见所做的那样。

import wx
import wx.grid
import numpy as np
import pandas as pd

class StartFrame(wx.Frame):
    def __init__(self, parent):
        wx.Frame.__init__(self, parent=parent,
         id=wx.ID_ANY, title="title", size=wx.Size(900,600),
         style=wx.CAPTION|wx.CLOSE_BOX|wx.MINIMIZE_BOX|wx.SYSTEM_MENU|wx.RESIZE_BORDER)
        self.SetSizeHints(wx.DefaultSize, wx.DefaultSize)

        self.numarray=[[1,0.0000,0.071,3.535,3.313,0.22],
                       [10,1.000,0.071,3.535,3.888,-0.353],
                       [20,1.301,0.357,4.634,4.526,0.108],
                       [50,1.699,0.929,6.456,6.442,0.023]]
        self.df = pd.DataFrame(self.numarray, columns=['Parasites/ml','log_qty',
         'probability','probit','est. probit','residual'])

        self.table = DataTable(self.df)
        grid = wx.grid.Grid(self, -1)
        grid.SetTable(self.table, takeOwnership=True)
        # Hide Index column
        grid.HideCol(0)
        grid.HideRowLabels()
        # Alignment of cells
        r = grid.GetNumberRows()
        c = grid.GetNumberCols()
        for row in range(r):
            for cell in range(c):
                grid.SetCellAlignment(row, cell, wx.ALIGN_RIGHT, wx.ALIGN_CENTER)
        grid.AutoSizeColumns()
        self.pnl = wx.Panel(self)
        self.vsizer = wx.BoxSizer(wx.VERTICAL)
        self.hsizer = wx.BoxSizer(wx.HORIZONTAL)

        self.hsizer.AddStretchSpacer()
        self.hsizer.Add(grid, 0, wx.CENTER)
        self.hsizer.AddStretchSpacer()
        self.vsizer.AddStretchSpacer()
        self.vsizer.Add(self.hsizer, wx.SizerFlags().Expand().Border(wx.ALL, 5))
        self.vsizer.AddStretchSpacer()
        self.pnl.SetSizerAndFit(self.vsizer)

class DataTable(wx.grid.GridTableBase):
    def __init__(self, printdata=None):
        wx.grid.GridTableBase.__init__(self)
        self.headerRows = 1
        if printdata is None: data = pd.DataFrame()
        self.data = printdata

    def GetNumberRows(self):
        return len(self.data)

    def GetNumberCols(self):
        return len(self.data.columns) + 1

    def GetValue(self, row, col):
        if col == 0: return self.data.index[row]
        return self.data.iloc[row, col - 1]

    def SetValue(self, row, col, value):
        self.data.iloc[row, col - 1] = value

    def GetColLabelValue(self, col):
        if col == 0:
            if self.data.index.name is None: return 'Index'
            else: return self.data.index.name
        return str(self.data.columns[col - 1])

def main():
    app = wx.App()
    frm = StartFrame(None)
    frm.Show()
    app.MainLoop()

if __name__ == "__main__":
    main()