Reputation: 141
I'm new to PyQt.
I'm trying to put a QTableView in a class, so I can define it's behaviour in the class without mixing it with all the other code, but when I do so it just won't show.
Here's the code i'm learning from. It was borrowed from [ Edit table in pyqt using QAbstractTableModel ]. Readapted it slightly to use with Qt5 and moved the QTableView in a class
import sys
from PyQt5 import QtGui, QtCore
from PyQt5.QtGui import *
from PyQt5.QtWidgets import QMainWindow, QPushButton, QApplication, QVBoxLayout, QTableView, QWidget
from PyQt5.QtCore import *
# données à représenter
my_array = [['00','01','02'],
['10','11','12'],
['20','21','22']]
def main():
app = QApplication(sys.argv)
w = MyWindow()
w.show()
sys.exit(app.exec_())
# création de la vue et du conteneur
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
tablemodel = MyTableModel(my_array, self)
table = Table(tablemodel)
layout = QVBoxLayout(self)
layout.addWidget(table)
self.setLayout(layout)
# création du modèle
class Table(QWidget):
def __init__(self, model):
super().__init__()
self.model = model
self.initUI()
def initUI(self):
self.setMinimumSize(300,300)
self.view = QTableView()
self.view.setModel(self.model)
class MyTableModel(QAbstractTableModel):
def __init__(self, datain, parent = None, *args):
QAbstractTableModel.__init__(self, parent, *args)
self.arraydata = datain
def rowCount(self, parent):
return len(self.arraydata)
def columnCount(self, parent):
return len(self.arraydata[0])
def data(self, index, role):
if not index.isValid():
return None
elif role != Qt.DisplayRole:
return None
return (self.arraydata[index.row()][index.column()])
"""
def setData(self, index, value):
self.arraydata[index.row()][index.column()] = value
return True
def flags(self, index):
return Qt.ItemIsEditable
"""
if __name__ == "__main__":
main()
If I remove the class and use
table = QTableView()
table.setModel(tablemodel)
the table shows no problem.
What am I missing?
Upvotes: 3
Views: 6045
Reputation: 4286
the problem: table.view has no parent. If you add self.view.show()
to test to Table.initUi()
, you get two widgets, MyWindow
with empty table as tmoreau wrote and table.view
as isolated widget.
You can either pass a parent when constructing table.view
in Table.initUi()
self.view = QTableView(self)
(then you don't need a layout) or add table.view to a layout as written by tmoreau, Then the tableview is reparented.
Removing the class has the same effect, then the tableview is added to layout.
Upvotes: 2
Reputation: 6065
You defined Table
as a QWidget
with an attribute self.view=QTableView
.
But you didn't define a layout on Table
, so it will be displayed as an empty widget.
You either have to define a layout for Table
, and add the view to it, or directly add the view to the main window's layout:
class MyWindow(QWidget):
def __init__(self, *args):
QWidget.__init__(self, *args)
tablemodel = MyTableModel(my_array, self)
table = Table(tablemodel)
layout = QVBoxLayout(self)
layout.addWidget(table.view) #add view instead of table
self.setLayout(layout)
A third way is to change the definition of Table
: you could subclass QTableView
instead of QWidget
(code not tested):
class Table(QTableView):
def __init__(self, model, parent):
super(Table,self).__init__(parent)
self.setMinimumSize(300,300)
self.setModel(model)
Upvotes: 2