[PyQt] Can't get QCheckBox to work in a QTableView

Chris Dunscombe cdunscombe at yahoo.com
Mon Nov 26 12:13:24 GMT 2007


--- Andreas Pakulat <apaku at gmx.de> wrote:

> On 23.11.07 09:04:56, Chris Dunscombe wrote:
> > Hi,
> > 
> > I'm trying to have a checkable column plus label with other columns in a table. I can't use
> > QTableWidget as one of the other columns is a ComboBox. After much trying, googling and
> reading of
> > Mark's excellent new book I just can't get it to work. I'm clearly doing something wrong
> > 
> > Main problem is that the label doesn't display unless it's being clicked. Also I can't check
> the
> > checkbox unless I've previously double-clicked in the area where the label is.
> 
> Why do you try to use a QCheckBox in the first place? Just return the
> Qt::IsUserCheckable flag in flags() and react to the Qt::CheckStateRole
> in data() for the apropriate column. Then the view itself will add a
> checkbox to the column and display the text from data(). Works like a
> charm.
> 
> Anyway, some comments...
> 
> > class myModel(QStandardItemModel):
> 
> This is wrong, you're misuing the standard item model. Please read its
> API docs, its usually not needed to subclass it, you only need to create
> QStandardItem's for the various cells in your model and set them
> checkable if they should be checkable.
> 
> If you want to write your own model, because you have some custom/legacy
> data format use QAbstractTableModel as base (when its tabular data) or
> QAbstractItemModel (if its tree-like data).
> 
> Andreas
> 
> -- 

Andreas,

Thanks very much for your reply. I've tried again, using QAbstractTableModel and without a custom
ItemDelegate, but I still can't get it to work.

Do I need to use a custom ItemDelegate given I don't need a QCheckBox but use
Qt.ItemIsUserCheckable from flags()?

I just can't seem to get my head around this. If you could include some code as a simple example
that would be greatly appreciated.

Anyway here's my latest code, where I've tried to implement your comments, but this just gives an
empty box not even two cells which I'd have expected as a minimum.

Any help from anyone else is also appreciated.

Thanks,

Chris 

Code

#!/usr/bin/env python

import sys, os
print os.environ["PYTHONPATH"]
print sys.version
from PyQt4.QtCore import *
from PyQt4.QtGui import *

class window(QWidget):
    def __init__(self, parent = None, myList = None):
        QWidget.__init__(self, parent)

        self.colsTable = myTableView(parent = self, numRows = 2, dataObj = myList)
        mainLayout = QHBoxLayout()
        mainLayout.addWidget(self.colsTable)
        self.setLayout(mainLayout)
        index1 = self.colsTable.model.index(0, 0, QModelIndex())
        self.colsTable.model.setData(index1,Qt.Checked ,Qt.CheckStateRole)

class myTableView(QTableView):

    def __init__(self, parent = None, numRows = 0, dataObj = None):
        super(myTableView, self).__init__(parent)
        self.dataObj = dataObj

        # Setup the model
        self.model = myModel(dataObj = dataObj)

        self.setModel(self.model)
        # Add the single column
        self.model.insertColumn(0)

        # Add the rows
        for dummy in range(numRows):
            self.model.insertRow(0)

class myModel(QAbstractTableModel):

    def __init__(self, parent=None, dataObj = None):
        super(myModel, self).__init__(parent)
        self.dataObj = dataObj


    def data(self, index, role=Qt.DisplayRole):

        if role == Qt.CheckStateRole:
            if self.dataObj[index.row()] == 0:
                return QVariant(Qt.Unchecked)
            else:
                return QVariant(Qt.Checked)
        else:
            return QVariant()


    def setData(self, index, value, role):

        if role == Qt.CheckStateRole:
            if value == Qt.Checked:
                self.dataObj[index.row()] = 1
            else:
                self.dataObj[index.row()] = 0
        else:
            print "Set data with no CheckStateRole"

        self.emit(SIGNAL("dataChanged(QModelIndex,QModelIndex)"),index, index)
        return True

    def flags(self, index):
        if index.column() == 0:
            return Qt.ItemIsEnabled | Qt.ItemIsEditable | Qt.ItemIsUserCheckable |
Qt.ItemIsSelectable
        else:
            return Qt.ItemIsEnabled

myList = []
myList.append(0)
myList.append(1)

a = QApplication(sys.argv)
w = window(myList = myList)
w.show()
sys.exit(a.exec_())




      ____________________________________________________________________________________
Get easy, one-click access to your favorites. 
Make Yahoo! your homepage.
http://www.yahoo.com/r/hs 


More information about the PyQt mailing list