File indexing completed on 2024-05-05 16:27:56

0001 /* SPDX-FileCopyrightText: 2003-2020 The KPhotoAlbum Development Team
0002 
0003    SPDX-License-Identifier: GPL-2.0-or-later
0004 */
0005 #include "CenteringIconView.h"
0006 
0007 #include <Utilities/BooleanGuard.h>
0008 #include <Utilities/FileUtil.h>
0009 #include <kpabase/SettingsData.h>
0010 
0011 #include <QApplication>
0012 #include <cmath>
0013 
0014 const int CELLWIDTH = 200;
0015 const int CELLHEIGHT = 150;
0016 
0017 Browser::CenteringIconView::CenteringIconView(QWidget *parent)
0018     : QListView(parent)
0019     , m_viewMode(NormalIconView)
0020 {
0021     setGridSize(QSize(CELLWIDTH, CELLHEIGHT));
0022     viewport()->setAutoFillBackground(false);
0023 
0024     QListView::setViewMode(QListView::IconMode);
0025 }
0026 
0027 void Browser::CenteringIconView::setViewMode(ViewMode viewMode)
0028 {
0029     m_viewMode = viewMode;
0030     if (viewMode == CenterView) {
0031         setGridSize(QSize(200, 150));
0032         setupMargins();
0033     } else {
0034         setGridSize(QSize());
0035         setViewportMargins(0, 0, 0, 0);
0036     }
0037 }
0038 
0039 void Browser::CenteringIconView::setupMargins()
0040 {
0041     if (m_viewMode == NormalIconView || !model() || !viewport())
0042         return;
0043 
0044     // In this code I'll call resize, which calls resizeEvent, which calls
0045     // this code. So I need to break that loop, which I do here.
0046     static bool inAction = false;
0047     Utilities::BooleanGuard guard(inAction);
0048     if (!guard.canContinue())
0049         return;
0050 
0051     const int count = model()->rowCount();
0052     if (count == 0)
0053         return;
0054 
0055     const int columns = columnCount(count);
0056     const int rows = std::ceil(1.0 * count / columns);
0057 
0058     const int xMargin = (availableWidth() - columns * CELLWIDTH) / 2;
0059     const int yMargin = qMax(0, (int)(availableHeight() - rows * CELLHEIGHT) / 2);
0060 
0061     setViewportMargins(xMargin, yMargin, xMargin, yMargin);
0062 }
0063 
0064 void Browser::CenteringIconView::resizeEvent(QResizeEvent *event)
0065 {
0066     QListView::resizeEvent(event);
0067     setupMargins();
0068 }
0069 
0070 void Browser::CenteringIconView::setModel(QAbstractItemModel *model)
0071 {
0072     QListView::setModel(model);
0073     setupMargins();
0074 }
0075 
0076 void Browser::CenteringIconView::showEvent(QShowEvent *event)
0077 {
0078     setupMargins();
0079     QListView::showEvent(event);
0080 }
0081 
0082 int Browser::CenteringIconView::columnCount(int elementCount) const
0083 {
0084     const int preferredCount = std::ceil(std::sqrt(elementCount));
0085     const int maxVisibleColumnsPossible = availableWidth() / CELLWIDTH;
0086     const int maxVisibleRowsPossible = qMax(1, availableHeight() / CELLHEIGHT);
0087     const int colCountToMakeAllRowVisible = std::ceil(1.0 * elementCount / maxVisibleRowsPossible);
0088 
0089     int res = preferredCount;
0090     res = qMax(res, colCountToMakeAllRowVisible); // Should we go for more due to limited row count?
0091     res = qMin(res, maxVisibleColumnsPossible); // No more than maximal visible count
0092     res = qMax(res, 1); // at least 1
0093     return res;
0094 }
0095 
0096 int Browser::CenteringIconView::availableWidth() const
0097 {
0098     // The 40 and 10 below are some magic numbers. I think the reason I
0099     // need them is that the viewport doesn't cover all of the list views area.
0100     return width() - 40;
0101 }
0102 
0103 int Browser::CenteringIconView::availableHeight() const
0104 {
0105     return height() - 10;
0106 }
0107 
0108 // vi:expandtab:tabstop=4 shiftwidth=4:
0109 
0110 #include "moc_CenteringIconView.cpp"