如何自动拉伸 QTableView 列并保持它们可调整
How to auto stretch QTableView columns and keep them being adjustable
我真的很喜欢使用
自动调整到QTableView
的列宽的干净结果:
self.view.horizontalHeader().setResizeMode(QHeaderView.Stretch)
但不幸的是,使用此标志后,列宽不再保持可调(用户无法调整列宽)。
我想知道是否有其他方法可以将列宽设置为 QTableView
的宽度,同时保持列宽 "user-adjustable"?
from PyQt4.QtCore import *
from PyQt4.QtGui import *
import sys
class Model(QAbstractTableModel):
def __init__(self, parent=None, *args):
QAbstractTableModel.__init__(self, parent, *args)
self.items = ['Item_A_001','Item_A_002','Item_B_001','Item_B_002']
self.totalColumn=10
def rowCount(self, parent=QModelIndex()):
return len(self.items)
def columnCount(self, parent=QModelIndex()):
return self.totalColumn
def setColumnCount(self, number):
self.totalColumn=number
self.reset()
def data(self, index, role):
if not index.isValid(): return QVariant()
elif role != Qt.DisplayRole:
return QVariant()
row=index.row()
if row<len(self.items):
return QVariant(self.items[row])
else:
return QVariant()
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
tableModel=Model(self)
self.view=QTableView(self)
self.view.setModel(tableModel)
self.view.horizontalHeader().setResizeMode(QHeaderView.Stretch)
hideButton=QPushButton('Hide Column')
hideButton.clicked.connect(self.hideColumn)
unhideButton=QPushButton('Unhide Column')
unhideButton.clicked.connect(self.unhideColumn)
layout = QVBoxLayout(self)
layout.addWidget(self.view)
layout.addWidget(hideButton)
layout.addWidget(unhideButton)
self.setLayout(layout)
def hideColumn(self):
self.view.model().setColumnCount(1)
def unhideColumn(self):
self.view.model().setColumnCount(10)
if __name__ == "__main__":
app = QApplication(sys.argv)
w = MyWindow()
w.show()
sys.exit(app.exec_())
所以这是我想出的一个小技巧。我修改了 MyWindow 的调整大小事件来调整你的 QTableWidget。
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
self.tableModel=Model(self) #Set the model as part of your class to access it in the event handler
self.view=QTableView(self)
self.view.setModel(self.tableModel) #Modified here too
self.view.horizontalHeader().setResizeMode(QHeaderView.Interactive) #Mode set to Interactive to allow resizing
hideButton=QPushButton('Hide Column')
hideButton.clicked.connect(self.hideColumn)
unhideButton=QPushButton('Unhide Column')
unhideButton.clicked.connect(self.unhideColumn)
layout = QVBoxLayout(self)
layout.addWidget(self.view)
layout.addWidget(hideButton)
layout.addWidget(unhideButton)
self.setLayout(layout)
def hideColumn(self):
self.view.model().setColumnCount(1)
def unhideColumn(self):
self.view.model().setColumnCount(10)
#Added a reimplementation of the resize event
def resizeEvent(self, event):
tableSize = self.view.width() #Retrieves your QTableView width
sideHeaderWidth = self.view.verticalHeader().width() #Retrieves the left header width
tableSize -= sideHeaderWidth #Perform a substraction to only keep all the columns width
numberOfColumns = self.tableModel.columnCount() #Retrieves the number of columns
for columnNum in range( self.tableModel.columnCount()): #For each column
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) ) #Set the width = tableSize / nbColumns
super(MyWindow, self).resizeEvent(event) #Restores the original behaviour of the resize event
唯一的缺点是滚动条闪烁。我认为这可以通过一些调整来解决。
更新:
调整大小时外观更清晰,不再闪烁,禁用滚动条。
修改了QTableView的初始化:
self.view=QTableView(self)
self.view.setModel(self.tableModel)
self.view.horizontalHeader().setResizeMode(QHeaderView.Interactive)
#Added these two lines
self.view.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
self.view.horizontalHeader().setStretchLastSection(True)
修改后的resizeEvent:
def resizeEvent(self, event):
super(MyWindow, self).resizeEvent(event)
tableSize = self.view.width()
sideHeaderWidth = self.view.verticalHeader().width()
tableSize -= sideHeaderWidth
numberOfColumns = self.tableModel.columnCount()
remainingWidth = tableSize % numberOfColumns
for columnNum in range( self.tableModel.columnCount()):
if remainingWidth > 0:
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) + 1 )
remainingWidth -= 1
else:
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) )
我真的很喜欢使用
自动调整到QTableView
的列宽的干净结果:
self.view.horizontalHeader().setResizeMode(QHeaderView.Stretch)
但不幸的是,使用此标志后,列宽不再保持可调(用户无法调整列宽)。
我想知道是否有其他方法可以将列宽设置为 QTableView
的宽度,同时保持列宽 "user-adjustable"?
from PyQt4.QtCore import *
from PyQt4.QtGui import *
import sys
class Model(QAbstractTableModel):
def __init__(self, parent=None, *args):
QAbstractTableModel.__init__(self, parent, *args)
self.items = ['Item_A_001','Item_A_002','Item_B_001','Item_B_002']
self.totalColumn=10
def rowCount(self, parent=QModelIndex()):
return len(self.items)
def columnCount(self, parent=QModelIndex()):
return self.totalColumn
def setColumnCount(self, number):
self.totalColumn=number
self.reset()
def data(self, index, role):
if not index.isValid(): return QVariant()
elif role != Qt.DisplayRole:
return QVariant()
row=index.row()
if row<len(self.items):
return QVariant(self.items[row])
else:
return QVariant()
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
tableModel=Model(self)
self.view=QTableView(self)
self.view.setModel(tableModel)
self.view.horizontalHeader().setResizeMode(QHeaderView.Stretch)
hideButton=QPushButton('Hide Column')
hideButton.clicked.connect(self.hideColumn)
unhideButton=QPushButton('Unhide Column')
unhideButton.clicked.connect(self.unhideColumn)
layout = QVBoxLayout(self)
layout.addWidget(self.view)
layout.addWidget(hideButton)
layout.addWidget(unhideButton)
self.setLayout(layout)
def hideColumn(self):
self.view.model().setColumnCount(1)
def unhideColumn(self):
self.view.model().setColumnCount(10)
if __name__ == "__main__":
app = QApplication(sys.argv)
w = MyWindow()
w.show()
sys.exit(app.exec_())
所以这是我想出的一个小技巧。我修改了 MyWindow 的调整大小事件来调整你的 QTableWidget。
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
self.tableModel=Model(self) #Set the model as part of your class to access it in the event handler
self.view=QTableView(self)
self.view.setModel(self.tableModel) #Modified here too
self.view.horizontalHeader().setResizeMode(QHeaderView.Interactive) #Mode set to Interactive to allow resizing
hideButton=QPushButton('Hide Column')
hideButton.clicked.connect(self.hideColumn)
unhideButton=QPushButton('Unhide Column')
unhideButton.clicked.connect(self.unhideColumn)
layout = QVBoxLayout(self)
layout.addWidget(self.view)
layout.addWidget(hideButton)
layout.addWidget(unhideButton)
self.setLayout(layout)
def hideColumn(self):
self.view.model().setColumnCount(1)
def unhideColumn(self):
self.view.model().setColumnCount(10)
#Added a reimplementation of the resize event
def resizeEvent(self, event):
tableSize = self.view.width() #Retrieves your QTableView width
sideHeaderWidth = self.view.verticalHeader().width() #Retrieves the left header width
tableSize -= sideHeaderWidth #Perform a substraction to only keep all the columns width
numberOfColumns = self.tableModel.columnCount() #Retrieves the number of columns
for columnNum in range( self.tableModel.columnCount()): #For each column
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) ) #Set the width = tableSize / nbColumns
super(MyWindow, self).resizeEvent(event) #Restores the original behaviour of the resize event
唯一的缺点是滚动条闪烁。我认为这可以通过一些调整来解决。
更新: 调整大小时外观更清晰,不再闪烁,禁用滚动条。
修改了QTableView的初始化:
self.view=QTableView(self)
self.view.setModel(self.tableModel)
self.view.horizontalHeader().setResizeMode(QHeaderView.Interactive)
#Added these two lines
self.view.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
self.view.horizontalHeader().setStretchLastSection(True)
修改后的resizeEvent:
def resizeEvent(self, event):
super(MyWindow, self).resizeEvent(event)
tableSize = self.view.width()
sideHeaderWidth = self.view.verticalHeader().width()
tableSize -= sideHeaderWidth
numberOfColumns = self.tableModel.columnCount()
remainingWidth = tableSize % numberOfColumns
for columnNum in range( self.tableModel.columnCount()):
if remainingWidth > 0:
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) + 1 )
remainingWidth -= 1
else:
self.view.setColumnWidth(columnNum, int(tableSize/numberOfColumns) )