File indexing completed on 2024-05-12 04:19:48

0001 // vim: set tabstop=4 shiftwidth=4 expandtab:
0002 /*
0003 Gwenview: an image viewer
0004 Copyright 2008 Aurélien Gâteau <agateau@kde.org>
0005 
0006 This program is free software; you can redistribute it and/or
0007 modify it under the terms of the GNU General Public License
0008 as published by the Free Software Foundation; either version 2
0009 of the License, or (at your option) any later version.
0010 
0011 This program is distributed in the hope that it will be useful,
0012 but WITHOUT ANY WARRANTY; without even the implied warranty of
0013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
0014 GNU General Public License for more details.
0015 
0016 You should have received a copy of the GNU General Public License
0017 along with this program; if not, write to the Free Software
0018 Foundation, Inc., 51 Franklin Street, Fifth Floor, Cambridge, MA 02110-1301, USA.
0019 
0020 */
0021 // Self
0022 #include "tagitemdelegate.h"
0023 
0024 // Qt
0025 #include <QAbstractItemView>
0026 #include <QPainter>
0027 #include <QToolButton>
0028 
0029 // KF
0030 #include <KIconLoader>
0031 #include <KLocalizedString>
0032 
0033 // Local
0034 #include "gwenview_lib_debug.h"
0035 #include <lib/semanticinfo/tagmodel.h>
0036 
0037 namespace Gwenview
0038 {
0039 TagItemDelegate::TagItemDelegate(QAbstractItemView *view)
0040     : KWidgetItemDelegate(view, view)
0041 {
0042 #define pm(x) view->style()->pixelMetric(QStyle::x)
0043     mMargin = pm(PM_ToolBarItemMargin);
0044     mSpacing = pm(PM_ToolBarItemSpacing);
0045 #undef pm
0046     const int iconSize = KIconLoader::global()->currentSize(KIconLoader::Toolbar);
0047     const QSize sz = view->style()->sizeFromContents(QStyle::CT_ToolButton, nullptr, QSize(iconSize, iconSize));
0048     mButtonSize = qMax(sz.width(), sz.height());
0049 }
0050 
0051 QList<QWidget *> TagItemDelegate::createItemWidgets(const QModelIndex &index) const
0052 {
0053 #define initButton(x)                                                                                                                                          \
0054     (x)->setAutoRaise(true);                                                                                                                                   \
0055     setBlockedEventTypes((x), QList<QEvent::Type>() << QEvent::MouseButtonPress << QEvent::MouseButtonRelease << QEvent::MouseButtonDblClick);
0056 
0057     Q_UNUSED(index);
0058 
0059     auto assignToAllButton = new QToolButton;
0060     initButton(assignToAllButton);
0061     assignToAllButton->setIcon(QIcon::fromTheme(QStringLiteral("fill-color"))); /* FIXME: Probably not the appropriate icon */
0062     assignToAllButton->setToolTip(i18nc("@info:tooltip", "Assign this tag to all selected images"));
0063     connect(assignToAllButton, &QToolButton::clicked, this, &TagItemDelegate::slotAssignToAllButtonClicked);
0064 
0065     auto removeButton = new QToolButton;
0066     initButton(removeButton);
0067     removeButton->setIcon(QIcon::fromTheme(QStringLiteral("list-remove")));
0068     connect(removeButton, &QToolButton::clicked, this, &TagItemDelegate::slotRemoveButtonClicked);
0069 
0070 #undef initButton
0071 
0072     return QList<QWidget *>() << removeButton << assignToAllButton;
0073 }
0074 
0075 void TagItemDelegate::updateItemWidgets(const QList<QWidget *> &widgets, const QStyleOptionViewItem &option, const QPersistentModelIndex &index) const
0076 {
0077     const bool fullyAssigned = index.data(TagModel::AssignmentStatusRole).toInt() == int(TagModel::FullyAssigned);
0078 
0079     auto removeButton = static_cast<QToolButton *>(widgets[0]);
0080     auto assignToAllButton = static_cast<QToolButton *>(widgets[1]);
0081 
0082     QSize buttonSize(mButtonSize, option.rect.height() - 2 * mMargin);
0083 
0084     removeButton->resize(buttonSize);
0085     assignToAllButton->resize(buttonSize);
0086 
0087     removeButton->move(option.rect.width() - mButtonSize - mMargin, mMargin);
0088 
0089     if (fullyAssigned) {
0090         assignToAllButton->hide();
0091     } else {
0092         assignToAllButton->move(removeButton->x() - mButtonSize - mSpacing, mMargin);
0093     }
0094 }
0095 
0096 void TagItemDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
0097 {
0098     if (!index.isValid()) {
0099         return;
0100     }
0101     const bool selected = option.state & QStyle::State_Selected;
0102     const bool fullyAssigned = index.data(TagModel::AssignmentStatusRole).toInt() == int(TagModel::FullyAssigned);
0103 
0104     itemView()->style()->drawPrimitive(QStyle::PE_PanelItemViewItem, &option, painter, nullptr);
0105 
0106     QRect textRect = option.rect;
0107     textRect.setLeft(textRect.left() + mMargin);
0108     textRect.setWidth(textRect.width() - mButtonSize - mMargin - mSpacing);
0109     if (!fullyAssigned) {
0110         textRect.setWidth(textRect.width() - mButtonSize - mSpacing);
0111     }
0112 
0113     painter->setPen(option.palette.color(QPalette::Normal, selected ? QPalette::HighlightedText : QPalette::Text));
0114     painter->drawText(textRect, Qt::AlignLeft | Qt::AlignVCenter, index.data().toString());
0115 }
0116 
0117 QSize TagItemDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const
0118 {
0119     const int width = option.fontMetrics.boundingRect(index.data().toString()).width();
0120     const int height = qMax(mButtonSize, option.fontMetrics.height());
0121     return QSize(width + 2 * mMargin, height + 2 * mMargin);
0122 }
0123 
0124 void TagItemDelegate::slotRemoveButtonClicked()
0125 {
0126     const QModelIndex index = focusedIndex();
0127     if (!index.isValid()) {
0128         qCWarning(GWENVIEW_LIB_LOG) << "!index.isValid()";
0129         return;
0130     }
0131     Q_EMIT removeTagRequested(index.data(TagModel::TagRole).toString());
0132 }
0133 
0134 void TagItemDelegate::slotAssignToAllButtonClicked()
0135 {
0136     const QModelIndex index = focusedIndex();
0137     if (!index.isValid()) {
0138         qCWarning(GWENVIEW_LIB_LOG) << "!index.isValid()";
0139         return;
0140     }
0141     Q_EMIT assignTagToAllRequested(index.data(TagModel::TagRole).toString());
0142 }
0143 
0144 } // namespace
0145 
0146 #include "moc_tagitemdelegate.cpp"