Delegate that paint entire widget area
-
Hello everybody, I want ask you help for a problem in model/view paradigm. Above there is a simple code to illustrate my issue. What I want to achieve is to paint 4 rectangles in a list view, but I cannot fill all the space that the listview widget has. It seems that option.widget->width() return the right size available to draw the rects but some space (approx 20 pixels) are reserved always for the scrollbar.
The picture above shows that the rects are too big so the four "icons" are drawn in one column and four rows
This images shows that when I subtract some pixels from the sizeHint function in mydelegate (commented code in line 26 of mydelegate.cpp) the rects fit the area, no scrollbar is created but obviously there is an ugly white vertical line in its place.This is the example code:
#ifndef MAINWINDOW_H #define MAINWINDOW_H #include <QMainWindow> #include "mymodel.h" #include "mydelegate.h" namespace Ui { class MainWindow; } class MainWindow : public QMainWindow { Q_OBJECT public: explicit MainWindow(QWidget *parent = 0); ~MainWindow(); private: Ui::MainWindow *ui; myModel model; myDelegate delegate; }; #endif // MAINWINDOW_H
#include "mainwindow.h" #include "ui_mainwindow.h" MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent), ui(new Ui::MainWindow) { ui->setupUi(this); ui->listView->setModel(&model); ui->listView->setItemDelegate(&delegate); ui->listView->setViewMode(QListView::IconMode); } MainWindow::~MainWindow() { delete ui; }
#ifndef MYMODEL_H #define MYMODEL_H #include <QAbstractListModel> #include <QColor> class myModel : public QAbstractListModel { Q_OBJECT public: explicit myModel(QObject *parent = nullptr); // Basic functionality: int rowCount(const QModelIndex &parent = QModelIndex()) const override; QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override; private: QColor array[4]; }; #endif // MYMODEL_H
#include "mymodel.h" #include <QDebug> myModel::myModel(QObject *parent) : QAbstractListModel(parent) { array[0] = QColor(18,226,240); array[1] = QColor(253,25,151); array[2] = QColor(211,211,211); array[3] = QColor(255,105,105); } int myModel::rowCount(const QModelIndex &parent) const { // For list models only the root node (an invalid parent) should return the list's size. For all // other (valid) parents, rowCount() should return 0 so that it does not become a tree model. if (parent.isValid()) return 0; return 4; } QVariant myModel::data(const QModelIndex &index, int role) const { if (!index.isValid()) return QVariant(); if (role == Qt::UserRole){ int colorIndex = index.row(); return array[colorIndex]; } return QVariant(); }
#ifndef MYDELEGATE_H #define MYDELEGATE_H #include <QStyledItemDelegate> #include <QPainter> class myDelegate : public QStyledItemDelegate { public: myDelegate(); void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const; QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index ) const; }; #endif // MYDELEGATE_H
#include "mydelegate.h" myDelegate::myDelegate() { } void myDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const { painter->save(); QVariant variant = index.data(Qt::UserRole); if ( !variant.isNull() ){ QColor color = variant.value<QColor>(); QRect rect = QRect(option.rect); painter->fillRect(rect,color); } painter->restore(); } QSize myDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const { return QSize( /* -11 + */ option.widget->width() / 2, /* -3 + */ option.widget->height() / 2 ); }
Is option.widget->width() and option.widget->height() the right way to fill the entire widget area?
Thank you all for any tips and support.Edit:
Project zip file. (Link valid until 09/21/17) -
Hi
the images are not visible. -
Hi
Could you try
setHorizontalScrollBarPolicy ( Qt::ScrollBarAlwaysOff );
setVerticalScrollBarPolicy ( Qt::ScrollBarAlwaysOff );and see if it still reserve space?
UPDATE
it is still reserved. -
Hi
Mr @VRonin suggested we looked at
http://doc.qt.io/qt-5/qabstractscrollarea.html#maximumViewportSize
so maybe yo u need to subclass view and return full area.