Qt: use guarded pointer for adding grid items to layout, in case playlist is changed (and hence the items get deleted) before they are all added

This commit is contained in:
Brad Parker 2018-05-07 14:29:54 -04:00
parent 649216c700
commit 03e0510fc4
4 changed files with 31 additions and 16 deletions

View File

@ -55,13 +55,14 @@
#include <QtWidgets>
#include "flowlayout.h"
#include "../ui_qt.h"
FlowLayout::FlowLayout(QWidget *parent, int margin, int hSpacing, int vSpacing)
: QLayout(parent), m_hSpace(hSpacing), m_vSpace(vSpacing)
{
setContentsMargins(margin, margin, margin, margin);
connect(this, SIGNAL(signalAddWidgetDeferred(QWidget*)), this, SLOT(onAddWidgetDeferred(QWidget*)), Qt::QueuedConnection);
connect(this, SIGNAL(signalAddWidgetDeferred(QPointer<ThumbnailWidget>)), this, SLOT(onAddWidgetDeferred(QPointer<ThumbnailWidget>)), Qt::QueuedConnection);
}
FlowLayout::FlowLayout(int margin, int hSpacing, int vSpacing)
@ -226,18 +227,22 @@ int FlowLayout::smartSpacing(QStyle::PixelMetric pm) const
else if (parentObj->isWidgetType())
{
const QWidget *pw = static_cast<const QWidget*>(parentObj);
return pw->style()->pixelMetric(pm, 0, pw);
return pw->style()->pixelMetric(pm, NULL, pw);
}
else
return static_cast<const QLayout*>(parentObj)->spacing();
}
void FlowLayout::addWidgetDeferred(QWidget *widget)
void FlowLayout::addWidgetDeferred(QPointer<ThumbnailWidget> widget)
{
emit signalAddWidgetDeferred(widget);
}
void FlowLayout::onAddWidgetDeferred(QWidget *widget)
void FlowLayout::onAddWidgetDeferred(QPointer<ThumbnailWidget> widget)
{
/* widget might have been deleted before we got to it since this uses a queued connection, hence the guarded QPointer */
if (!widget)
return;
addWidget(widget);
}

View File

@ -63,6 +63,8 @@
#include <QRect>
#include <QStyle>
class ThumbnailWidget;
class FlowLayout : public QLayout
{
Q_OBJECT
@ -83,13 +85,13 @@ public:
void setGeometry(const QRect &rect);
QSize sizeHint() const;
QLayoutItem* takeAt(int index);
void addWidgetDeferred(QWidget *widget);
void addWidgetDeferred(QPointer<ThumbnailWidget> widget);
signals:
void signalAddWidgetDeferred(QWidget *widget);
void signalAddWidgetDeferred(QPointer<ThumbnailWidget> widget);
private slots:
void onAddWidgetDeferred(QWidget *widget);
void onAddWidgetDeferred(QPointer<ThumbnailWidget> widget);
private:
int doLayout(const QRect &rect, bool testOnly) const;

View File

@ -126,7 +126,8 @@ static void scan_finished_handler(void *task_data, void *user_data, const char *
#endif
GridItem::GridItem() :
widget(NULL)
QObject()
,widget(NULL)
,label(NULL)
,hash()
,image()
@ -545,6 +546,8 @@ MainWindow::MainWindow(QWidget *parent) :
QAction *viewTypeListAction = NULL;
int i = 0;
qRegisterMetaType<QPointer<ThumbnailWidget> >("ThumbnailWidget");
viewTypePushButton->setObjectName("viewTypePushButton");
viewTypePushButton->setFlat(true);
@ -2895,13 +2898,13 @@ void MainWindow::removeGridItems()
{
if (m_gridItems.count() > 0)
{
QMutableListIterator<GridItem*> items(m_gridItems);
QMutableVectorIterator<QPointer<GridItem> > items(m_gridItems);
m_pendingItemUpdates.clear();
while (items.hasNext())
{
GridItem *item = items.next();
QPointer<GridItem> item = items.next();
if (item)
{
@ -3003,8 +3006,8 @@ void MainWindow::addPlaylistItemsToGrid(const QString &pathString)
for (i = 0; i < items.count(); i++)
{
const QHash<QString, QString> &hash = items.at(i);
GridItem *item = new GridItem();
ThumbnailLabel *label = NULL;
QPointer<GridItem> item (new GridItem());
QPointer<ThumbnailLabel> label;
QString thumbnailFileNameNoExt;
QLabel *newLabel = NULL;
QSize thumbnailWidgetSizeHint(screenSize.width() / 8, screenSize.height() / 8);

View File

@ -31,6 +31,7 @@
#include <QFutureWatcher>
#include <QPixmap>
#include <QImage>
#include <QPointer>
extern "C" {
#include <retro_common_api.h>
@ -65,12 +66,14 @@ class ThumbnailWidget;
class ThumbnailLabel;
class FlowLayout;
struct GridItem
class GridItem : public QObject
{
Q_OBJECT
public:
GridItem();
ThumbnailWidget *widget;
ThumbnailLabel *label;
QPointer<ThumbnailWidget> widget;
QPointer<ThumbnailLabel> label;
QHash<QString, QString> hash;
QImage image;
QPixmap pixmap;
@ -394,7 +397,7 @@ private:
FlowLayout *m_gridLayout;
QWidget *m_gridWidget;
QScrollArea *m_gridScrollArea;
QList<GridItem*> m_gridItems;
QVector<QPointer<GridItem> > m_gridItems;
QWidget *m_gridLayoutWidget;
QSlider *m_zoomSlider;
int m_lastZoomSliderValue;
@ -406,6 +409,8 @@ protected:
void keyPressEvent(QKeyEvent *event);
};
Q_DECLARE_METATYPE(QPointer<ThumbnailWidget>)
RETRO_BEGIN_DECLS
typedef struct ui_application_qt