Add carddav in parallel to ldap searches.

Hide favorites for readonly friends.
Fix hidden friend menu.
This commit is contained in:
Julien Wadel 2025-01-23 17:22:13 +01:00
parent dc45edf172
commit 1a94417139
15 changed files with 109 additions and 76 deletions

View file

@ -124,17 +124,9 @@ CallCore::CallCore(const std::shared_ptr<linphone::Call> &call) : QObject(nullpt
mRemoteName = Utils::coreStringToAppString(
linphoneFriend->getVcard() ? linphoneFriend->getVcard()->getFullName() : linphoneFriend->getName());
if (mRemoteName.isEmpty()) mRemoteName = ToolModel::getDisplayName(mRemoteAddress);
mShouldFindRemoteLdapFriend = !linphoneFriend; //
if (mShouldFindRemoteLdapFriend) {
auto servers = CoreModel::getInstance()->getCore()->getRemoteContactDirectories();
bool haveLdap = false;
for (auto s : servers) {
if (s->getType() == linphone::RemoteContactDirectory::Type::Ldap) {
haveLdap = true;
break;
}
}
mShouldFindRemoteLdapFriend = haveLdap;
mShouldFindRemoteFriend = !linphoneFriend;
if (mShouldFindRemoteFriend) {
mShouldFindRemoteFriend = CoreModel::getInstance()->getCore()->getRemoteContactDirectories().size() > 0;
}
mLocalAddress = Utils::coreStringToAppString(call->getCallLog()->getLocalAddress()->asStringUriOnly());
mStatus = LinphoneEnums::fromLinphone(call->getCallLog()->getStatus());
@ -438,7 +430,7 @@ void CallCore::setSelf(QSharedPointer<CallCore> me) {
setVideoStats(videoStats);
}
});
if (mShouldFindRemoteLdapFriend) findRemoteLdapFriend(me);
if (mShouldFindRemoteFriend) findRemoteFriend(me);
}
DEFINE_GET_SET_API(CallCore, bool, isStarted, IsStarted)
@ -776,30 +768,39 @@ void CallCore::setVideoStats(VideoStats stats) {
}
}
void CallCore::findRemoteLdapFriend(QSharedPointer<CallCore> me) {
void CallCore::findRemoteFriend(QSharedPointer<CallCore> me) {
mustBeInLinphoneThread(log().arg(Q_FUNC_INFO));
auto linphoneSearch = CoreModel::getInstance()->getCore()->createMagicSearch();
linphoneSearch->setLimitedSearch(true);
mLdapMagicSearchModel = Utils::makeQObject_ptr<MagicSearchModel>(linphoneSearch);
mLdapMagicSearchModel->setSelf(mLdapMagicSearchModel);
mLdapMagicSearchModelConnection = SafeConnection<CallCore, MagicSearchModel>::create(me, mLdapMagicSearchModel);
mLdapMagicSearchModelConnection->makeConnectToModel(
mRemoteMagicSearchModel = Utils::makeQObject_ptr<MagicSearchModel>(linphoneSearch);
mRemoteMagicSearchModel->setSelf(mRemoteMagicSearchModel);
mRemoteMagicSearchModelConnection = SafeConnection<CallCore, MagicSearchModel>::create(me, mRemoteMagicSearchModel);
mRemoteMagicSearchModelConnection->makeConnectToModel(
&MagicSearchModel::searchResultsReceived,
[this, remoteAdress = mRemoteAddress](const std::list<std::shared_ptr<linphone::SearchResult>> &results) {
mustBeInLinphoneThread(log().arg(Q_FUNC_INFO));
auto ldapFriend = ToolModel::findFriendByAddress(remoteAdress);
if (ldapFriend) {
auto ldapName = Utils::coreStringToAppString(ldapFriend->getName());
mLdapMagicSearchModelConnection->invokeToCore([this, ldapName]() {
QString name;
auto remoteFriend = ToolModel::findFriendByAddress(remoteAdress); // Priorize what is stored.
if (!remoteFriend && results.size() > 0) remoteFriend = results.front()->getFriend(); // Then result friend.
if (remoteFriend) name = Utils::coreStringToAppString(remoteFriend->getName());
else if (results.size() > 0) // Then result address.
name = Utils::coreStringToAppString(results.front()->getAddress()->getDisplayName());
if (name.isEmpty()) name = Utils::coreStringToAppString(results.front()->getAddress()->getUsername());
if (!name.isEmpty())
mRemoteMagicSearchModelConnection->invokeToCore([this, name]() {
mustBeInMainThread(log().arg(Q_FUNC_INFO));
if (ldapName != mRemoteName) {
mRemoteName = ldapName;
if (name != mRemoteName) {
mRemoteName = name;
emit remoteNameChanged();
}
});
}
});
mLdapMagicSearchModel->search(
SettingsModel::getInstance()->getUsernameOnlyForLdapLookupsInCalls() ? mRemoteUsername : mRemoteAddress,
(int)LinphoneEnums::MagicSearchSource::LdapServers, LinphoneEnums::MagicSearchAggregation::Friend, -1);
bool ldapSearch = SettingsModel::getInstance()->getUsernameOnlyForLdapLookupsInCalls();
bool cardDAVSearch = SettingsModel::getInstance()->getUsernameOnlyForCardDAVLookupsInCalls();
mRemoteMagicSearchModel->search(ldapSearch || cardDAVSearch ? mRemoteUsername : mRemoteAddress,
(ldapSearch ? (int)LinphoneEnums::MagicSearchSource::LdapServers : 0) |
(cardDAVSearch ? (int)LinphoneEnums::MagicSearchSource::RemoteCardDAV : 0),
LinphoneEnums::MagicSearchAggregation::Friend, -1);
}

View file

@ -236,7 +236,7 @@ public:
VideoStats getVideoStats() const;
void setVideoStats(VideoStats stats);
void findRemoteLdapFriend(QSharedPointer<CallCore> me);
void findRemoteFriend(QSharedPointer<CallCore> me);
signals:
void statusChanged(LinphoneEnums::CallStatus status);
@ -345,9 +345,9 @@ private:
ZrtpStats mZrtpStats;
AudioStats mAudioStats;
VideoStats mVideoStats;
std::shared_ptr<MagicSearchModel> mLdapMagicSearchModel;
bool mShouldFindRemoteLdapFriend;
QSharedPointer<SafeConnection<CallCore, MagicSearchModel>> mLdapMagicSearchModelConnection;
std::shared_ptr<MagicSearchModel> mRemoteMagicSearchModel;
bool mShouldFindRemoteFriend;
QSharedPointer<SafeConnection<CallCore, MagicSearchModel>> mRemoteMagicSearchModelConnection;
DECLARE_ABSTRACT_OBJECT
};

View file

@ -29,14 +29,17 @@ DEFINE_ABSTRACT_OBJECT(FriendCore)
const QString _addressLabel = FriendCore::tr("Adresse SIP");
const QString _phoneLabel = FriendCore::tr("Téléphone");
QSharedPointer<FriendCore> FriendCore::create(const std::shared_ptr<linphone::Friend> &contact, bool isStored) {
auto sharedPointer = QSharedPointer<FriendCore>(new FriendCore(contact, isStored), &QObject::deleteLater);
QSharedPointer<FriendCore>
FriendCore::create(const std::shared_ptr<linphone::Friend> &contact, bool isStored, int sourceFlags) {
auto sharedPointer =
QSharedPointer<FriendCore>(new FriendCore(contact, isStored, sourceFlags), &QObject::deleteLater);
sharedPointer->setSelf(sharedPointer);
sharedPointer->moveToThread(App::getInstance()->thread());
return sharedPointer;
}
FriendCore::FriendCore(const std::shared_ptr<linphone::Friend> &contact, bool isStored) : QObject(nullptr) {
FriendCore::FriendCore(const std::shared_ptr<linphone::Friend> &contact, bool isStored, int sourceFlags)
: QObject(nullptr) {
App::getInstance()->mEngine->setObjectOwnership(this, QQmlEngine::CppOwnership);
if (contact) {
mustBeInLinphoneThread(getClassName());
@ -80,17 +83,19 @@ FriendCore::FriendCore(const std::shared_ptr<linphone::Friend> &contact, bool is
LinphoneEnums::fromLinphone(device->getSecurityLevel())));
}
updateVerifiedDevicesCount();
mStarred = contact->getStarred();
mIsSaved = true;
mIsStored = isStored;
mIsLdap = ToolModel::friendIsInFriendList(ToolModel::getLdapFriendList(), contact);
mIsCardDAV = (sourceFlags & (int)linphone::MagicSearch::Source::RemoteCardDAV) != 0;
} else {
mIsSaved = false;
mStarred = false;
mIsStored = false;
mIsLdap = false;
mIsCardDAV = false;
}
connect(this, &FriendCore::addressChanged, &FriendCore::allAddressesChanged);
connect(this, &FriendCore::phoneNumberChanged, &FriendCore::allAddressesChanged);
}
@ -110,6 +115,7 @@ FriendCore::FriendCore(const FriendCore &friendCore) {
mIsSaved = friendCore.mIsSaved;
mIsStored = friendCore.mIsStored;
mIsLdap = friendCore.mIsLdap;
mIsCardDAV = friendCore.mIsCardDAV;
}
FriendCore::~FriendCore() {
@ -662,7 +668,7 @@ void FriendCore::save() { // Save Values to model
thisCopy->writeIntoModel(mFriendModel);
thisCopy->deleteLater();
mVCardString = mFriendModel->getVCardAsString();
auto carddavListForNewFriends = SettingsModel::getCarddavListForNewFriends();
auto carddavListForNewFriends = SettingsModel::getCardDAVListForNewFriends();
auto listWhereToAddFriend = carddavListForNewFriends != nullptr ? carddavListForNewFriends
: ToolModel::getAppFriendList();
bool created = (listWhereToAddFriend->addFriend(contact) == linphone::FriendList::Status::OK);
@ -702,9 +708,13 @@ bool FriendCore::isLdap() const {
return mIsLdap;
}
bool FriendCore::isCardDAV() const {
return mIsCardDAV;
}
bool FriendCore::getReadOnly() const {
return isLdap(); // TODO add conditions for friends retrieved via HTTP [misc]vcards-contacts-list=<URL> &
// CardDAV
return isLdap() || isCardDAV(); // TODO add conditions for friends retrieved via HTTP
// [misc]vcards-contacts-list=<URL> & CardDAV
}
std::shared_ptr<FriendModel> FriendCore::getFriendModel() {

View file

@ -72,11 +72,13 @@ class FriendCore : public QObject, public AbstractObject {
Q_PROPERTY(bool starred READ getStarred WRITE lSetStarred NOTIFY starredChanged)
Q_PROPERTY(bool readOnly READ getReadOnly CONSTANT)
Q_PROPERTY(bool isLdap READ isLdap CONSTANT)
Q_PROPERTY(bool isCardDAV READ isCardDAV CONSTANT)
public:
// Should be call from model Thread. Will be automatically in App thread after initialization
static QSharedPointer<FriendCore> create(const std::shared_ptr<linphone::Friend> &contact, bool isStored = true);
FriendCore(const std::shared_ptr<linphone::Friend> &contact, bool isStored = true);
static QSharedPointer<FriendCore>
create(const std::shared_ptr<linphone::Friend> &contact, bool isStored = true, int sourceFlags = 0);
FriendCore(const std::shared_ptr<linphone::Friend> &contact, bool isStored = true, int sourceFlags = 0);
FriendCore(const FriendCore &friendCore);
~FriendCore();
void setSelf(QSharedPointer<FriendCore> me);
@ -146,6 +148,7 @@ public:
void onPresenceReceived(LinphoneEnums::ConsolidatedPresence consolidatedPresence, QDateTime presenceTimestamp);
bool isLdap() const;
bool isCardDAV() const;
bool getReadOnly() const;
std::shared_ptr<FriendModel> getFriendModel();
@ -204,7 +207,7 @@ protected:
bool mIsSaved;
bool mIsStored;
QString mVCardString;
bool mIsLdap;
bool mIsLdap, mIsCardDAV;
std::shared_ptr<FriendModel> mFriendModel;
QSharedPointer<SafeConnection<FriendCore, FriendModel>> mFriendModelConnection;
QSharedPointer<SafeConnection<FriendCore, CoreModel>> mCoreModelConnection;

View file

@ -97,12 +97,12 @@ void MagicSearchList::setSelf(QSharedPointer<MagicSearchList> me) {
if (linphoneFriend) {
isStored =
(ldapContacts->findFriendByAddress(linphoneFriend->getAddress()) != linphoneFriend);
contact = FriendCore::create(linphoneFriend, isStored);
contact = FriendCore::create(linphoneFriend, isStored, it->getSourceFlags());
contacts->append(contact);
} else if (auto address = it->getAddress()) {
auto linphoneFriend = CoreModel::getInstance()->getCore()->createFriend();
linphoneFriend->setAddress(address);
contact = FriendCore::create(linphoneFriend, isStored);
contact = FriendCore::create(linphoneFriend, isStored, it->getSourceFlags());
auto displayName = Utils::coreStringToAppString(address->getDisplayName());
auto splitted = displayName.split(" ");
if (!displayName.isEmpty() && splitted.size() > 0) {
@ -118,7 +118,7 @@ void MagicSearchList::setSelf(QSharedPointer<MagicSearchList> me) {
} else if (!it->getPhoneNumber().empty()) {
linphoneFriend = CoreModel::getInstance()->getCore()->createFriend();
linphoneFriend->setAddress(address);
contact = FriendCore::create(linphoneFriend, isStored);
contact = FriendCore::create(linphoneFriend, isStored, it->getSourceFlags());
contact->setGivenName(Utils::coreStringToAppString(it->getPhoneNumber()));
contact->appendPhoneNumber(tr("Phone"), Utils::coreStringToAppString(it->getPhoneNumber()));
contacts->append(contact);
@ -215,7 +215,8 @@ QVariant MagicSearchList::data(const QModelIndex &index, int role) const {
if (role == Qt::DisplayRole) {
return QVariant::fromValue(new FriendGui(mList[row].objectCast<FriendCore>()));
} else if (role == Qt::DisplayRole + 1) {
return mList[row].objectCast<FriendCore>()->getIsStored() || mList[row].objectCast<FriendCore>()->isLdap();
return mList[row].objectCast<FriendCore>()->getIsStored() || mList[row].objectCast<FriendCore>()->isLdap() ||
mList[row].objectCast<FriendCore>()->isCardDAV();
}
return QVariant();
}

View file

@ -54,7 +54,7 @@ void MagicSearchProxy::setList(QSharedPointer<MagicSearchList> newList) {
[this](int index, FriendGui *data) {
auto sortModel = dynamic_cast<SortFilterList *>(sourceModel());
sortModel->invalidate();
if (!data->mCore->isLdap()) {
if (!data->mCore->isLdap() && !data->mCore->isCardDAV()) {
auto proxyIndex = sortModel->mapFromSource(mList->index(index, 0)).row();
// auto proxyIndex = mapFromSource(sourceModel()->index(index, 0)); // OLD (keep for checking new
// proxy behavior)
@ -196,6 +196,9 @@ bool MagicSearchProxy::SortFilterList::filterAcceptsRow(int sourceRow, const QMo
toShow = friendCore->isLdap();
// if (!toShow) return false;
}
if (!toShow && (mFilterType & (int)FilteringTypes::CardDAV) > 0) {
toShow = friendCore->isCardDAV();
}
if (!toShow && (mFilterType & (int)FilteringTypes::App) > 0) {
toShow = friendCore->getIsStored() && !friendCore->isLdap();
// if (!toShow) return false;
@ -220,8 +223,8 @@ bool MagicSearchProxy::SortFilterList::lessThan(const QModelIndex &sourceLeft, c
auto r = getItemAtSource<MagicSearchList, FriendCore>(sourceRight.row());
if (l && r) {
bool lIsStored = l->getIsStored() || l->isLdap();
bool rIsStored = r->getIsStored() || r->isLdap();
bool lIsStored = l->getIsStored() || l->isLdap() || l->isCardDAV();
bool rIsStored = r->getIsStored() || r->isLdap() || r->isCardDAV();
if (lIsStored && !rIsStored) return true;
else if (!lIsStored && rIsStored) return false;
auto lName = l->getFullName().toLower();

View file

@ -41,7 +41,7 @@ class MagicSearchProxy : public LimitProxy {
Q_PROPERTY(MagicSearchProxy *hideListProxy READ getHideListProxy WRITE setHideListProxy NOTIFY hideListProxyChanged)
public:
enum class FilteringTypes { None = 0, Favorites = 1, App = 2, Ldap = 4, Other = 8 };
enum class FilteringTypes { None = 0, Favorites = 1, App = 2, Ldap = 4, CardDAV = 8, Other = 16 };
Q_ENUM(FilteringTypes)
DECLARE_SORTFILTER_CLASS(MagicSearchProxy *mHideListProxy = nullptr;)

View file

@ -49,7 +49,7 @@ CarddavModel::~CarddavModel() {
bool CarddavModel::storeNewFriendsInIt() {
if (!mCarddavFriendList) return false;
auto carddavListForNewFriends = SettingsModel::getCarddavListForNewFriends();
auto carddavListForNewFriends = SettingsModel::getCardDAVListForNewFriends();
return carddavListForNewFriends != nullptr &&
mCarddavFriendList->getDisplayName() == carddavListForNewFriends->getDisplayName();
}
@ -100,7 +100,7 @@ void CarddavModel::onSyncStatusChanged(const std::shared_ptr<linphone::FriendLis
if (status == linphone::FriendList::SyncStatus::Successful) {
lInfo() << log().arg("Successfully synchronized:") << mCarddavFriendList->getUri();
setMonitor(nullptr);
if (mStoreNewFriendsInIt) SettingsModel::setCarddavListForNewFriends(friendList->getDisplayName());
if (mStoreNewFriendsInIt) SettingsModel::setCardDAVListForNewFriends(friendList->getDisplayName());
emit saved(true);
}
if (status == linphone::FriendList::SyncStatus::Failure) {

View file

@ -49,6 +49,8 @@ void MagicSearchModel::search(QString filter,
if (((sourceFlags & (int)LinphoneEnums::MagicSearchSource::LdapServers) > 0) &&
!SettingsModel::getInstance()->getSyncLdapContacts())
sourceFlags &= ~(int)LinphoneEnums::MagicSearchSource::LdapServers;
if (((sourceFlags & (int)LinphoneEnums::MagicSearchSource::RemoteCardDAV) > 0))
sourceFlags &= ~(int)LinphoneEnums::MagicSearchSource::RemoteCardDAV;
// For complete search, we search only on local contacts.
// sourceFlags &= ~(int)LinphoneEnums::MagicSearchSource::CallLogs;
// sourceFlags &= ~(int)LinphoneEnums::MagicSearchSource::ChatRooms;
@ -88,12 +90,12 @@ void MagicSearchModel::onSearchResultsReceived(const std::shared_ptr<linphone::M
<< (fList ? fList->getDisplayName().c_str() : "NoList") << result->getSourceFlags() << " / "
<< (f ? f.get() : nullptr);
bool isLdap = (result->getSourceFlags() & (int)LinphoneEnums::MagicSearchSource::LdapServers) != 0;
bool isLdap = (result->getSourceFlags() & (int)linphone::MagicSearch::Source::LdapServers) != 0;
// Do not add it into ldap_friends if it already exists in app_friends.
if (isLdap && f && (!fList || fList->getDisplayName() != "app_friends") &&
!ToolModel::friendIsInFriendList(appFriends, f)) { // Double check because of SDK merging that lead to
// use a ldap result as of app_friends/ldap_friends.
updateLdapFriendListWithFriend(f);
updateFriendListWithFriend(f, ToolModel::getLdapFriendList());
}
auto resultIt =
@ -106,9 +108,8 @@ void MagicSearchModel::onSearchResultsReceived(const std::shared_ptr<linphone::M
emit searchResultsReceived(finalResults);
}
void MagicSearchModel::onLdapHaveMoreResults(const std::shared_ptr<linphone::MagicSearch> &magicSearch,
const std::shared_ptr<linphone::Ldap> &ldap) {
// emit ldapHaveMoreResults(ldap);
void MagicSearchModel::onMoreResultsAvailable(const std::shared_ptr<linphone::MagicSearch> &magicSearch,
linphone::MagicSearch::Source source) {
}
// Store LDAP friends in separate list so they can still be retrieved by core->findFriend() for display names,
@ -116,29 +117,30 @@ void MagicSearchModel::onLdapHaveMoreResults(const std::shared_ptr<linphone::Mag
// Done in this place so the application can benefit from user initiated searches for faster ldap name retrieval
// upon incoming call / chat message.
void MagicSearchModel::updateLdapFriendListWithFriend(const std::shared_ptr<linphone::Friend> &linphoneFriend) {
void MagicSearchModel::updateFriendListWithFriend(const std::shared_ptr<linphone::Friend> &linphoneFriend,
std::shared_ptr<linphone::FriendList> friendList) {
mustBeInLinphoneThread(log().arg(Q_FUNC_INFO));
auto core = CoreModel::getInstance()->getCore();
auto ldapFriendList = ToolModel::getLdapFriendList();
if (ToolModel::friendIsInFriendList(ldapFriendList, linphoneFriend))
if (ToolModel::friendIsInFriendList(friendList, linphoneFriend))
return; // Already exist. We don't need to manipulate list.
for (auto address : linphoneFriend->getAddresses()) {
auto existingFriend = ldapFriendList->findFriendByAddress(address);
auto existingFriend = friendList->findFriendByAddress(address);
if (existingFriend) {
ldapFriendList->removeFriend(existingFriend);
ldapFriendList->addFriend(linphoneFriend);
friendList->removeFriend(existingFriend);
friendList->addFriend(linphoneFriend);
return;
}
}
for (auto number : linphoneFriend->getPhoneNumbers()) {
auto existingFriend = ldapFriendList->findFriendByPhoneNumber(number);
auto existingFriend = friendList->findFriendByPhoneNumber(number);
if (existingFriend) {
ldapFriendList->removeFriend(existingFriend);
ldapFriendList->addFriend(linphoneFriend);
friendList->removeFriend(existingFriend);
friendList->addFriend(linphoneFriend);
return;
}
}
qDebug() << log().arg("Adding Friend:") << linphoneFriend.get();
ldapFriendList->addFriend(linphoneFriend);
friendList->addFriend(linphoneFriend);
emit CoreModel::getInstance()->friendCreated(linphoneFriend);
}

View file

@ -53,9 +53,10 @@ private:
// LINPHONE
//--------------------------------------------------------------------------------
virtual void onSearchResultsReceived(const std::shared_ptr<linphone::MagicSearch> &magicSearch) override;
virtual void onLdapHaveMoreResults(const std::shared_ptr<linphone::MagicSearch> &magicSearch,
const std::shared_ptr<linphone::Ldap> &ldap) override;
void updateLdapFriendListWithFriend(const std::shared_ptr<linphone::Friend> &linphoneFriend);
virtual void onMoreResultsAvailable(const std::shared_ptr<linphone::MagicSearch> &magicSearch,
linphone::MagicSearch::Source source) override;
void updateFriendListWithFriend(const std::shared_ptr<linphone::Friend> &linphoneFriend,
std::shared_ptr<linphone::FriendList> friendList);
signals:
void searchResultsReceived(const std::list<std::shared_ptr<linphone::SearchResult>> &results);

View file

@ -575,7 +575,7 @@ void SettingsModel::setIpv6Enabled(bool status) {
// Carddav storage list
// =============================================================================
const std::shared_ptr<linphone::FriendList> SettingsModel::getCarddavListForNewFriends() {
const std::shared_ptr<linphone::FriendList> SettingsModel::getCardDAVListForNewFriends() {
mustBeInLinphoneThread(sLog().arg(Q_FUNC_INFO));
auto core = CoreModel::getInstance()->getCore();
if (core) {
@ -586,7 +586,7 @@ const std::shared_ptr<linphone::FriendList> SettingsModel::getCarddavListForNewF
} else return nullptr;
}
void SettingsModel::setCarddavListForNewFriends(std::string name) {
void SettingsModel::setCardDAVListForNewFriends(std::string name) {
mustBeInLinphoneThread(sLog().arg(Q_FUNC_INFO));
auto core = CoreModel::getInstance()->getCore();
if (core) {
@ -687,6 +687,7 @@ void SettingsModel::notifyConfigReady(){
DEFINE_NOTIFY_CONFIG_READY(shortcutCount, ShortcutCount)
DEFINE_NOTIFY_CONFIG_READY(shortcuts, Shortcuts)
DEFINE_NOTIFY_CONFIG_READY(usernameOnlyForLdapLookupsInCalls, UsernameOnlyForLdapLookupsInCalls)
DEFINE_NOTIFY_CONFIG_READY(usernameOnlyForCardDAVLookupsInCalls, UsernameOnlyForCardDAVLookupsInCalls)
}
DEFINE_GETSET_CONFIG(SettingsModel, bool, Bool, disableChatFeature, DisableChatFeature, "disable_chat_feature", true)
@ -808,4 +809,11 @@ DEFINE_GETSET_CONFIG(SettingsModel,
UsernameOnlyForLdapLookupsInCalls,
"username_only_for_ldap_lookups_in_calls",
false)
DEFINE_GETSET_CONFIG(SettingsModel,
bool,
Bool,
usernameOnlyForCardDAVLookupsInCalls,
UsernameOnlyForCardDAVLookupsInCalls,
"username_only_for_carddav_lookups_in_calls",
false)
// clang-format on

View file

@ -138,8 +138,8 @@ public:
QString getLogsEmail() const;
static const std::shared_ptr<linphone::FriendList> getCarddavListForNewFriends();
static void setCarddavListForNewFriends(std::string listName);
static const std::shared_ptr<linphone::FriendList> getCardDAVListForNewFriends();
static void setCardDAVListForNewFriends(std::string listName);
static QString getDeviceName(const std::shared_ptr<linphone::Config> &config);
@ -171,6 +171,7 @@ public:
DECLARE_GETSET(int, shortcutCount, ShortcutCount)
DECLARE_GETSET(QVariantList, shortcuts, Shortcuts)
DECLARE_GETSET(bool, usernameOnlyForLdapLookupsInCalls, UsernameOnlyForLdapLookupsInCalls)
DECLARE_GETSET(bool, usernameOnlyForCardDAVLookupsInCalls, UsernameOnlyForCardDAVLookupsInCalls)
signals:
void logsUploadUrlChanged();

View file

@ -285,7 +285,8 @@ Flickable{
model:MagicSearchProxy {
id: contactsProxy
parentProxy: mainItem.mainModel
filterType: MagicSearchProxy.FilteringTypes.App | (mainItem.searchText != '*' && mainItem.searchText != '' || SettingsCpp.syncLdapContacts ? MagicSearchProxy.FilteringTypes.Ldap : 0)
filterType: MagicSearchProxy.FilteringTypes.App
| (mainItem.searchText != '*' && mainItem.searchText != '' || SettingsCpp.syncLdapContacts ? MagicSearchProxy.FilteringTypes.Ldap | MagicSearchProxy.FilteringTypes.CardDAV: 0)
initialDisplayItems: Math.max(20, 2 * mainItem.height / (63 * DefaultStyle.dp))
displayItemsStep: 3 * initialDisplayItems / 2
onLocalFriendCreated: (index) => {

View file

@ -165,7 +165,7 @@ FocusScope {
popup.contentItem: ColumnLayout {
IconLabelButton {
visible: searchResultItem.core.isStored
visible: searchResultItem.core.isStored && !searchResultItem.core.readOnly
text: searchResultItem.core.starred ? qsTr("Enlever des favoris") : qsTr("Mettre en favori")
icon.source: searchResultItem.core.starred ? AppIcons.heartFill : AppIcons.heart
spacing: 10 * DefaultStyle.dp

View file

@ -703,11 +703,13 @@ AbstractMainPage {
anchors.fill: parent
IconLabelButton {
Layout.fillWidth: true
property bool isLdap: contactDetail.contact?.core?.isLdap
property bool isCardDAV: contactDetail.contact?.core?.isCardDAV
text: contactDetail.contact ? qsTr("Voir le contact") : qsTr("Ajouter aux contacts")
icon.source: AppIcons.plusCircle
icon.width: 32 * DefaultStyle.dp
icon.height: 32 * DefaultStyle.dp
visible: SettingsCpp.syncLdapContacts || !contactDetail.contact?.core?.isLdap
visible: !isLdap && !isCardDAV
onClicked: {
detailOptions.close()
if (contactDetail.contact) mainWindow.displayContactPage(contactDetail.contactAddress)