Nominate our 2022 Qt Champions!

[SOLVED]QTableModel crashes on headerData

  • I am trying to implement a really simple Table Model inheriting from a QAbstractTableModel which looks like this

    #include <QAbstractTableModel>
    #include <QStringList>
    class ViewModel : public QAbstractTableModel
        ViewModel(QList<QStringList>* mat, QStringList* cnames, QStringList* rnames, QObject *parent=0);
        virtual QVariant headerData (int section, Qt::Orientation orientation, int role = Qt::DisplayRole ) const;
        virtual int rowCount ( const QModelIndex & parent = QModelIndex() ) const;
        virtual int columnCount ( const QModelIndex & parent = QModelIndex() ) const;
        virtual QVariant data ( const QModelIndex & index, int role = Qt::DisplayRole ) const;
    public slots:
        QStringList* colnames;
        QStringList* rownames;
        QList<QStringList>* sourceMat;

    Implemented as

    ViewModel::ViewModel(QList<QStringList>* mat, QStringList* cnames, QStringList* rnames,QObject *parent)
        if(mat->count()!=rnames->count() || mat->at(0).count()!=cnames->count())
        sourceMat = mat;
        colnames = cnames;
        rownames = rnames;
    int ViewModel::rowCount(const QModelIndex &parent ) const
        return sourceMat->count();  //last line is empty
    int ViewModel::columnCount(const QModelIndex &parent ) const
        return sourceMat->at(0).count();
    QVariant ViewModel::headerData(int section,
                Qt::Orientation orientation, int role) const
        if (role != Qt::DisplayRole)
                return QVariant();
        qDebug() << orientation << " " << section;
        if (orientation == Qt::Horizontal)
            return colnames->at(section);
            return rownames->at(section);

    I think the problem is in the headerData as the rownames and colnames are correct the first times the function is called but when the function gets called for a second iteration (I have no idea why) the rownames and colnames are not accessible anymore. Also - the data function is never reached.

    The model is called with a single column and 24 rows and attached to a QTableView

    ViewModel* mod_meta = new ViewModel(mat_meta,&cnamMet,data.rnames);
    QTableView* tview = new QTableView;
    QGridLayout* gl = new QGridLayout;
    delete frame->layout();   // delete previous layout 

  • Lifetime Qt Champion

    @RDiGuida said:
    Hi, is cnamMet and data.rnames part of a class so that they remain valid
    for the life time of the Model?

  • Thanks, that was the problem! I converted the private members into QStringList rather than QStringList*

  • Lifetime Qt Champion

    you made the
    QStringList* colnames;
    QStringList* rownames;
    in ViewModel
    QStringList colnames;
    QStringList rownames;

  • Yes, and I passed the pointer dereferenced.

  • Lifetime Qt Champion

    Ok. it is fine. as you long as you are aware that its
    most likely a copy the model have then.
    so if you change cnamMet or data.rnames in main program, the model
    still uses the original ones. (its copy)

  • @mrjj I know thanks, the only thing that puzzles me is that it works if I keep sourceMat as pointer while it should have the same problems of rownames and colnames.

  • Lifetime Qt Champion

    @RDiGuida said:
    Ok. super.
    Me too.
    In this line
    ViewModel* mod_meta = new ViewModel(mat_meta,&cnamMet,data.rnames);
    the variables cnamMet and data.rnames. where are they declared? (lives) ?

  • cnamMet is declared in the same function where the model is initialised while data.rnames is declared in another class which is initialised outside of the function

  • Lifetime Qt Champion

    Ok, so cnamMet would run out of scope and be deleted (when function ended)
    but sounds like data.rnames should have been working.
    Well if a copy on creation time works for you, its a wrap :)

Log in to reply