1 /*
2   SPDX-FileCopyrightText: 2013-2021 Laurent Montel <montel@kde.org>
3 
4   SPDX-License-Identifier: GPL-2.0-or-later
5 */
6 
7 #include "checkedcollectionwidget.h"
8 #include <Akonadi/CollectionFilterProxyModel>
9 
10 #include <Akonadi/EntityTreeModel>
11 #include <Akonadi/Monitor>
12 #include <QSortFilterProxyModel>
13 
14 #include <KCheckableProxyModel>
15 #include <KLocalizedString>
16 #include <QLineEdit>
17 
18 #include <QTreeView>
19 #include <QVBoxLayout>
20 
21 using namespace PimCommon;
22 
23 class PimCommon::CheckedCollectionWidgetPrivate
24 {
25 public:
CheckedCollectionWidgetPrivate()26     CheckedCollectionWidgetPrivate()
27     {
28     }
29 
30     QTreeView *mFolderView = nullptr;
31     QItemSelectionModel *mSelectionModel = nullptr;
32     KCheckableProxyModel *mCheckProxy = nullptr;
33     QSortFilterProxyModel *mCollectionFilter = nullptr;
34 
35     Akonadi::EntityTreeModel *mEntityTreeModel = nullptr;
36 };
37 
CheckedCollectionWidget(const QString & mimetype,QWidget * parent)38 CheckedCollectionWidget::CheckedCollectionWidget(const QString &mimetype, QWidget *parent)
39     : QWidget(parent)
40     , d(new PimCommon::CheckedCollectionWidgetPrivate)
41 {
42     auto vbox = new QVBoxLayout(this);
43     vbox->setContentsMargins({});
44 
45     // Create a new change recorder.
46     auto monitor = new Akonadi::Monitor(this);
47     monitor->setObjectName(QStringLiteral("CheckedCollectionWidgetMonitor"));
48     monitor->fetchCollection(true);
49     monitor->setAllMonitored(true);
50     monitor->setMimeTypeMonitored(mimetype);
51     connect(monitor, &Akonadi::Monitor::collectionAdded, this, &CheckedCollectionWidget::collectionAdded);
52     connect(monitor, &Akonadi::Monitor::collectionRemoved, this, &CheckedCollectionWidget::collectionRemoved);
53 
54     d->mEntityTreeModel = new Akonadi::EntityTreeModel(monitor, this);
55     // Set the model to show only collections, not items.
56     d->mEntityTreeModel->setItemPopulationStrategy(Akonadi::EntityTreeModel::NoItemPopulation);
57 
58     auto mimeTypeProxy = new Akonadi::CollectionFilterProxyModel(this);
59     mimeTypeProxy->setExcludeVirtualCollections(true);
60     mimeTypeProxy->addMimeTypeFilters({mimetype});
61     mimeTypeProxy->setSourceModel(d->mEntityTreeModel);
62 
63     // Create the Check proxy model.
64     d->mSelectionModel = new QItemSelectionModel(mimeTypeProxy);
65     d->mCheckProxy = new KCheckableProxyModel(this);
66     d->mCheckProxy->setSelectionModel(d->mSelectionModel);
67     d->mCheckProxy->setSourceModel(mimeTypeProxy);
68     d->mCollectionFilter = new QSortFilterProxyModel(this);
69     d->mCollectionFilter->setRecursiveFilteringEnabled(true);
70     d->mCollectionFilter->setSourceModel(d->mCheckProxy);
71     d->mCollectionFilter->setFilterCaseSensitivity(Qt::CaseInsensitive);
72 
73     auto searchLine = new QLineEdit(this);
74     searchLine->setPlaceholderText(i18n("Search..."));
75     searchLine->setClearButtonEnabled(true);
76     connect(searchLine, &QLineEdit::textChanged, this, &CheckedCollectionWidget::slotSetCollectionFilter);
77 
78     vbox->addWidget(searchLine);
79 
80     d->mFolderView = new QTreeView;
81     d->mFolderView->setEditTriggers(QAbstractItemView::NoEditTriggers);
82     d->mFolderView->setAlternatingRowColors(true);
83     d->mFolderView->setModel(d->mCollectionFilter);
84 
85     vbox->addWidget(d->mFolderView);
86 }
87 
88 CheckedCollectionWidget::~CheckedCollectionWidget() = default;
89 
entityTreeModel() const90 Akonadi::EntityTreeModel *CheckedCollectionWidget::entityTreeModel() const
91 {
92     return d->mEntityTreeModel;
93 }
94 
folderTreeView() const95 QTreeView *CheckedCollectionWidget::folderTreeView() const
96 {
97     return d->mFolderView;
98 }
99 
selectionModel() const100 QItemSelectionModel *CheckedCollectionWidget::selectionModel() const
101 {
102     return d->mSelectionModel;
103 }
104 
checkableProxy() const105 KCheckableProxyModel *CheckedCollectionWidget::checkableProxy() const
106 {
107     return d->mCheckProxy;
108 }
109 
slotSetCollectionFilter(const QString & filter)110 void CheckedCollectionWidget::slotSetCollectionFilter(const QString &filter)
111 {
112     d->mCollectionFilter->setFilterWildcard(filter);
113     d->mFolderView->expandAll();
114 }
115