【发布时间】:2019-12-27 12:49:22
【问题描述】:
我正在使用 pyqt 进行模型/视图编程以尝试理解它。 我的问题是,当我从已选择的项目组中尝试 si select in item 时,不会触发 onSelection changed 事件,并且选择行为变得很奇怪。 (不仅不能从先前选择的项目中选择项目,而且还会发生连续的选择......)。
如果我评论 def data(self, _index, role=Qt.DisplayRole): 方法,我会得到我想要的行为,所以我想我在表格中填充数据的方式上遗漏了一些东西。但是,如果已对此进行注释,我将无法在表中填充数据(您好 :))。
我尝试使用 onMouseClick 事件和选择行为来处理它,但没有成功。 我想要的选择行为也可以在这个例子中找到: https://wiki.python.org/moin/PyQt/Reading%20selections%20from%20a%20selection%20model
在我的代码下方查找,这可能有点混乱,因为我只是在进行一些试验(对此感到抱歉)。 任何意见将不胜感激,非常感谢。
from PyQt5.QtWidgets import QApplication, QTableView, QAbstractItemView
import sys
from PyQt5.QtCore import QAbstractTableModel, Qt, QModelIndex, QItemSelection, QItemSelectionModel, QAbstractItemModel
class myTableModel(QAbstractTableModel):
def __init__(self, rows, columns, parent=None, *args):
QAbstractTableModel.__init__(self, parent, *args)
self.rowCount = rows
self.columnCount = columns
self.table_data = [[None] * columns for _ in range(rows)]
self.unselectedItems = []
def rowCount(self, parent):
return self.rowCount
def columnCount(self, parent):
return self.columnCount
def flags(self, index):
return Qt.ItemIsEditable | Qt.ItemIsEnabled | Qt.ItemIsSelectable
def data(self, _index, role=Qt.DisplayRole):
if role == Qt.DisplayRole and _index.isValid():
row = _index.row()
column = _index.column()
item = _index.internalPointer()
if item is not None:
print(item)
value = self.table_data[row][column]
# print('value returned: ' + str(value) + ' row: ' + str(row) + ' col: ' + str(column))
return value
else:
return None
def setData(self, _index, value, role=Qt.EditRole):
if role == Qt.EditRole and _index.isValid():
# print(_index.row())
# self.arraydata[index.row()] = [value]
# print('Return from rowCount: {0}'.format(self.rowCount(index)))
row = _index.row()
column = _index.column()
self.table_data[row][column] = value
self.dataChanged.emit(_index, _index)
return True
return QAbstractTableModel.setData(self, index, value, role)
def updateSelection(self, selected, deselected):
selectedItems = selected.indexes()
for _index in selectedItems:
_text = f"({_index.row()}, {_index.column()})"
self.setData(_index, _text)
del selectedItems[:]
self.unselectedItems = deselected.indexes()
for _index in self.unselectedItems:
_text = "previous selection"
self.setData(_index, _text)
print('unselected item: ' + str(_index))
class myTableView(QTableView):
def __init__(self, rowCount, columnCount, model):
super().__init__()
self.rowCount = rowCount
self.columnCount = columnCount
self.model = model
self.setModel(model)
self.selectionModel().selectionChanged.connect(tblModel.updateSelection)
self.setSelectionMode(QAbstractItemView.ContiguousSelection)
def mouseReleaseEvent(self, event):
if event.button() == Qt.LeftButton:
selectedItems = self.selectedIndexes()
allIndexes = []
for i in range(self.rowCount):
for j in range(self.columnCount):
allIndexes.append(self.model.index(i, j))
# print('all indexes appended')
indexesToClear = [_index for _index in allIndexes if
_index not in selectedItems and _index not in self.model.unselectedItems]
for _index in indexesToClear:
valueFromIndex = str(self.model.data(_index, Qt.DisplayRole))
if valueFromIndex == "previous selection":
self.model.setData(_index, "")
# def mousePressEvent(self, event):
# if event.button() == Qt.LeftButton:
# self.selectionModel().reset()
app = QApplication(sys.argv)
tblModel = myTableModel(8, 4, app) # create table model
tblView = myTableView(8, 4, tblModel)
topLeft = tblModel.index(0, 0, QModelIndex())
bottomRight = tblModel.index(5, 2, QModelIndex())
selectionMode = tblView.selectionModel()
selection = QItemSelection(topLeft, bottomRight)
selectionMode.select(selection, QItemSelectionModel.Select)
# set selected indexes text to selection
indexes = selectionMode.selectedIndexes()
for index in indexes:
text = str(index.row()) + str(index.column())
tblModel.setData(index, text, role=Qt.EditRole)
tblView.show()
app.exec()
【问题讨论】:
标签: python pyqt pyqt5 tableview