Adding A QComboBox to the header of QtreeView having multiple columns and a custom model



  • Is it possible to add a QComboBox in the header item of the Qtreeview class backed up by a custom model. I have headerData overriden in the model and against the Qt:DisplayRole label text are returned back as QVariant. I am also able to add an Icon on the header using Qt:DecorationRole. How do I add a ComboBox??
    Please help


  • Lifetime Qt Champion

    Hi and welcome to DevNet,

    A quick google search turned "this":http://blog.qt.digia.com/blog/2012/09/28/qt-support-weekly-27-widgets-on-a-header/ up.

    Hope it helps



  • Thanks a lot SGaist...
    That really helped.
    For others that are trying to do the same, I am posting the sample code.

    @#ifndef MAINWINDOW_H
    #define MAINWINDOW_H

    #include <QMainWindow>
    #include <QComboBox>
    #include <QGridLayout>
    #include <QCheckBox>
    #include <QTableView>
    #include <QStyledItemDelegate>
    #include <QHeaderView>

    #include <QtGui>
    #include <QLabel>
    #include <QDebug>

    class MainWindow : public QMainWindow
    {
    Q_OBJECT

    public:
    MainWindow(QWidget *parent = 0);
    ~MainWindow();
    };

    class HeaderObject : public QWidget{
    Q_OBJECT
    public:
    HeaderObject(QWidget *parent = 0) : QWidget(parent){
    QComboBox *c = new QComboBox(this);
    // QCheckBox cb = new QCheckBox(this);
    QLabel
    objLabel = new QLabel();
    objLabel->setText("Testy");
    c->addItem("test");
    c->addItem("test2");
    QHBoxLayout *h = new QHBoxLayout;
    //l->addWidget(c);
    // l->addWidget(cb);
    h->addWidget(objLabel);
    h->addWidget(c);
    setLayout(h);
    }
    };

    class CustomModel : public QAbstractTableModel{
    Q_OBJECT
    public:
    CustomModel() : QAbstractTableModel(){
    }

    int rowCount(const QModelIndex &parent = QModelIndex()) const{return 5;}
    int columnCount(const QModelIndex &parent = QModelIndex()) const {return 5;}
    QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const{
        if (role == Qt::DisplayRole) return QVariant();
        return QVariant();
    }
    
    QVariant headerData(int section,
                                             Qt::Orientation orientation, int role) const
    {
        qDebug() << "CSapActvtyTreeModel::headerData" << endl;
        if (orientation == Qt::Horizontal && role == Qt::DisplayRole) {
            return QVariant();
        }
        return QAbstractTableModel::headerData(section,orientation,role);
    }
    

    private:
    };

    class CustomHeader : public QHeaderView{
    Q_OBJECT
    public Q_SLOTS:
    void handleSectionResized(int i)
    {
    qDebug() << "HandleSectionResized :" << i;
    for (int j = i; j<5;j++) {
    int logical = j;
    headerSections[logical]->setGeometry(sectionViewportPosition(logical), 0,
    sectionSize(logical) - 5, height());
    }
    }

    void handleSectionMoved(int logical, int oldVisualIndex, int newVisualIndex)
    {
        int ilogicalIndex = logical;
        for (int i=qMin(oldVisualIndex, newVisualIndex);i<count();i++){
            ilogicalIndex = logicalIndex(i);
            headerSections[ilogicalIndex]->setGeometry(sectionViewportPosition(ilogicalIndex), 0,
                                           sectionSize(ilogicalIndex) - 5, height());
        }
    }
    

    public:
    CustomHeader(QWidget *parent = 0):QHeaderView(Qt::Horizontal, parent){

        for(int i = 0; i<5; i++){
            headerSections.insert(i,new HeaderObject(this));
            headerSections[i]->hide();
        }
    
        setMinimumSectionSize(headerSections[0]->minimumSizeHint().width());
        setDefaultSectionSize(headerSections[0]->minimumSizeHint().width());
        setSectionsMovable(true);
        connect(this, SIGNAL(sectionResized(int,int,int)), this,
                    SLOT(handleSectionResized(int)));
    
    }
    

    protected:
    void paintSection(QPainter *painter, const QRect &rect, int logicalIndex) const {
    if (!rect.isValid())
    return;
    //qDebug() << logicalIndex;
    //qDebug() << "QRect: " << rect << " AND OFFSET:" << offset();
    // headerSections[logicalIndex]->setGeometry(rect);
    // headerSections[logicalIndex]->show();
    QHeaderView::paintSection(painter,rect,logicalIndex);
    }

    void showEvent(QShowEvent *e)
    {
        for (int i=0;i<5;i++) {
           headerSections[i]->setGeometry(sectionViewportPosition(i), 0,
                                                     sectionSize(i) - 5, height());
           headerSections[i]->show();
        }
        QHeaderView::showEvent(e);
     }
    
    QSize sizeHint() const {
        QSize s = size();
        s.setHeight(headerSections[0]->minimumSizeHint().height());
        return s;
    }
    

    private:
    mutable QVector< QPointer <HeaderObject> > headerSections;
    };

    /// The call
    int main(int argc, char *argv[])
    {
    QApplication a(argc, argv);

    CustomModel *model = new CustomModel;
    QTableView *view = new QTableView();
    view->setModel(model);
    
    view->setHorizontalHeader(new CustomHeader(view));
    view->show();
    return a.exec&#40;&#41;;
    

    }

    @

    Please note here that you will need to update the header positions in the overriden method
    void scrollContentsBy(int dx, int dy) so that when you scroll the headers also scroll



  • hi prady_80
    i m trying similar solution i m new to Qt could you please post full owrking soltion where event can be handle for each of combox .and apply filter model..



  • hi prady_80
    i m trying similar solution i m new to Qt could you please post full owrking soltion where event can be handle for each of combox .and apply filter model..



  • Hi,
    I have put a Git for you.
    Pull the sample from there. I suggest you build a complex realistic model, modify with filter proxy to handle complexity and then learn. That way you will have a better understanding of Qt Model-View architecture.
    Hope it helps.
    "Git link":https://github.com/PSaraph/Qt-Header-view-combo.git
    Happy learning



  • Hi,
    I have put a Git for you.
    Pull the sample from there. I suggest you build a complex realistic model, modify with filter proxy to handle complexity and then learn. That way you will have a better understanding of Qt Model-View architecture.
    Hope it helps.
    "Git link":https://github.com/PSaraph/Qt-Header-view-combo.git
    Happy learning


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.