diff --git a/Linphone/core/call-history/CallHistoryCore.cpp b/Linphone/core/call-history/CallHistoryCore.cpp index b447d26f8..b03b33be8 100644 --- a/Linphone/core/call-history/CallHistoryCore.cpp +++ b/Linphone/core/call-history/CallHistoryCore.cpp @@ -79,6 +79,28 @@ CallHistoryCore::~CallHistoryCore() { void CallHistoryCore::setSelf(QSharedPointer me) { mHistoryModelConnection = QSharedPointer>( new SafeConnection(me, mCallHistoryModel), &QObject::deleteLater); + mCoreModelConnection = QSharedPointer>( + new SafeConnection(me, CoreModel::getInstance()), &QObject::deleteLater); + if (!ToolModel::findFriendByAddress(mRemoteAddress)) { + mCoreModelConnection->makeConnectToModel( + &CoreModel::friendCreated, + [this, remoteAddress = mRemoteAddress](const std::shared_ptr &f) { + auto inFriend = Utils::findFriendByAddress(remoteAddress); + QString displayName; + if (inFriend) { + auto friendGui = inFriend->getValue().value(); + if (friendGui) displayName = friendGui->getCore()->getDisplayName(); + } + if (!displayName.isEmpty()) { + mCoreModelConnection->invokeToCore([this, displayName]() { + if (displayName != mDisplayName) { + mDisplayName = displayName; + emit displayNameChanged(); + } + }); + } + }); + } } ConferenceInfoGui *CallHistoryCore::getConferenceInfoGui() const { diff --git a/Linphone/core/call-history/CallHistoryCore.hpp b/Linphone/core/call-history/CallHistoryCore.hpp index 4584d3ac6..9ecd651bd 100644 --- a/Linphone/core/call-history/CallHistoryCore.hpp +++ b/Linphone/core/call-history/CallHistoryCore.hpp @@ -34,7 +34,7 @@ class CallHistoryModel; class CallHistoryCore : public QObject, public AbstractObject { Q_OBJECT - Q_PROPERTY(QString displayName MEMBER mDisplayName CONSTANT) + Q_PROPERTY(QString displayName MEMBER mDisplayName NOTIFY displayNameChanged) Q_PROPERTY(QString remoteAddress MEMBER mRemoteAddress CONSTANT) Q_PROPERTY(bool isOutgoing MEMBER mIsOutgoing CONSTANT) Q_PROPERTY(bool isConference MEMBER mIsConference CONSTANT) @@ -66,12 +66,14 @@ public: signals: void durationChanged(QString duration); + void displayNameChanged(); private: QString mDuration; QSharedPointer mConferenceInfo = nullptr; std::shared_ptr mCallHistoryModel; QSharedPointer> mHistoryModelConnection; + QSharedPointer> mCoreModelConnection; DECLARE_ABSTRACT_OBJECT }; diff --git a/Linphone/core/call/CallCore.cpp b/Linphone/core/call/CallCore.cpp index 7a1f46441..2459fa0f9 100644 --- a/Linphone/core/call/CallCore.cpp +++ b/Linphone/core/call/CallCore.cpp @@ -22,6 +22,7 @@ #include "core/App.hpp" #include "core/conference/ConferenceCore.hpp" #include "core/conference/ConferenceGui.hpp" +#include "core/friend/FriendCore.hpp" #include "core/setting/SettingsCore.hpp" #include "model/tool/ToolModel.hpp" #include "tool/Utils.hpp" @@ -129,6 +130,7 @@ CallCore::CallCore(const std::shared_ptr &call) : QObject(nullpt mRemoteName = Utils::coreStringToAppString( linphoneFriend->getVcard() ? linphoneFriend->getVcard()->getFullName() : linphoneFriend->getName()); if (mRemoteName.isEmpty()) mRemoteName = ToolModel::getDisplayName(mRemoteAddress); + mShouldFindRemoteLdapFriend = !linphoneFriend && !CoreModel::getInstance()->getCore()->getLdapList().empty(); mLocalAddress = Utils::coreStringToAppString(call->getCallLog()->getLocalAddress()->asStringUriOnly()); mStatus = LinphoneEnums::fromLinphone(call->getCallLog()->getStatus()); @@ -466,14 +468,11 @@ void CallCore::setSelf(QSharedPointer me) { setVideoStats(videoStats); } }); + if (mShouldFindRemoteLdapFriend) findRemoteLdapFriend(me); } DEFINE_GET_SET_API(CallCore, bool, isStarted, IsStarted) -QString CallCore::getRemoteName() const { - return mRemoteName; -} - QString CallCore::getRemoteAddress() const { return mRemoteAddress; } @@ -818,3 +817,32 @@ void CallCore::setVideoStats(VideoStats stats) { emit videoStatsChanged(); } } + +void CallCore::findRemoteLdapFriend(QSharedPointer me) { + mustBeInLinphoneThread(log().arg(Q_FUNC_INFO)); + auto linphoneSearch = CoreModel::getInstance()->getCore()->createMagicSearch(); + linphoneSearch->setLimitedSearch(true); + mLdapMagicSearchModel = Utils::makeQObject_ptr(linphoneSearch); + mLdapMagicSearchModel->setSourceFlags((int)LinphoneEnums::MagicSearchSource::LdapServers); + mLdapMagicSearchModel->setAggregationFlag(LinphoneEnums::MagicSearchAggregation::Friend); + mLdapMagicSearchModel->setSelf(mLdapMagicSearchModel); + mLdapMagicSearchModelConnection = QSharedPointer>( + new SafeConnection(me, mLdapMagicSearchModel), &QObject::deleteLater); + mLdapMagicSearchModelConnection->makeConnectToModel( + &MagicSearchModel::searchResultsReceived, + [this, remoteAdress = mRemoteAddress](const std::list> &results) { + mustBeInLinphoneThread(log().arg(Q_FUNC_INFO)); + auto ldapFriend = ToolModel::findFriendByAddress(remoteAdress); + if (ldapFriend) { + auto ldapName = Utils::coreStringToAppString(ldapFriend->getName()); + mLdapMagicSearchModelConnection->invokeToCore([this, ldapName]() { + mustBeInMainThread(log().arg(Q_FUNC_INFO)); + if (ldapName != mRemoteName) { + mRemoteName = ldapName; + emit remoteNameChanged(); + } + }); + } + }); + mLdapMagicSearchModel->search(mRemoteAddress); +} diff --git a/Linphone/core/call/CallCore.hpp b/Linphone/core/call/CallCore.hpp index 82a86a79c..74eaabf00 100644 --- a/Linphone/core/call/CallCore.hpp +++ b/Linphone/core/call/CallCore.hpp @@ -25,6 +25,7 @@ #include "core/conference/ConferenceGui.hpp" #include "core/videoSource/VideoSourceDescriptorGui.hpp" #include "model/call/CallModel.hpp" +#include "model/search/MagicSearchModel.hpp" #include "tool/LinphoneEnums.hpp" #include "tool/thread/SafeConnection.hpp" #include @@ -104,7 +105,7 @@ class CallCore : public QObject, public AbstractObject { Q_PROPERTY(bool speakerMuted READ getSpeakerMuted WRITE lSetSpeakerMuted NOTIFY speakerMutedChanged) Q_PROPERTY(bool microphoneMuted READ getMicrophoneMuted WRITE lSetMicrophoneMuted NOTIFY microphoneMutedChanged) Q_PROPERTY(bool paused READ getPaused WRITE lSetPaused NOTIFY pausedChanged) - Q_PROPERTY(QString remoteName READ getRemoteName CONSTANT) + Q_PROPERTY(QString remoteName MEMBER mRemoteName NOTIFY remoteNameChanged) Q_PROPERTY(QString remoteAddress READ getRemoteAddress CONSTANT) Q_PROPERTY(QString localAddress READ getLocalAddress CONSTANT) Q_PROPERTY(bool tokenVerified READ getTokenVerified WRITE setTokenVerified NOTIFY securityUpdated) @@ -146,7 +147,6 @@ public: ~CallCore(); void setSelf(QSharedPointer me); - QString getRemoteName() const; QString getRemoteAddress() const; QString getLocalAddress() const; @@ -245,6 +245,8 @@ public: VideoStats getVideoStats() const; void setVideoStats(VideoStats stats); + void findRemoteLdapFriend(QSharedPointer me); + signals: void statusChanged(LinphoneEnums::CallStatus status); void stateChanged(LinphoneEnums::CallState state); @@ -274,6 +276,7 @@ signals: void zrtpStatsChanged(); void audioStatsChanged(); void videoStatsChanged(); + void remoteNameChanged(); // Linphone commands void lAccept(bool withVideo); // Accept an incoming call @@ -355,6 +358,9 @@ private: ZrtpStats mZrtpStats; AudioStats mAudioStats; VideoStats mVideoStats; + std::shared_ptr mLdapMagicSearchModel; + bool mShouldFindRemoteLdapFriend; + QSharedPointer> mLdapMagicSearchModelConnection; DECLARE_ABSTRACT_OBJECT }; diff --git a/Linphone/core/friend/FriendCore.cpp b/Linphone/core/friend/FriendCore.cpp index 9b24244f0..65ba82651 100644 --- a/Linphone/core/friend/FriendCore.cpp +++ b/Linphone/core/friend/FriendCore.cpp @@ -99,7 +99,7 @@ FriendCore::FriendCore(const std::shared_ptr &contact) : QObje mStarred = false; } - mIsLdap = false; + mIsLdap = ToolModel::friendIsInLdapFriendList(contact); connect(this, &FriendCore::addressChanged, &FriendCore::allAddressesChanged); connect(this, &FriendCore::phoneNumberChanged, &FriendCore::allAddressesChanged); } @@ -670,17 +670,11 @@ void FriendCore::undo() { // Retrieve values from model } } -bool FriendCore::getIsLdap() const { +bool FriendCore::isLdap() const { return mIsLdap; } -void FriendCore::setIsLdap(bool data) { - if (mIsLdap != data) { - mIsLdap = data; - emit readOnlyChanged(); - } -} bool FriendCore::getReadOnly() const { - return getIsLdap(); // TODO add conditions for friends retrieved via HTTP [misc]vcards-contacts-list= & - // CardDAV + return isLdap(); // TODO add conditions for friends retrieved via HTTP [misc]vcards-contacts-list= & + // CardDAV } diff --git a/Linphone/core/friend/FriendCore.hpp b/Linphone/core/friend/FriendCore.hpp index a453b16a8..a0636cd9e 100644 --- a/Linphone/core/friend/FriendCore.hpp +++ b/Linphone/core/friend/FriendCore.hpp @@ -67,7 +67,8 @@ class FriendCore : public QObject, public AbstractObject { Q_PROPERTY(bool isSaved READ getIsSaved NOTIFY isSavedChanged) Q_PROPERTY(QString pictureUri READ getPictureUri WRITE setPictureUri NOTIFY pictureUriChanged) Q_PROPERTY(bool starred READ getStarred WRITE lSetStarred NOTIFY starredChanged) - Q_PROPERTY(bool readOnly READ getReadOnly NOTIFY readOnlyChanged) + Q_PROPERTY(bool readOnly READ getReadOnly CONSTANT) + Q_PROPERTY(bool isLdap READ isLdap CONSTANT) public: // Should be call from model Thread. Will be automatically in App thread after initialization @@ -135,8 +136,7 @@ public: void onPresenceReceived(LinphoneEnums::ConsolidatedPresence consolidatedPresence, QDateTime presenceTimestamp); - bool getIsLdap() const; - void setIsLdap(bool isLdap); + bool isLdap() const; bool getReadOnly() const; Q_INVOKABLE void remove(); @@ -168,7 +168,6 @@ signals: void devicesChanged(); void verifiedDevicesChanged(); void lSetStarred(bool starred); - void readOnlyChanged(); protected: void writeIntoModel(std::shared_ptr model) const; diff --git a/Linphone/core/search/MagicSearchList.cpp b/Linphone/core/search/MagicSearchList.cpp index 0dd2ab3ff..8542ca8ab 100644 --- a/Linphone/core/search/MagicSearchList.cpp +++ b/Linphone/core/search/MagicSearchList.cpp @@ -122,8 +122,6 @@ void MagicSearchList::setSelf(QSharedPointer me) { contact->appendPhoneNumber(tr("Phone"), Utils::coreStringToAppString(it->getPhoneNumber())); contacts->append(contact); } - bool isLdap = (it->getSourceFlags() & (int)LinphoneEnums::MagicSearchSource::LdapServers) != 0; - if (contact) contact->setIsLdap(isLdap); } mModelConnection->invokeToCore([this, contacts]() { setResults(*contacts); diff --git a/Linphone/core/search/MagicSearchList.hpp b/Linphone/core/search/MagicSearchList.hpp index 7403fbf08..783a39174 100644 --- a/Linphone/core/search/MagicSearchList.hpp +++ b/Linphone/core/search/MagicSearchList.hpp @@ -74,6 +74,7 @@ private: std::shared_ptr mMagicSearch; QSharedPointer> mModelConnection; QSharedPointer> mCoreModelConnection; + DECLARE_ABSTRACT_OBJECT }; diff --git a/Linphone/core/search/MagicSearchProxy.cpp b/Linphone/core/search/MagicSearchProxy.cpp index 0250fef01..75ced5c0d 100644 --- a/Linphone/core/search/MagicSearchProxy.cpp +++ b/Linphone/core/search/MagicSearchProxy.cpp @@ -68,7 +68,10 @@ void MagicSearchProxy::setList(QSharedPointer newList) { Qt::QueuedConnection); } auto sortFilterList = new SortFilterList(mList.get(), Qt::AscendingOrder); - if (oldModel) sortFilterList->mShowFavoritesOnly = oldModel->mShowFavoritesOnly; + if (oldModel) { + sortFilterList->mShowFavoritesOnly = oldModel->mShowFavoritesOnly; + sortFilterList->mShowLdapContacts = oldModel->mShowLdapContacts; + } setSourceModels(sortFilterList); } @@ -133,7 +136,7 @@ void MagicSearchProxy::setAggregationFlag(LinphoneEnums::MagicSearchAggregation bool MagicSearchProxy::SortFilterList::filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const { auto friendCore = getItemAtSource(sourceRow); if (friendCore) { - return !mShowFavoritesOnly || friendCore->getStarred(); + return (!mShowFavoritesOnly || friendCore->getStarred()) && (mShowLdapContacts || !friendCore->isLdap()); } return false; } @@ -149,3 +152,15 @@ bool MagicSearchProxy::SortFilterList::lessThan(const QModelIndex &sourceLeft, c } return true; } + +bool MagicSearchProxy::showLdapContacts() const { + return dynamic_cast(sourceModel())->mShowLdapContacts; +} + +void MagicSearchProxy::setShowLdapContacts(bool show) { + auto list = dynamic_cast(sourceModel()); + if (list->mShowLdapContacts != show) { + list->mShowLdapContacts = show; + list->invalidate(); + } +} diff --git a/Linphone/core/search/MagicSearchProxy.hpp b/Linphone/core/search/MagicSearchProxy.hpp index 4f1554fe3..6419e736a 100644 --- a/Linphone/core/search/MagicSearchProxy.hpp +++ b/Linphone/core/search/MagicSearchProxy.hpp @@ -36,9 +36,11 @@ class MagicSearchProxy : public LimitProxy { NOTIFY aggregationFlagChanged) Q_PROPERTY(bool showFavoritesOnly READ showFavoritesOnly WRITE setShowFavoritesOnly NOTIFY showFavoriteOnlyChanged) Q_PROPERTY(MagicSearchProxy *parentProxy WRITE setParentProxy NOTIFY parentProxyChanged) + Q_PROPERTY(bool showLdapContacts READ showLdapContacts WRITE setShowLdapContacts CONSTANT) public: - DECLARE_SORTFILTER_CLASS(bool mShowFavoritesOnly = false;) + DECLARE_SORTFILTER_CLASS(bool mShowFavoritesOnly = false; bool mShowLdapContacts = false;) + MagicSearchProxy(QObject *parent = Q_NULLPTR); ~MagicSearchProxy(); @@ -54,6 +56,9 @@ public: bool showFavoritesOnly() const; void setShowFavoritesOnly(bool show); + bool showLdapContacts() const; + void setShowLdapContacts(bool show); + void setList(QSharedPointer list); Q_INVOKABLE void setParentProxy(MagicSearchProxy *proxy); diff --git a/Linphone/model/search/MagicSearchModel.cpp b/Linphone/model/search/MagicSearchModel.cpp index e89d3e9b9..13fbcf646 100644 --- a/Linphone/model/search/MagicSearchModel.cpp +++ b/Linphone/model/search/MagicSearchModel.cpp @@ -23,6 +23,7 @@ #include #include "model/core/CoreModel.hpp" +#include "model/tool/ToolModel.hpp" #include "tool/Utils.hpp" DEFINE_ABSTRACT_OBJECT(MagicSearchModel) @@ -60,6 +61,10 @@ void MagicSearchModel::setAggregationFlag(LinphoneEnums::MagicSearchAggregation } void MagicSearchModel::onSearchResultsReceived(const std::shared_ptr &magicSearch) { + for (auto it : magicSearch->getLastSearch()) { + bool isLdap = (it->getSourceFlags() & (int)LinphoneEnums::MagicSearchSource::LdapServers) != 0; + if (isLdap && it->getFriend()) updateLdapFriendListWithFriend(it->getFriend()); + } emit searchResultsReceived(magicSearch->getLastSearch()); } @@ -67,3 +72,32 @@ void MagicSearchModel::onLdapHaveMoreResults(const std::shared_ptr &ldap) { // emit ldapHaveMoreResults(ldap); } + +// Store LDAP friends in separate list so they can still be retrieved by core->findFriend() for display names, +// but can be amended only by LDAP received friends. +// 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 &linphoneFriend) { + mustBeInLinphoneThread(log().arg(Q_FUNC_INFO)); + auto core = CoreModel::getInstance()->getCore(); + auto ldapFriendList = ToolModel::getLdapFriendList(); + for (auto address : linphoneFriend->getAddresses()) { + auto existingFriend = ldapFriendList->findFriendByAddress(address); + if (existingFriend) { + ldapFriendList->removeFriend(existingFriend); + ldapFriendList->addFriend(linphoneFriend); + return; + } + } + for (auto number : linphoneFriend->getPhoneNumbers()) { + auto existingFriend = ldapFriendList->findFriendByPhoneNumber(number); + if (existingFriend) { + ldapFriendList->removeFriend(existingFriend); + ldapFriendList->addFriend(linphoneFriend); + return; + } + } + ldapFriendList->addFriend(linphoneFriend); + emit CoreModel::getInstance()->friendCreated(linphoneFriend); +} diff --git a/Linphone/model/search/MagicSearchModel.hpp b/Linphone/model/search/MagicSearchModel.hpp index e2898aab2..3ab53f82c 100644 --- a/Linphone/model/search/MagicSearchModel.hpp +++ b/Linphone/model/search/MagicSearchModel.hpp @@ -58,6 +58,8 @@ private: virtual void onSearchResultsReceived(const std::shared_ptr &magicSearch) override; virtual void onLdapHaveMoreResults(const std::shared_ptr &magicSearch, const std::shared_ptr &ldap) override; + void updateLdapFriendListWithFriend(const std::shared_ptr &linphoneFriend); + signals: void searchResultsReceived(const std::list> &results); }; diff --git a/Linphone/model/tool/ToolModel.cpp b/Linphone/model/tool/ToolModel.cpp index 28f78cd6e..390881d8e 100644 --- a/Linphone/model/tool/ToolModel.cpp +++ b/Linphone/model/tool/ToolModel.cpp @@ -275,3 +275,22 @@ bool ToolModel::isLocal(const std::shared_ptr &conference, auto gruuAddress = findAccount(callAddress)->getContactAddress(); return deviceAddress->equal(gruuAddress); } + +std::shared_ptr ToolModel::getLdapFriendList() { + auto core = CoreModel::getInstance()->getCore(); + auto ldapFriendList = core->getFriendListByName("ldap_friends"); + if (!ldapFriendList) { + ldapFriendList = core->createFriendList(); + ldapFriendList->setDisplayName("ldap_friends"); + core->addFriendList(ldapFriendList); + } + return ldapFriendList; +} + +bool ToolModel::friendIsInLdapFriendList(const std::shared_ptr &f) { + auto ldapFriendList = getLdapFriendList(); + for (auto ldapFriend : ldapFriendList->getFriends()) { + if (f == ldapFriend) return true; + } + return false; +} diff --git a/Linphone/model/tool/ToolModel.hpp b/Linphone/model/tool/ToolModel.hpp index 4a5558a10..5ed0cb0bc 100644 --- a/Linphone/model/tool/ToolModel.hpp +++ b/Linphone/model/tool/ToolModel.hpp @@ -59,6 +59,9 @@ public: linphone::MediaEncryption = linphone::MediaEncryption::None, QString *errorMessage = nullptr); + static std::shared_ptr getLdapFriendList(); + static bool friendIsInLdapFriendList(const std::shared_ptr &f); + private: DECLARE_ABSTRACT_OBJECT }; diff --git a/Linphone/view/Control/Display/Contact/Avatar.qml b/Linphone/view/Control/Display/Contact/Avatar.qml index 7322a9e8f..b6fa3be3f 100644 --- a/Linphone/view/Control/Display/Contact/Avatar.qml +++ b/Linphone/view/Control/Display/Contact/Avatar.qml @@ -175,6 +175,10 @@ Loader{ shadowColor: DefaultStyle.grey_1000 shadowOpacity: 0.1 } + Connections { + target: mainItem.call?.core ? mainItem.call.core : null + onRemoteNameChanged: initialItem.initials = UtilsCpp.getInitials(mainItem.call.core.remoteName) + } } } Component{ diff --git a/Linphone/view/Control/Display/Contact/ContactListView.qml b/Linphone/view/Control/Display/Contact/ContactListView.qml index bad5100ab..9728a9c01 100644 --- a/Linphone/view/Control/Display/Contact/ContactListView.qml +++ b/Linphone/view/Control/Display/Contact/ContactListView.qml @@ -26,6 +26,7 @@ ListView { property bool displayNameCapitalization: true property bool showFavoritesOnly: false property bool showDefaultAddress: false + property bool showLdapContacts: false property var listProxy: MagicSearchProxy{} @@ -112,6 +113,7 @@ ListView { } aggregationFlag: mainItem.aggregationFlag parentProxy: mainItem.listProxy + showLdapContacts: mainItem.showLdapContacts sourceFlags: mainItem.sourceFlags onInitialized: { magicSearchProxy.forceUpdate() diff --git a/Linphone/view/Control/Popup/Notification/NotificationReceivedCall.qml b/Linphone/view/Control/Popup/Notification/NotificationReceivedCall.qml index 32fd14997..3098e45c8 100644 --- a/Linphone/view/Control/Popup/Notification/NotificationReceivedCall.qml +++ b/Linphone/view/Control/Popup/Notification/NotificationReceivedCall.qml @@ -49,8 +49,7 @@ Notification { } ColumnLayout { Text { - property var remoteAddress: UtilsCpp.getDisplayName(call.core.remoteAddress) - text: remoteAddress ? remoteAddress.value : "" + text: call.core.remoteName color: DefaultStyle.grey_600 font { pixelSize: 20 * DefaultStyle.dp diff --git a/Linphone/view/Page/Layout/Main/MainLayout.qml b/Linphone/view/Page/Layout/Main/MainLayout.qml index 90a04110c..8f7aed309 100644 --- a/Linphone/view/Page/Layout/Main/MainLayout.qml +++ b/Linphone/view/Page/Layout/Main/MainLayout.qml @@ -249,6 +249,7 @@ Item { actionLayoutVisible: true selectionEnabled: false showDefaultAddress: true + showLdapContacts: true Control.ScrollBar.vertical: scrollbar searchText: magicSearchBar.text diff --git a/Linphone/view/Page/Main/Call/CallPage.qml b/Linphone/view/Page/Main/Call/CallPage.qml index ac2849b8e..fef08f4b2 100644 --- a/Linphone/view/Page/Main/Call/CallPage.qml +++ b/Linphone/view/Page/Main/Call/CallPage.qml @@ -655,7 +655,12 @@ AbstractMainPage { contact: contactObj && contactObj.value || null conferenceInfo: mainItem.selectedRowHistoryGui && mainItem.selectedRowHistoryGui.core.conferenceInfo || null specificAddress: mainItem.selectedRowHistoryGui && mainItem.selectedRowHistoryGui.core.remoteAddress || "" - + Connections { + target: mainItem.selectedRowHistoryGui?.core ? mainItem.selectedRowHistoryGui.core : null + onDisplayNameChanged: { + mainItem.onSelectedRowHistoryGuiChanged() // to cover displayName & Avatar. + } + } buttonContent: PopupButton { id: detailOptions anchors.right: parent.right @@ -687,6 +692,7 @@ AbstractMainPage { textColor: DefaultStyle.main2_500main contentImageColor: DefaultStyle.main2_600 background: Item {} + visible: SettingsCpp.syncLdapContacts || !detailOptions.friendGui?.core?.isLdap onClicked: { detailOptions.close() if (detailOptions.friendGui) mainWindow.displayContactPage(contactDetail.contactAddress) diff --git a/Linphone/view/Page/Main/Contact/ContactPage.qml b/Linphone/view/Page/Main/Contact/ContactPage.qml index d6067de00..221282177 100644 --- a/Linphone/view/Page/Main/Contact/ContactPage.qml +++ b/Linphone/view/Page/Main/Contact/ContactPage.qml @@ -56,6 +56,7 @@ AbstractMainPage { MagicSearchProxy { id: allFriends + showLdapContacts: SettingsCpp.syncLdapContacts } function deleteContact(contact) { @@ -446,6 +447,7 @@ AbstractMainPage { button.topPadding: 10 * DefaultStyle.dp button.bottomPadding: 10 * DefaultStyle.dp button.onClicked: mainItem.editContact(mainItem.selectedContact) + button.visible: !mainItem.selectedContact?.core.readOnly property string contactAddress: contact ? contact.core.defaultAddress : "" property var computedContactNameObj: UtilsCpp.getDisplayName(contactAddress) property string computedContactName: computedContactNameObj ? computedContactNameObj.value : ""