I want to use QGraphicsView to write a resource browser. It's slightly different from the example using QGraphicsView and QGraphicsItems because I just want to have a scrollbar and I want the item to be able to move automatically when the viewport size changes. For example, when the viewport width is large enough to display 4 assets, they should be displayed like this:
aaaa
aaaa
aa
But when the viewport is reduced and can only hold 3 in a row, it should show up like this:
aaa
aaa
aaa
a
Instead of moving these assets myself, I want to let the graphical view manage them. Is this possible?
I've written something like this once, but using QWidget and paintEvent, draw all the assets yourself and track how many assets can be displayed in a row. Can it be done easier with QGraphicsView?
Solution
Method 1: Use QGraphicsFlowLayout
QGraphicsView supports layout. What you need to do is implement your own layout manager, inherited from QGraphicsLayout.
For the layout you need, check out Qt's flow layout example. Converting this example will give you a QGraphicsFlowLayout. Add your QGraphicsItems to this layout and set the layout of your QGraphicsView to that layout, which will do the job.
Method 2: Use QListWidget
It sounds like you want a list, not a graphical view. You can set the list to display content that wraps the line like you want. See the puzzle example, note the list of puzzle pieces on the left. For the proposed situation, it is very simple to set up.
Of course, if you really want to implement it in a graphical view, I think you can add a list to the view and use it there.
Code Example
from import QRectF from import QBrush, QColor, QPen from import QApplication, QGraphicsItem, QGraphicsRectItem, QGraphicsScene, QGraphicsView, QVBoxLayout, QWidget class QGraphicsFlowLayout(QGraphicsLayout): def __init__(self): super().__init__() self.item_list = [] def addItem(self, item): self.item_list.append(item) def count(self): return len(self.item_list) def itemAt(self, index): return self.item_list[index] def takeAt(self, index): item = self.item_list.pop(index) return item def boundingRect(self): rect = QRectF() for item in self.item_list: rect |= () return rect def sizeHint(self, which, constraint): return ().size() def minimumSize(self): return (, QSizeF()) def preferredSize(self): return (, QSizeF()) def get_row_width(self): row_width = 0 for item in self.item_list: row_width += ().width() return row_width def get_row_height(self): row_height = 0 for item in self.item_list: row_height = max(row_height, ().height()) return row_height def get_num_rows(self, view_width): row_width = self.get_row_width() num_rows = 1 if row_width > view_width: num_rows = row_width // view_width + 1 return num_rows def get_row_spacing(self): return 10 def get_column_spacing(self): return 10 def get_item_position(self, item, row, column): x = column * (().width() + self.get_column_spacing()) y = row * (().height() + self.get_row_spacing()) return QPointF(x, y) def setGeometry(self, rect): view_width = () num_rows = self.get_num_rows(view_width) row_height = self.get_row_height() for i, item in enumerate(self.item_list): row = i // num_rows column = i % num_rows pos = self.get_item_position(item, row, column) (pos) class QGraphicsFlowView(QGraphicsView): def __init__(self): super().__init__() = QGraphicsScene(self) = QGraphicsFlowLayout() () ( | ) () def add_item(self, item): (item) def resizeEvent(self, event): super().resizeEvent(event) (()) class QGraphicsFlowItem(QGraphicsRectItem): def __init__(self, color): super().__init__() (0, 0, 100, 100) (QBrush(color)) (QPen(QColor(0, 0, 0), 1)) if __name__ == "__main__": app = QApplication([]) view = QGraphicsFlowView() view.add_item(QGraphicsFlowItem(QColor(255, 0, 0))) view.add_item(QGraphicsFlowItem(QColor(0, 255, 0))) view.add_item(QGraphicsFlowItem(QColor(0, 0, 255))) view.add_item(QGraphicsFlowItem(QColor(255, 255, 0))) view.add_item(QGraphicsFlowItem(QColor(255, 0, 255))) view.add_item(QGraphicsFlowItem(QColor(0, 255, 255))) () app.exec_()
This is the end of this article about the implementation of pandas using QGraphicsView to automatically arrange items. For more related pandas QGraphicsView to automatically arrange content, please search for my previous articles or continue browsing the related articles below. I hope everyone will support me in the future!