File indexing completed on 2024-11-24 04:50:42

0001 // SPDX-FileCopyrightText: 2022 Carl Schwan <carlschwan@kde.org>
0002 // SPDX-License-Identifier: LGPL-2.1-or-later
0003 
0004 #include "contactsmodel.h"
0005 #include <akonadi/entitytreemodel.h>
0006 
0007 #include <Akonadi/ContactsFilterProxyModel>
0008 #include <Akonadi/ContactsTreeModel>
0009 #include <Akonadi/EmailAddressSelectionModel>
0010 #include <Akonadi/EntityMimeTypeFilterModel>
0011 #include <KContacts/Addressee>
0012 #include <KDescendantsProxyModel>
0013 
0014 ContactsModel::ContactsModel(QObject *parent)
0015     : QSortFilterProxyModel(parent)
0016 {
0017     auto sourceModel = new Akonadi::EmailAddressSelectionModel(this);
0018     auto filterModel = new Akonadi::ContactsFilterProxyModel(this);
0019     filterModel->setSourceModel(sourceModel->model());
0020     filterModel->setFilterFlags(Akonadi::ContactsFilterProxyModel::HasEmail);
0021 
0022     auto flatModel = new KDescendantsProxyModel(this);
0023     flatModel->setSourceModel(filterModel);
0024 
0025     auto addresseeOnlyModel = new Akonadi::EntityMimeTypeFilterModel(this);
0026     addresseeOnlyModel->setSourceModel(flatModel);
0027     addresseeOnlyModel->addMimeTypeInclusionFilter(KContacts::Addressee::mimeType());
0028 
0029     setSourceModel(addresseeOnlyModel);
0030     setDynamicSortFilter(true);
0031     setFilterCaseSensitivity(Qt::CaseInsensitive);
0032     sort(0);
0033 }
0034 
0035 bool ContactsModel::filterAcceptsRow(int row, const QModelIndex &sourceParent) const
0036 {
0037     // Eliminate duplicate Akonadi items
0038     const QModelIndex sourceIndex = sourceModel()->index(row, 0, sourceParent);
0039     Q_ASSERT(sourceIndex.isValid());
0040 
0041     auto data = sourceIndex.data(Akonadi::EntityTreeModel::ItemIdRole);
0042     auto matches = match(index(0, 0), Akonadi::EntityTreeModel::ItemIdRole, data, 2, Qt::MatchExactly | Qt::MatchWrap | Qt::MatchRecursive);
0043 
0044     return matches.length() < 1;
0045 }
0046 
0047 QVariant ContactsModel::data(const QModelIndex &idx, int role) const
0048 {
0049     if (role == AllEmailsRole) {
0050         const auto item = QSortFilterProxyModel::data(idx, Akonadi::EntityTreeModel::ItemRole).value<Akonadi::Item>();
0051         if (item.mimeType() == KContacts::Addressee::mimeType()) {
0052             if (!item.hasPayload<KContacts::Addressee>()) {
0053                 return {};
0054             }
0055             const auto contact = item.payload<KContacts::Addressee>();
0056             return contact.emails();
0057         }
0058         return {};
0059     }
0060     if (role == EmailRole) {
0061         const auto item = QSortFilterProxyModel::data(idx, Akonadi::EntityTreeModel::ItemRole).value<Akonadi::Item>();
0062         if (item.mimeType() == KContacts::Addressee::mimeType()) {
0063             if (!item.hasPayload<KContacts::Addressee>()) {
0064                 return {};
0065             }
0066             const auto contact = item.payload<KContacts::Addressee>();
0067             return contact.preferredEmail();
0068         }
0069         return {};
0070     }
0071 
0072     if (role == GidRole) {
0073         const auto item = QSortFilterProxyModel::data(idx, Akonadi::EntityTreeModel::ItemRole).value<Akonadi::Item>();
0074         if (item.mimeType() == KContacts::Addressee::mimeType()) {
0075             if (!item.hasPayload<KContacts::Addressee>()) {
0076                 return {};
0077             }
0078             return item.id();
0079         }
0080         return {};
0081     }
0082 
0083     return QSortFilterProxyModel::data(idx, role);
0084 }
0085 
0086 QHash<int, QByteArray> ContactsModel::roleNames() const
0087 {
0088     auto roles = QSortFilterProxyModel::roleNames();
0089     roles[EmailRole] = "email";
0090     roles[GidRole] = "gid";
0091     return roles;
0092 }
0093 
0094 #include "moc_contactsmodel.cpp"