Reputation: 511
I have C++ Qt 5.2.1 based project and one of graphic component looks like:
+-- ParentWidget == QScrollArea ----------+
| |^|
| +-- MiddleWidget == QWidget -------+ | |
| | (>) Expand/collapse button | | |
| |----------------------------------| | |
| | | | |
| | +-- ChildWidget ---------------+ | | |
| | | ... | | |0|
| | +------------------------------+ | |0|
| | | |0|
| | +-- ChildWidget ---------------+ | |0|
| | | ... | | |0|
| | +------------------------------+ | |0|
| | | |0|
| | ... | |0|
| +----------------------------------+ |0|
| |0|
| +-- MiddleWidget == QWidget -------+ |0|
| | (>) Expand/collapse button | | |
| |----------------------------------| | |
| | | | |
| | +-- ChildWidget ---------------+ | | |
| | | ... | | | |
| | +------------------------------+ | | |
| | | | |
| | +-- ChildWidget ---------------+ | | |
| | | ... | | | |
+-----------------------------------------+
So, ParentWidget is QScrollArea, others are QWidgets. ParentWidget contains some MiddleWidgets, MiddleWidget contains some ChildWidgets. MiddleWidget also can be expanded or collapsed - when collapsed, ChildWidgets are not "visible" (isVisible() == false).
When user scrolls ParentWidget up and down, ChildWidgets which are "visible" (isVisible() == true) can actually be not real visible on screen. ChildWidgets contains pictures, and it's inefficiently to store all pictures in memory. So i want to load picture when ChildWidget is really appears on screen and user sees it; when ChildWidget disappears, picture should be stored to file and erased from memory.
Right now i can check such real visibility changing via ParentWidget:
bool ParentWidget::eventFilter(QObject *object, QEvent *event)
{
if (object == widget() && event->type() == QEvent::Paint) {
for (auto middle : _middles) {
for (auto child : middle->childs()) {
if (!child->visibleRegion().isEmpty()) {
...
}
}
}
}
return QScrollArea::eventFilter(object, event);
}
But this way obviously has its disadvantages:
So my question is: can QWidget catch changing its real visibility state itself? If no, maybe there is more effective way to implement such behaviour?
Upvotes: 4
Views: 1793
Reputation: 22890
can QWidget catch changing its real visibility state itself?
No.
The only real way for a widget to know it is visible is when it executes paintEvent
. But the widget has no way to know it is really not visible.
So i want to load picture when ChildWidget is really appears on screen and user sees it; when ChildWidget disappears, picture should be stored to file and erased from memory.
Did you look at the Graphic view framework? It is designed to efficiently handle a large number of items, and to do it very fast.
Edit: I have never used it, but there is QPixmapCache . You can share a cache between ChildWidget
instances and manage the limit of pixmaps available.
There is a tutorial on how to use a Qpixmap cache.
Upvotes: 4