Search code examples
qtqt4

QListView in gridmode: auto stretch with fixed items on a row / column


I want to make a simple grid with QListView, e.g 3x3, but the gridSize() option in QListView doesn't work that way, it's the width/height of all child widgets in QListView, how should I do that ?


Solution

  • class Widget(QtGui.QWidget):
        def __init__(self):
            super(Widget, self).__init__()
            self.resize(600,400)
            layout = QtGui.QVBoxLayout(self)
            self.list = QtGui.QListWidget()
            self.list.addItems(['item_%d' % i for i in xrange(9)])
            self.list.setViewMode(self.list.IconMode)
            self.list.setResizeMode(self.list.Adjust)
            self.list.installEventFilter(self)
            layout.addWidget(self.list)
    
        def eventFilter(self, obj, event):
            if obj is self.list and event.type() == event.Resize:
                gridsize = self.list.size()/3
                # remove from width to account for the scrollbar
                gridsize.setWidth(gridsize.width()-15)
                self.list.setGridSize(gridsize)
    
            return super(Widget, self).eventFilter(obj, event)
    

    While I had thought the gridSize was the entire list, its actually per cell. The key things here are to set the resize mode to adjust, so that its always re-evaluating the item sizes, and also to keep adjusting the gridSize every time the list widget resizes. In my example, I am using an event filter, but you could also subclass the list and re-implement the resizeEvent.

    The size of the list is divided by 3 and then some padding is removed for the scrollbars. The result is that the items are laid out in 3x width and keep resizing with the view.