From 67849d619b2da3e824e16da197ce9878dc9f2aa6 Mon Sep 17 00:00:00 2001 From: saurabh Date: Sat, 21 Feb 2026 14:35:09 +0530 Subject: [PATCH] Wire: Fix republish/like popup, correct profile counts, show followers, adopt defnax UI cleanup, fix GxsStatisticsProvider migration --- retroshare-gui/src/CMakeLists.txt | 3 - retroshare-gui/src/gui/NewsFeed.cpp | 11 +- retroshare-gui/src/gui/NewsFeed.h | 2 +- retroshare-gui/src/gui/Posted/PostedDialog.h | 2 +- .../src/gui/Posted/PostedUserNotify.cpp | 2 +- .../src/gui/Posted/PostedUserNotify.h | 2 +- .../src/gui/TheWire/PulseAddDialog.cpp | 1 + .../src/gui/TheWire/PulseViewGroup.cpp | 8 +- .../src/gui/TheWire/PulseViewGroup.ui | 34 + retroshare-gui/src/gui/TheWire/WireDialog.cpp | 170 +---- retroshare-gui/src/gui/TheWire/WireDialog.h | 34 +- .../src/gui/common/NotifyWidget.cpp | 65 -- retroshare-gui/src/gui/common/NotifyWidget.h | 83 --- retroshare-gui/src/gui/common/NotifyWidget.ui | 66 -- .../src/gui/feeds/WireNotifyGroupItem.cpp | 13 +- .../src/gui/feeds/WireNotifyGroupItem.h | 1 - .../src/gui/feeds/WireNotifyPostItem.cpp | 376 ++-------- .../src/gui/feeds/WireNotifyPostItem.h | 12 +- .../src/gui/feeds/WireNotifyPostItem.ui | 106 +-- retroshare-gui/src/gui/feeds/WirePostItem.cpp | 693 ------------------ retroshare-gui/src/gui/feeds/WirePostItem.h | 108 --- .../src/gui/gxs/GxsGroupFrameDialog.cpp | 5 +- .../src/gui/gxs/GxsGroupFrameDialog.h | 26 +- .../src/gui/gxs/GxsStatisticsProvider.cpp | 39 - .../src/gui/gxs/GxsStatisticsProvider.h | 53 +- retroshare-gui/src/gui/gxs/GxsUserNotify.h | 1 - .../src/gui/gxschannels/GxsChannelDialog.h | 2 +- .../gui/gxschannels/GxsChannelUserNotify.cpp | 2 +- .../gui/gxschannels/GxsChannelUserNotify.h | 3 +- .../src/gui/gxsforums/GxsForumsDialog.h | 2 +- .../src/gui/settings/rsharesettings.cpp | 4 +- retroshare-gui/src/retroshare-gui.pro | 3 - 32 files changed, 194 insertions(+), 1738 deletions(-) delete mode 100644 retroshare-gui/src/gui/common/NotifyWidget.cpp delete mode 100644 retroshare-gui/src/gui/common/NotifyWidget.h delete mode 100644 retroshare-gui/src/gui/common/NotifyWidget.ui delete mode 100644 retroshare-gui/src/gui/feeds/WirePostItem.cpp delete mode 100644 retroshare-gui/src/gui/feeds/WirePostItem.h diff --git a/retroshare-gui/src/CMakeLists.txt b/retroshare-gui/src/CMakeLists.txt index 6de5ceeba..71dd6770f 100644 --- a/retroshare-gui/src/CMakeLists.txt +++ b/retroshare-gui/src/CMakeLists.txt @@ -176,7 +176,6 @@ list( src/gui/common/FlowLayout.cpp src/gui/common/PictureFlow.cpp src/gui/common/ToasterNotify.cpp - src/gui/common/NotifyWidget.cpp src/gui/style/RSStyle.cpp src/gui/style/StyleDialog.cpp @@ -383,7 +382,6 @@ list( src/gui/common/RsCollectionDialog.ui src/gui/common/HeaderFrame.ui src/gui/common/RSFeedWidget.ui - src/gui/common/NotifyWidget.ui src/gui/style/StyleDialog.ui @@ -643,7 +641,6 @@ list( src/gui/common/FlowLayout.h src/gui/common/PictureFlow.h src/gui/common/ToasterNotify.h - src/gui/common/NotifyWidget.h src/gui/style/RSStyle.h src/gui/style/StyleDialog.h diff --git a/retroshare-gui/src/gui/NewsFeed.cpp b/retroshare-gui/src/gui/NewsFeed.cpp index aab329846..069548356 100644 --- a/retroshare-gui/src/gui/NewsFeed.cpp +++ b/retroshare-gui/src/gui/NewsFeed.cpp @@ -529,17 +529,8 @@ void NewsFeed::handleWireEvent(std::shared_ptr event) addFeedItem( new WireNotifyGroupItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, false, true, RsWireEventCode::NEW_WIRE)); break; case RsWireEventCode::NEW_POST: - addFeedItem( new WireNotifyPostItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, pe->mWireMsgId, false, true)); + addFeedItem( new WireNotifyPostItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, pe->mWireMsgId, true)); break; -// case RsWireEventCode::NEW_REPLY: -// addFeedItem( new WireNotifyPostItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, pe->mWireMsgId, false, true)); -// break; -// case RsWireEventCode::NEW_REPUBLISH: -// addFeedItem( new WireNotifyPostItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, pe->mWireMsgId, false, true)); -// break; -// case RsWireEventCode::NEW_LIKE: -// addFeedItem( new WireNotifyPostItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, pe->mWireMsgId, false, true)); -// break; case RsWireEventCode::WIRE_UPDATED: addFeedItem( new WireNotifyGroupItem(this, NEWSFEED_WIRELIST, pe->mWireGroupId, false, true, RsWireEventCode::WIRE_UPDATED)); break; diff --git a/retroshare-gui/src/gui/NewsFeed.h b/retroshare-gui/src/gui/NewsFeed.h index b1bc2d967..876eef95a 100644 --- a/retroshare-gui/src/gui/NewsFeed.h +++ b/retroshare-gui/src/gui/NewsFeed.h @@ -49,7 +49,7 @@ const uint32_t NEWSFEED_POSTEDNEWLIST = 0x000b; const uint32_t NEWSFEED_POSTEDMSGLIST = 0x000c; const uint32_t NEWSFEED_CIRCLELIST = 0x000d; const uint32_t NEWSFEED_CHANNELPUBKEYLIST= 0x000e; -const uint32_t NEWSFEED_WIRELIST = 0X000f; +const uint32_t NEWSFEED_WIRELIST = 0x0010; namespace Ui { class NewsFeed; diff --git a/retroshare-gui/src/gui/Posted/PostedDialog.h b/retroshare-gui/src/gui/Posted/PostedDialog.h index 433adbe93..6f348d218 100644 --- a/retroshare-gui/src/gui/Posted/PostedDialog.h +++ b/retroshare-gui/src/gui/Posted/PostedDialog.h @@ -54,7 +54,7 @@ private: /* GxsGroupFrameDialog */ virtual QString text(TextType type) override; virtual QString icon(IconType type) override; - virtual QString settingsGroupName() override{ return "PostedDialog"; } + virtual QString settingsGroupName() { return "PostedDialog"; } virtual GxsGroupDialog *createNewGroupDialog() override; virtual GxsGroupDialog *createGroupDialog(GxsGroupDialog::Mode mode, RsGxsGroupId groupId) override; virtual int shareKeyType() override; diff --git a/retroshare-gui/src/gui/Posted/PostedUserNotify.cpp b/retroshare-gui/src/gui/Posted/PostedUserNotify.cpp index ce6e49835..305bc6fac 100644 --- a/retroshare-gui/src/gui/Posted/PostedUserNotify.cpp +++ b/retroshare-gui/src/gui/Posted/PostedUserNotify.cpp @@ -23,7 +23,7 @@ #include "gui/MainWindow.h" #include "gui/common/FilesDefs.h" -PostedUserNotify::PostedUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsGroupFrameDialog *g, QObject *parent) : +PostedUserNotify::PostedUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsStatisticsProvider *g, QObject *parent) : GxsUserNotify(ifaceImpl, g, parent) { } diff --git a/retroshare-gui/src/gui/Posted/PostedUserNotify.h b/retroshare-gui/src/gui/Posted/PostedUserNotify.h index b7631bc37..26bb08e22 100644 --- a/retroshare-gui/src/gui/Posted/PostedUserNotify.h +++ b/retroshare-gui/src/gui/Posted/PostedUserNotify.h @@ -28,7 +28,7 @@ class PostedUserNotify : public GxsUserNotify Q_OBJECT public: - explicit PostedUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsGroupFrameDialog *g, QObject *parent = 0); + explicit PostedUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsStatisticsProvider *g, QObject *parent = 0); virtual bool hasSetting(QString *name, QString *group) override; diff --git a/retroshare-gui/src/gui/TheWire/PulseAddDialog.cpp b/retroshare-gui/src/gui/TheWire/PulseAddDialog.cpp index 77d0217ce..6e681329a 100644 --- a/retroshare-gui/src/gui/TheWire/PulseAddDialog.cpp +++ b/retroshare-gui/src/gui/TheWire/PulseAddDialog.cpp @@ -307,6 +307,7 @@ void PulseAddDialog::setReplyTo(const RsGxsGroupId &grpId, const RsGxsMessageId * Qt::QueuedConnection is important! */ + mGroup = *pGroup; setReplyTo(*pPulse, pPulse, pGroup->mMeta.mGroupName, replyType); }, this ); diff --git a/retroshare-gui/src/gui/TheWire/PulseViewGroup.cpp b/retroshare-gui/src/gui/TheWire/PulseViewGroup.cpp index f962daaeb..39739a6d9 100644 --- a/retroshare-gui/src/gui/TheWire/PulseViewGroup.cpp +++ b/retroshare-gui/src/gui/TheWire/PulseViewGroup.cpp @@ -112,13 +112,17 @@ void PulseViewGroup::setup() uint32_t replies = mGroup->mRefReplies; uint32_t republishes = mGroup->mRefRepublishes; uint32_t likes = mGroup->mRefLikes; - // uint32_t following = mGroup->mGroupFollowing; // TODO: field not yet in RsWireGroup label_extra_pulses->setText(BoldString(ToNumberUnits(pulses))); label_extra_replies->setText(BoldString(ToNumberUnits(replies))); label_extra_republishes->setText(BoldString(ToNumberUnits(republishes))); label_extra_likes->setText(BoldString(ToNumberUnits(likes))); - // label_extra_following->setText(BoldString(ToNumberUnits(following))); // TODO: enable when mGroupFollowing added + + uint32_t following = mGroup->mGroupFollowing; + label_extra_following->setText(BoldString(ToNumberUnits(following))); + + uint32_t followers = mGroup->mGroupFollowers; + label_extra_followers->setText(BoldString(ToNumberUnits(followers))); // hide follow button but keep copy link visible. followButton->setVisible(false); diff --git a/retroshare-gui/src/gui/TheWire/PulseViewGroup.ui b/retroshare-gui/src/gui/TheWire/PulseViewGroup.ui index caf6533ff..bb4075bd3 100644 --- a/retroshare-gui/src/gui/TheWire/PulseViewGroup.ui +++ b/retroshare-gui/src/gui/TheWire/PulseViewGroup.ui @@ -548,6 +548,40 @@ + + + + + + <html><head/><body><p><span style=" font-weight:600;">0</span></p></body></html> + + + + + + + <html><head/><body><p><span style=" color:#2e3436;">Followers</span></p></body></html> + + + + + + + Qt::Horizontal + + + QSizePolicy::Preferred + + + + 40 + 20 + + + + + + diff --git a/retroshare-gui/src/gui/TheWire/WireDialog.cpp b/retroshare-gui/src/gui/TheWire/WireDialog.cpp index 1d83274cb..10d0c6b4d 100644 --- a/retroshare-gui/src/gui/TheWire/WireDialog.cpp +++ b/retroshare-gui/src/gui/TheWire/WireDialog.cpp @@ -25,7 +25,6 @@ #include "gui/settings/rsharesettings.h" #include "gui/gxs/GxsIdDetails.h" #include "gui/common/FilesDefs.h" -#include "gui/common/NotifyWidget.h" #include "gui/gxs/GxsStatisticsProvider.h" #include "gui/gxs/GxsGroupShareKey.h" @@ -62,18 +61,20 @@ // #define GROUP_SET_RECOMMENDED (5) -#define WIRE_TOKEN_TYPE_SUBSCRIBE_CHANGE 1 -#define TOKEN_TYPE_GROUP_SUMMARY 1 - /** Constructor */ WireDialog::WireDialog(QWidget *parent) - : GxsStatisticsProvider(rsWire, settingsGroupName(),parent, true), mGroupSet(GROUP_SET_ALL) - , mAddDialog(nullptr), mGroupSelected(nullptr), mWireQueue(nullptr) + : MainPage(parent), mGroupSet(GROUP_SET_ALL) + , mAddDialog(nullptr), mGroupSelected(nullptr) , mHistoryIndex(-1), mEventHandlerId(0), mSortAscending(false) , mAccountSortType(0), mHideInactiveAccounts(false) { ui.setupUi(this); + mInterface = rsWire; + mSettingsName = "WireDialog"; + mDistSyncAllowed = true; + mStateHelper = nullptr; + connect( ui.toolButton_createAccount, SIGNAL(clicked()), this, SLOT(createGroup())); connect( ui.toolButton_createPulse, SIGNAL(clicked()), this, SLOT(createPulse())); connect( ui.toolButton_home, SIGNAL(clicked()), this, SLOT(showHomeFeed())); @@ -126,8 +127,6 @@ WireDialog::WireDialog(QWidget *parent) timer->connect(timer, SIGNAL(timeout()), this, SLOT(checkUpdate())); timer->start(1000); - /* setup TokenQueue */ - mWireQueue = new TokenQueue(rsWire->getTokenService(), this); mCountChildMsgs = false; mShouldUpdateGroupStatistics = false; mDistSyncAllowed = true; @@ -195,7 +194,6 @@ WireDialog::~WireDialog() processSettings(false); clearTwitterView(); - delete(mWireQueue); rsEvents->unregisterEventsHandler(mEventHandlerId); } @@ -435,14 +433,12 @@ void WireDialog::subscribe(RsGxsGroupId &groupId) { uint32_t token; rsWire->subscribeToGroup(token, groupId, true); - mWireQueue->queueRequest(token, TOKENREQ_GROUPINFO, RS_TOKREQ_ANSTYPE_ACK, WIRE_TOKEN_TYPE_SUBSCRIBE_CHANGE); } void WireDialog::unsubscribe(RsGxsGroupId &groupId) { uint32_t token; rsWire->subscribeToGroup(token, groupId, false); - mWireQueue->queueRequest(token, TOKENREQ_GROUPINFO, RS_TOKREQ_ANSTYPE_ACK, WIRE_TOKEN_TYPE_SUBSCRIBE_CHANGE); } void WireDialog::notifyGroupSelection(WireGroupItem *item) @@ -734,25 +730,12 @@ void WireDialog::requestGroupData() std::cerr << "WireDialog::requestGroupData()"; std::cerr << std::endl; - RsTokReqOptions opts; - uint32_t token; - opts.mReqType = GXS_REQUEST_TYPE_GROUP_DATA; - mWireQueue->requestGroupInfo(token, RS_TOKREQ_ANSTYPE_DATA, opts, 0); -} - -bool WireDialog::loadGroupData(const uint32_t &token) -{ - std::cerr << "WireDialog::loadGroupData()"; - std::cerr << std::endl; - std::vector groups; - rsWire->getGroupData(token, groups); + rsWire->getGroups({}, groups); - // save list of groups. updateGroups(groups); showGroups(); - // check for pending navigation if (!mNavigatePendingGroupId.isNull()) { if (!mNavigatePendingMsgId.isNull()) { requestPulseFocus(mNavigatePendingGroupId, mNavigatePendingMsgId); @@ -762,7 +745,6 @@ bool WireDialog::loadGroupData(const uint32_t &token) mNavigatePendingGroupId.clear(); mNavigatePendingMsgId.clear(); } - return true; } rstime_t WireDialog::getFilterTimestamp() @@ -788,60 +770,6 @@ rstime_t WireDialog::getFilterTimestamp() return filterTimestamp; } -void WireDialog::acknowledgeGroup(const uint32_t &token, const uint32_t &userType) -{ - /* reload groups */ - std::cerr << "WireDialog::acknowledgeGroup(usertype: " << userType << ")"; - std::cerr << std::endl; - - RsGxsGroupId grpId; - rsWire->acknowledgeGrp(token, grpId); - - refreshGroups(); -} - - -/**************************** Request / Response Filling of Data ************************/ - -void WireDialog::loadRequest(const TokenQueue *queue, const TokenRequest &req) -{ - std::cerr << "WireDialog::loadRequest()"; - std::cerr << std::endl; - - if (queue == mWireQueue) - { - /* now switch on req */ - switch(req.mType) - { - case TOKENREQ_GROUPINFO: - switch(req.mAnsType) - { - case RS_TOKREQ_ANSTYPE_DATA: - loadGroupData(req.mToken); - break; - case RS_TOKREQ_ANSTYPE_ACK: - acknowledgeGroup(req.mToken, req.mUserType); - break; - default: - std::cerr << "WireDialog::loadRequest() ERROR: GROUP: INVALID ANS TYPE"; - std::cerr << std::endl; - break; - } - break; - default: - std::cerr << "WireDialog::loadRequest() ERROR: INVALID TYPE"; - std::cerr << std::endl; - break; - } - } -} - - -/**************************** Request / Response Filling of Data ************************/ - - - - /****************************************************************************************/ // TWITTER VIEW. @@ -894,55 +822,10 @@ void WireDialog::PVHrepublish(const RsGxsGroupId &groupId, const RsGxsMessageId std::cerr << " MsgId: " << msgId; std::cerr << std::endl; - int idx = ui.groupChooser->currentIndex(); - if (idx < 0 || idx >= (int)mOwnGroups.size()) { - std::cerr << "WireDialog::PVHrepublish() No own group selected"; - std::cerr << std::endl; - QMessageBox::warning(this, tr("RetroShare"), tr("Please select your Wire account first"), QMessageBox::Ok); - return; - } - - RsGxsGroupId replyWith = mOwnGroups[idx].mMeta.mGroupId; - setCursor(Qt::WaitCursor); - - RsThread::async([this, groupId, msgId, replyWith]() + if (setupPulseAddDialog()) { - RsWirePulseSPtr origPulse; - if (!rsWire->getWirePulse(groupId, msgId, origPulse)) - { - std::cerr << "WireDialog::PVHrepublish() failed to fetch original pulse"; - std::cerr << std::endl; - RsQThreadUtils::postToObject([this]() - { - setCursor(Qt::ArrowCursor); - }, this); - return; - } - - RsWirePulseSPtr pPulse(new RsWirePulse()); - pPulse->mSentiment = origPulse->mSentiment; - pPulse->mPulseText = origPulse->mPulseText; - pPulse->mImage1 = origPulse->mImage1; - pPulse->mImage2 = origPulse->mImage2; - pPulse->mImage3 = origPulse->mImage3; - pPulse->mImage4 = origPulse->mImage4; - - RsGxsMessageId targetMsgId = origPulse->mMeta.mOrigMsgId; - if (targetMsgId.isNull()) { - targetMsgId = msgId; - } - - bool success = rsWire->createReplyPulse(groupId, targetMsgId, replyWith, - WIRE_PULSE_TYPE_REPUBLISH, pPulse); - - RsQThreadUtils::postToObject([this, success]() - { - setCursor(Qt::ArrowCursor); - if (!success) { - std::cerr << "WireDialog::PVHrepublish() FAILED" << std::endl; - } - }, this); - }); + mAddDialog->setReplyTo(groupId, msgId, WIRE_PULSE_TYPE_REPUBLISH); + } } void WireDialog::PVHlike(const RsGxsGroupId &groupId, const RsGxsMessageId &msgId) @@ -951,34 +834,10 @@ void WireDialog::PVHlike(const RsGxsGroupId &groupId, const RsGxsMessageId &msgI std::cerr << " MsgId: " << msgId; std::cerr << std::endl; - int idx = ui.groupChooser->currentIndex(); - if (idx < 0 || idx >= (int)mOwnGroups.size()) { - std::cerr << "WireDialog::PVHlike() No own group selected"; - std::cerr << std::endl; - QMessageBox::warning(this, tr("RetroShare"), tr("Please select your Wire account first"), QMessageBox::Ok); - return; - } - - RsGxsGroupId replyWith = mOwnGroups[idx].mMeta.mGroupId; - setCursor(Qt::WaitCursor); - - RsThread::async([this, groupId, msgId, replyWith]() + if (setupPulseAddDialog()) { - RsWirePulseSPtr pPulse(new RsWirePulse()); - pPulse->mSentiment = WIRE_PULSE_SENTIMENT_NO_SENTIMENT; - pPulse->mPulseText = ""; - - bool success = rsWire->createReplyPulse(groupId, msgId, replyWith, - WIRE_PULSE_TYPE_LIKE, pPulse); - - RsQThreadUtils::postToObject([this, success]() - { - setCursor(Qt::ArrowCursor); - if (!success) { - std::cerr << "WireDialog::PVHlike() FAILED" << std::endl; - } - }, this); - }); + mAddDialog->setReplyTo(groupId, msgId, WIRE_PULSE_TYPE_LIKE); + } } void WireDialog::PVHviewGroup(const RsGxsGroupId &groupId) @@ -1022,7 +881,6 @@ void WireDialog::PVHfollow(const RsGxsGroupId &groupId) uint32_t token; rsWire->subscribeToGroup(token, groupId, true); - mWireQueue->queueRequest(token, TOKENREQ_GROUPINFO, RS_TOKREQ_ANSTYPE_ACK, WIRE_TOKEN_TYPE_SUBSCRIBE_CHANGE); } void WireDialog::PVHrate(const RsGxsId &authorId) diff --git a/retroshare-gui/src/gui/TheWire/WireDialog.h b/retroshare-gui/src/gui/TheWire/WireDialog.h index 0557d3002..d3ec5347d 100644 --- a/retroshare-gui/src/gui/TheWire/WireDialog.h +++ b/retroshare-gui/src/gui/TheWire/WireDialog.h @@ -36,7 +36,9 @@ #include "gui/TheWire/PulseReply.h" #include "gui/gxs/GxsStatisticsProvider.h" -#include "util/TokenQueue.h" +class UIStateHelper; +class GxsMessageFrameWidget; +class RsGxsIfaceHelper; #define IMAGE_WIRE ":/icons/wire.png" @@ -68,7 +70,7 @@ public: }; //--------------------------------------------------------- -class WireDialog : public GxsStatisticsProvider, public TokenResponse, public WireGroupHolder, public PulseViewHolder +class WireDialog : public MainPage, public GxsStatisticsProvider, public WireGroupHolder, public PulseViewHolder { Q_OBJECT @@ -118,16 +120,16 @@ public: void showGroupsPulses(const std::list& groupIds); void postGroupsPulses(std::list pulses); - void getServiceStatistics(GxsServiceStatistic& stats) const ; + void getServiceStatistics(GxsServiceStatistic& stats) const override; - virtual bool navigate(const RsGxsGroupId &groupId, const RsGxsMessageId& msgId) override; + virtual bool navigate(const RsGxsGroupId &groupId, const RsGxsMessageId& msgId); protected: - bool getGroupStatistics(const RsGxsGroupId& groupId,GxsGroupStatistic& stat) override; + bool getGroupStatistics(const RsGxsGroupId& groupId,GxsGroupStatistic& stat); UserNotify *createUserNotify(QObject *parent) override; - virtual void updateGroupStatistics(const RsGxsGroupId &groupId) override; - virtual void updateGroupStatisticsReal(const RsGxsGroupId &groupId) override; + virtual void updateGroupStatistics(const RsGxsGroupId &groupId); + virtual void updateGroupStatisticsReal(const RsGxsGroupId &groupId); private slots: @@ -170,19 +172,13 @@ private: // Loading Data. void requestGroupData(); - bool loadGroupData(const uint32_t &token); - void acknowledgeGroup(const uint32_t &token, const uint32_t &userType); - virtual void loadRequest(const TokenQueue *queue, const TokenRequest &req) override; - - virtual QString settingsGroupName() override{ return "WireDialog"; } - virtual GxsMessageFrameWidget *messageWidget(const RsGxsGroupId &groupId) override; + GxsMessageFrameWidget *messageWidget(const RsGxsGroupId &groupId); int mGroupSet; PulseAddDialog *mAddDialog; WireGroupItem *mGroupSelected; - TokenQueue *mWireQueue; std::map mAllGroups; std::vector mOwnGroups; @@ -197,9 +193,17 @@ private: int mAccountSortType; bool mHideInactiveAccounts; - // pending navigation (for when navigate called before groups loaded) + // Members for GxsStatisticsProvider interface support + QString mSettingsName; + RsGxsIfaceHelper *mInterface; + bool mDistSyncAllowed; + std::map mCachedGroupStats; + bool mShouldUpdateGroupStatistics; + std::set mGroupStatisticsToUpdate; + bool mCountChildMsgs; RsGxsGroupId mNavigatePendingGroupId; RsGxsMessageId mNavigatePendingMsgId; + UIStateHelper *mStateHelper; /* UI - from Designer */ Ui::WireDialog ui; diff --git a/retroshare-gui/src/gui/common/NotifyWidget.cpp b/retroshare-gui/src/gui/common/NotifyWidget.cpp deleted file mode 100644 index 9fe2f4abf..000000000 --- a/retroshare-gui/src/gui/common/NotifyWidget.cpp +++ /dev/null @@ -1,65 +0,0 @@ -#include "NotifyWidget.h" -#include "ui_NotifyWidget.h" -#include "RSTreeWidgetItem.h" - -#define ROLE_ID Qt::UserRole -#define ROLE_NAME Qt::UserRole + 1 -#define ROLE_DESCRIPTION Qt::UserRole + 2 -#define ROLE_SUBSCRIBE_FLAGS Qt::UserRole + 3 -#define ROLE_COLOR Qt::UserRole + 4 -#define ROLE_REQUEST_ID Qt::UserRole + 5 -#define ROLE_SORT Qt::UserRole + 6 - -NotifyWidget::NotifyWidget(QWidget *parent) : - QWidget(parent), - ui(new Ui::NotifyWidget) -{ - ui->setupUi(this); -} - -NotifyWidget::~NotifyWidget() -{ - delete ui; -} - -void NotifyWidget::setUnreadCount(QTreeWidgetItem *item, int unreadCount) -{ - if (item == NULL) { - return; - } - - QFont itFont = item->font(GTW_COLUMN_NAME); - - if (unreadCount) { - item->setText(GTW_COLUMN_UNREAD, QString::number(unreadCount)); - itFont.setBold(true); - } else { - item->setText(GTW_COLUMN_UNREAD, ""); - itFont.setBold(false); - } - item->setData(GTW_COLUMN_UNREAD, ROLE_SORT, unreadCount); - - item->setFont(GTW_COLUMN_NAME, itFont); -} - -QTreeWidgetItem *NotifyWidget::getItemFromId(const QString &id) -{ - if (id.isEmpty()) { - return NULL; - } - - /* Search exisiting item */ - QTreeWidgetItemIterator itemIterator(ui->treeWidget); - QTreeWidgetItem *item; - while ((item = *itemIterator) != NULL) { - ++itemIterator; - - if (item->parent() == NULL) { - continue; - } - if (item->data(GTW_COLUMN_DATA, ROLE_ID).toString() == id) { - return item; - } - } - return NULL ; -} diff --git a/retroshare-gui/src/gui/common/NotifyWidget.h b/retroshare-gui/src/gui/common/NotifyWidget.h deleted file mode 100644 index 55c536439..000000000 --- a/retroshare-gui/src/gui/common/NotifyWidget.h +++ /dev/null @@ -1,83 +0,0 @@ -/******************************************************************************* - * gui/common/NotifyWidget.h * - * * - * Copyright (C) 2010, Retroshare Team * - * * - * This program is free software: you can redistribute it and/or modify * - * it under the terms of the GNU Affero General Public License as * - * published by the Free Software Foundation, either version 3 of the * - * License, or (at your option) any later version. * - * * - * This program is distributed in the hope that it will be useful, * - * but WITHOUT ANY WARRANTY; without even the implied warranty of * - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * - * GNU Affero General Public License for more details. * - * * - * You should have received a copy of the GNU Affero General Public License * - * along with this program. If not, see . * - * * - *******************************************************************************/ - -#ifndef NOTIFYWIDGET_H -#define NOTIFYWIDGET_H - -#include -#include -#include - -#include - -#define GTW_COLUMN_NAME 0 -#define GTW_COLUMN_UNREAD 1 -#define GTW_COLUMN_POSTS 2 -#define GTW_COLUMN_POPULARITY 3 -#define GTW_COLUMN_LAST_POST 4 -#define GTW_COLUMN_SEARCH_SCORE 5 -#define GTW_COLUMN_DESCRIPTION 6 -#define GTW_COLUMN_COUNT 7 -#define GTW_COLUMN_DATA GTW_COLUMN_NAME - -namespace Ui { -class NotifyWidget; -} - -//class GroupItemInfo -//{ -//public: -// GroupItemInfo() -// : popularity(0), publishKey(false), adminKey(false) -// , subscribeFlags(0), max_visible_posts(0) -// {} - -//public: -// QString id; -// QString name; -// QString description; -// int popularity; -// QDateTime lastpost; -// QIcon icon; -// bool publishKey; -// bool adminKey; -// quint32 subscribeFlags; -// quint32 max_visible_posts ; -// std::set context_strings; -//}; - -class NotifyWidget : public QWidget -{ - Q_OBJECT - -public: - NotifyWidget(QWidget *parent = nullptr); - ~NotifyWidget(); - - // Set the unread count of an item - void setUnreadCount(QTreeWidgetItem *item, int unreadCount); - QTreeWidgetItem *getItemFromId(const QString &id); - -private: - Ui::NotifyWidget *ui; - -}; - -#endif // NOTIFYWIDGET_H diff --git a/retroshare-gui/src/gui/common/NotifyWidget.ui b/retroshare-gui/src/gui/common/NotifyWidget.ui deleted file mode 100644 index 6429f4258..000000000 --- a/retroshare-gui/src/gui/common/NotifyWidget.ui +++ /dev/null @@ -1,66 +0,0 @@ - - - NotifyWidget - - - - 0 - 0 - 400 - 300 - - - - Form - - - - - - true - - - - 0 - 0 - - - - - 11 - - - - Qt::CustomContextMenu - - - QAbstractItemView::NoEditTriggers - - - - 19 - 19 - - - - true - - - - 1 - - - - - - - - - RSTreeWidget - QTreeWidget -
gui/common/RSTreeWidget.h
-
-
- - -
diff --git a/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.cpp b/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.cpp index 44d145066..7a0674d09 100644 --- a/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.cpp +++ b/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.cpp @@ -43,15 +43,6 @@ WireNotifyGroupItem::WireNotifyGroupItem(FeedHolder *feedHolder, uint32_t feedId addEventHandler(); } -WireNotifyGroupItem::WireNotifyGroupItem(FeedHolder *feedHolder, uint32_t feedId, const RsWireGroup &group, bool isHome, bool autoUpdate, RsWireEventCode eventCode) : - GxsGroupFeedItem(feedHolder, feedId, group.mMeta.mGroupId, isHome, rsWire, autoUpdate), - mEventCode(eventCode) -{ - setup(); - setGroup(group); - addEventHandler(); -} - void WireNotifyGroupItem::addEventHandler() { mEventHandlerId = 0; @@ -68,6 +59,8 @@ void WireNotifyGroupItem::addEventHandler() { case RsWireEventCode::FOLLOW_STATUS_CHANGED: case RsWireEventCode::WIRE_UPDATED: + mGroup = RsWireGroup(); + requestGroup(); break; default: break; @@ -137,6 +130,7 @@ void WireNotifyGroupItem::loadGroup() if(!rsWire->getGroups(groupIds,groups)) { RsErr() << "WireNotifyGroupItem::loadGroup() ERROR getting data" << std::endl; + deferred_update(); return; } @@ -144,6 +138,7 @@ void WireNotifyGroupItem::loadGroup() { std::cerr << "WireNotifyGroupItem::loadGroup() Wrong number of Items"; std::cerr << std::endl; + deferred_update(); return; } RsWireGroup group(groups[0]); diff --git a/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.h b/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.h index d8b695d31..7110feb4f 100644 --- a/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.h +++ b/retroshare-gui/src/gui/feeds/WireNotifyGroupItem.h @@ -37,7 +37,6 @@ class WireNotifyGroupItem : public GxsGroupFeedItem public: /** Default Constructor */ WireNotifyGroupItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId &groupId, bool isHome, bool autoUpdate, RsWireEventCode eventCode = RsWireEventCode::NEW_WIRE); - WireNotifyGroupItem(FeedHolder *feedHolder, uint32_t feedId, const RsWireGroup &group, bool isHome, bool autoUpdate, RsWireEventCode eventCode = RsWireEventCode::NEW_WIRE); ~WireNotifyGroupItem(); bool setGroup(const RsWireGroup &group); diff --git a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.cpp b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.cpp index 786d8ede5..824af3131 100644 --- a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.cpp +++ b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.cpp @@ -35,37 +35,14 @@ #include #include -WireNotifyPostItem::WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGroupMetaData& group_meta, const RsGxsMessageId &messageId, bool isHome, bool autoUpdate,const std::set& older_versions) : - GxsFeedItem(feedHolder, feedId, group_meta.mGroupId, messageId, isHome, rsWire, autoUpdate), - mGroupMeta(group_meta) +WireNotifyPostItem::WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool autoUpdate, const std::set &older_versions) : + GxsFeedItem(feedHolder, feedId, groupId, messageId, false, rsWire, autoUpdate) { + mLoadingStatus = LOADING_STATUS_NO_DATA; mLoadingGroup = false; mLoadingMessage = false; mLoadingComment = false; - mPulse.mMeta.mMsgId = messageId; // useful for uniqueIdentifer() before the post is loaded - mPulse.mMeta.mGroupId = mGroupMeta.mGroupId; - - QVector v; - //bool self = false; - - for(std::set::const_iterator it(older_versions.begin());it!=older_versions.end();++it) - v.push_back(*it) ; - - if(older_versions.find(messageId) == older_versions.end()) - v.push_back(messageId); - - setMessageVersions(v) ; - setup(); - - // no call to loadGroup() here because we have it already. -} - -WireNotifyPostItem::WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool isHome, bool autoUpdate, const std::set &older_versions) : - GxsFeedItem(feedHolder, feedId, groupId, messageId, isHome, rsWire, autoUpdate) // this one should be in GxsFeedItem -{ - mPulse.mMeta.mMsgId = messageId; // useful for uniqueIdentifer() before the post is loaded - QVector v; //bool self = false; @@ -77,8 +54,6 @@ WireNotifyPostItem::WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, setMessageVersions(v) ; setup(); - - loadGroup(); } void WireNotifyPostItem::paintEvent(QPaintEvent *e) @@ -86,17 +61,27 @@ void WireNotifyPostItem::paintEvent(QPaintEvent *e) /* This method employs a trick to trigger a deferred loading. The post and group is requested only * when actually displayed on the screen. */ - if(!mLoaded) - { - mLoaded = true ; + if(mLoadingStatus != LOADING_STATUS_FILLED && !mGroupMeta.mGroupId.isNull() && !mPulse.mMeta.mMsgId.isNull() ) + mLoadingStatus = LOADING_STATUS_HAS_DATA; - std::set older_versions; // not so nice. We need to use std::set everywhere - for(auto& m:messageVersions()) - older_versions.insert(m); + if(mGroupMeta.mGroupId.isNull() && !mLoadingGroup) + requestGroup(); - fill(); + if(mPulse.mMeta.mMsgId.isNull() && !mLoadingMessage) requestMessage(); - requestComment(); + + switch(mLoadingStatus) + { + case LOADING_STATUS_FILLED: + case LOADING_STATUS_NO_DATA: + default: + break; + + case LOADING_STATUS_HAS_DATA: + fill(); + setGroup(mGroup); + mLoadingStatus = LOADING_STATUS_FILLED; + break; } GxsFeedItem::paintEvent(e) ; @@ -104,7 +89,7 @@ void WireNotifyPostItem::paintEvent(QPaintEvent *e) WireNotifyPostItem::~WireNotifyPostItem() { - auto timeout = std::chrono::steady_clock::now() + std::chrono::milliseconds(300); + auto timeout = std::chrono::steady_clock::now() + std::chrono::milliseconds(GROUP_ITEM_LOADING_TIMEOUT_ms); while( (mLoadingGroup || mLoadingMessage || mLoadingComment) && std::chrono::steady_clock::now() < timeout) @@ -139,11 +124,6 @@ void WireNotifyPostItem::setup() // ui->logoLabel->setPixmap(FilesDefs::getPixmapFromQtResourcePath(":/images/thumb-default-video.png")); //ui->warn_image_label->setPixmap(FilesDefs::getPixmapFromQtResourcePath(":/images/status_unknown.png")); ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-unread.png")); -// ui->voteUpButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/vote_up.png")); -// ui->voteDownButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/vote_down.png")); -// ui->downloadButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/download.png")); -// ui->playButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/play.png")); - ui->commentButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/comment.png")); //ui->editButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/pencil-edit-button.png")); // ui->copyLinkButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/copy.png")); // ui->expandButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/down-arrow.png")); @@ -154,14 +134,12 @@ void WireNotifyPostItem::setup() mInFill = false; mCloseOnRead = false; - mLoaded = false; /* clear ui */ ui->titleLabel->setText(tr("Loading...")); ui->titleLabel->setOpenExternalLinks(false); //To get linkActivated working connect(ui->titleLabel, SIGNAL(linkActivated(QString)), this, SLOT(on_linkActivated(QString))); ui->datetimelabel->clear(); - ui->filelabel->clear(); // ui->newCommentLabel->hide(); // ui->commLabel->hide(); @@ -171,32 +149,15 @@ void WireNotifyPostItem::setup() /* specific */ connect(ui->readAndClearButton, SIGNAL(clicked()), this, SLOT(readAndClearItem())); - connect(ui->unsubscribeButton, SIGNAL(clicked()), this, SLOT(unsubscribeChannel())); + connect(ui->unsubscribeButton, SIGNAL(clicked()), this, SLOT(unsubscribe())); - connect(ui->downloadButton, SIGNAL(clicked()), this, SLOT(download())); - // HACK FOR NOW. - ui->commentButton->hide();// hidden until properly enabled. - connect(ui->commentButton, SIGNAL(clicked()), this, SLOT(loadComments())); - - connect(ui->playButton, SIGNAL(clicked()), this, SLOT(play(void))); //connect(ui->editButton, SIGNAL(clicked()), this, SLOT(edit(void))); connect(ui->copyLinkButton, SIGNAL(clicked()), this, SLOT(copyMessageLink())); connect(ui->readButton, SIGNAL(toggled(bool)), this, SLOT(readToggled(bool))); - // hide voting buttons, backend is not implemented yet - ui->voteUpButton->hide(); - ui->voteDownButton->hide(); - //connect(ui-> voteUpButton, SIGNAL(clicked()), this, SLOT(makeUpVote())); - //connect(ui->voteDownButton, SIGNAL(clicked()), this, SLOT(makeDownVote())); - - ui->scoreLabel->hide(); - // hide unsubscribe button not necessary ui->unsubscribeButton->hide(); - - ui->downloadButton->hide(); - ui->playButton->hide(); //ui->warn_image_label->hide(); //ui->warning_label->hide(); @@ -265,10 +226,8 @@ void WireNotifyPostItem::loadMessage() if (!rsWire->getWirePulse(grpId, msgId, pPulse)) { RsErr() << "WireNotifyPostItem::loadMessage() ERROR getting pulse" << std::endl; - RsQThreadUtils::postToObject([this]() - { - mLoadingMessage = false; - }, this); + mLoadingMessage = false; + deferred_update(); return; } @@ -281,15 +240,18 @@ void WireNotifyPostItem::loadMessage() RsQThreadUtils::postToObject([pulse, this]() { - setPost(pulse); + mPulse = pulse; mLoadingMessage = false; + update(); // triggers paintEvent if needed }, this); } else { RsQThreadUtils::postToObject([this]() { + removeItem(); mLoadingMessage = false; + update(); }, this); } }); @@ -297,45 +259,7 @@ void WireNotifyPostItem::loadMessage() void WireNotifyPostItem::loadComment() { -#ifdef DEBUG_ITEM - std::cerr << "WireNotifyPostItem::loadComment()"; - std::cerr << std::endl; -#endif -// mLoadingComment = true; - -// RsThread::async([this]() -// { -// // 1 - get group data - -// std::set msgIds; - -// for(auto MsgId: messageVersions()) -// msgIds.insert(MsgId); - -// std::vector posts; -// std::vector comments; - -// if(! rsGxsChannels->getChannelComments( groupId(),msgIds,comments)) -// { -// RsErr() << "GxsGxsChannelGroupItem::loadGroup() ERROR getting data" << std::endl; -// return; -// } - -// int comNb = comments.size(); - -// RsQThreadUtils::postToObject( [comNb,this]() -// { -// QString sComButText = tr("Comment"); -// if (comNb == 1) -// sComButText = sComButText.append("(1)"); -// else if(comNb > 1) -// sComButText = tr("Comments ").append("(%1)").arg(comNb); - -// ui->commentButton->setText(sComButText); -// mLoadingComment = false; - -// }, this ); -// }); + // TODO: implement Wire comment loading when Wire comments are supported } void WireNotifyPostItem::loadGroup() @@ -357,6 +281,8 @@ void WireNotifyPostItem::loadGroup() if(!rsWire->getGroups(groupIds,groups)) // would be better to call channel Summaries for a single group { RsErr() << "WireNotifyPostItem::loadGroup() ERROR getting data" << std::endl; + mLoadingGroup = false; + deferred_update(); return; } @@ -364,6 +290,8 @@ void WireNotifyPostItem::loadGroup() { std::cerr << "WireNotifyPostItem::loadGroup() Wrong number of Items"; std::cerr << std::endl; + mLoadingGroup = false; + deferred_update(); return; } RsWireGroup group = groups[0]; @@ -374,91 +302,16 @@ void WireNotifyPostItem::loadGroup() * thread, for example to update the data model with new information * after a blocking call to RetroShare API complete */ + mGroup = group; mGroupMeta = group.mMeta; mLoadingGroup = false; - setGroup(group); + + update(); // triggers paintEvent if needed }, this ); }); } -//void WireNotifyPostItem::updateItem() -//{ -// /* fill in */ - -//#ifdef DEBUG_ITEM -// std::cerr << "WireNotifyPostItem::updateItem()"; -// std::cerr << std::endl; -//#endif - -// int msec_rate = 10000; - -// int downloadCount = 0; -// int downloadStartable = 0; -// int playCount = 0; -// int playStartable = 0; -// bool startable; -// bool loopAgain = false; - -// /* Very slow Tick to check when all files are downloaded */ -// std::list::iterator it; -// for(it = mFileItems.begin(); it != mFileItems.end(); ++it) -// { -// SubFileItem *item = *it; - -// if (item->isDownloadable(startable)) { -// ++downloadCount; -// if (startable) { -// ++downloadStartable; -// } -// } -// if (item->isPlayable(startable)) { -// ++playCount; -// if (startable) { -// ++playStartable; -// } -// } - -// if (!item->done()) -// { -// /* loop again */ -// loopAgain = true; -// } -// } - -// if (downloadCount) { -// ui->downloadButton->show(); - -// if (downloadStartable) { -// ui->downloadButton->setEnabled(true); -// } else { -// ui->downloadButton->setEnabled(false); -// } -// } else { -// ui->downloadButton->hide(); -// } -// if (playCount) { -// /* one file is playable */ -// ui->playButton->show(); - -// if (playStartable == 1) { -// ui->playButton->setEnabled(true); -// } else { -// ui->playButton->setEnabled(false); -// } -// } else { -// ui->playButton->hide(); -// } - -// if (loopAgain) { -// QTimer::singleShot( msec_rate, this, SLOT(updateItem(void))); -// } - -// // HACK TO DISPLAY COMMENT BUTTON FOR NOW. -// //downloadButton->show(); -// //downloadButton->setEnabled(true); -//} - QString WireNotifyPostItem::groupName() { return QString::fromUtf8(mGroupMeta.mGroupName.c_str()); @@ -525,150 +378,33 @@ void WireNotifyPostItem::fill() pulseTypeStr = tr("Pulse"); } - if (!mIsHome) + if (mCloseOnRead && !IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { + removeItem(); + } + + msgText = pulseTypeStr + ": "; + RetroShareLink msgLink = RetroShareLink::createGxsMessageLink(RetroShareLink::TYPE_WIRE, mPulse.mMeta.mGroupId, mPulse.mMeta.mMsgId, messageName()); + msgText += msgLink.toHtml(); + ui->subjectLabel->setText(msgText); + + ui->pulseMessage->setText(QString::fromUtf8(mPulse.mPulseText.c_str())); + ui->datetimelabel->setText(DateTime::formatLongDateTime(mPulse.mRefPublishTs)); + + if (IS_GROUP_SUBSCRIBED(mGroupMeta.mSubscribeFlags) || IS_GROUP_ADMIN(mGroupMeta.mSubscribeFlags)) { - if (mCloseOnRead && !IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { - removeItem(); - } - - msgText = pulseTypeStr + ": "; - RetroShareLink msgLink = RetroShareLink::createGxsMessageLink(RetroShareLink::TYPE_WIRE, mPulse.mMeta.mGroupId, mPulse.mMeta.mMsgId, messageName()); - msgText += msgLink.toHtml(); - ui->subjectLabel->setText(msgText); - - ui->pulseMessage->setText(QString::fromUtf8(mPulse.mPulseText.c_str())); - ui->datetimelabel->setText(DateTime::formatLongDateTime(mPulse.mRefPublishTs)); - - if (IS_GROUP_SUBSCRIBED(mGroupMeta.mSubscribeFlags) || IS_GROUP_ADMIN(mGroupMeta.mSubscribeFlags)) - { - ui->unsubscribeButton->setEnabled(true); - } - else - { - ui->unsubscribeButton->setEnabled(false); - } - ui->readButton->hide(); - ui->newLabel->hide(); - ui->copyLinkButton->hide(); - - if (IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { - mCloseOnRead = true; - } + ui->unsubscribeButton->setEnabled(true); } else { - - /* disable buttons: deletion facility not enabled with cache services yet */ - ui->clearButton->setEnabled(false); ui->unsubscribeButton->setEnabled(false); - ui->clearButton->hide(); - ui->readAndClearButton->hide(); - ui->unsubscribeButton->hide(); - ui->copyLinkButton->show(); - - if (IS_GROUP_SUBSCRIBED(mGroupMeta.mSubscribeFlags) || IS_GROUP_ADMIN(mGroupMeta.mSubscribeFlags)) - { - ui->readButton->setVisible(true); - - setReadStatus(IS_MSG_NEW(mPulse.mMeta.mMsgStatus), IS_MSG_UNREAD(mPulse.mMeta.mMsgStatus) || IS_MSG_NEW(mPulse.mMeta.mMsgStatus)); - } - else - { - ui->readButton->setVisible(false); - ui->newLabel->setVisible(false); - } - - mCloseOnRead = false; } + ui->readButton->hide(); + ui->newLabel->hide(); + ui->copyLinkButton->hide(); - // differences between Feed or Top of Comment. - if (mFeedHolder) - { - if (mIsHome) { - ui->commentButton->show(); - } else if (ui->commentButton->icon().isNull()){ - //Icon is seted if a comment received. - ui->commentButton->hide(); - } - -// THIS CODE IS doesn't compile - disabling until fixed. -#if 0 - if (post.mComments) - { - QString commentText = QString::number(post.mComments); - commentText += " "; - commentText += tr("Comments"); - ui->commentButton->setText(commentText); - } - else - { - ui->commentButton->setText(tr("Comment")); - } -#endif - + if (IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { + mCloseOnRead = true; } - else - { - ui->commentButton->hide(); - } - - // disable voting buttons - if they have already voted. - /*if (post.mMeta.mMsgStatus & GXS_SERV::GXS_MSG_STATUS_VOTE_MASK) - { - voteUpButton->setEnabled(false); - voteDownButton->setEnabled(false); - }*/ - -// { -// QTextDocument doc; -// doc.setHtml( QString::fromUtf8(mPulse.mMsg.c_str()) ); - -// ui->msgFrame->setVisible(doc.toPlainText().length() > 0); -// } - -// if (wasExpanded() || ui->expandFrame->isVisible()) { -// fillExpandFrame(); -// } - -// if ( (mPulse.mAttachmentCount != 0) || (mPulse.mSize != 0) ) { -// ui->filelabel->setVisible(true); -// ui->filelabel->setText(QString("(%1 %2) %3").arg(mPulse.mAttachmentCount).arg( (mPulse.mAttachmentCount > 1)?tr("Files"):tr("File")).arg(misc::friendlyUnit(mPulse.mSize))); -// } else { -// ui->filelabel->setVisible(false); -// } - -// if (mFileItems.empty() == false) { -// std::list::iterator it; -// for(it = mFileItems.begin(); it != mFileItems.end(); ++it) -// { -// delete(*it); -// } -// mFileItems.clear(); -// } - -// std::list::const_iterator it; -// for(it = mPulse.mFiles.begin(); it != mPulse.mFiles.end(); ++it) -// { -// /* add file */ -// std::string path; -// SubFileItem *fi = new SubFileItem(it->mHash, it->mName, path, it->mSize, SFI_STATE_REMOTE | SFI_TYPE_CHANNEL, RsPeerId()); -// mFileItems.push_back(fi); - -// /* check if the file is a media file */ -// if (!misc::isPreviewable(QFileInfo(QString::fromUtf8(it->mName.c_str())).suffix())) -// { -// fi->mediatype(); -// /* check if the file is not a media file and change text */ -// ui->playButton->setText(tr("Open")); -// ui->playButton->setToolTip(tr("Open File")); -// } else { -// ui->playButton->setText(tr("Play")); -// ui->playButton->setToolTip(tr("Play Media")); -// } - -// QLayout *layout = ui->expandFrame->layout(); -// layout->addWidget(fi); -// } mInFill = false; } diff --git a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.h b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.h index 8633985ae..1dbb4c5ad 100644 --- a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.h +++ b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.h @@ -38,12 +38,7 @@ class WireNotifyPostItem : public GxsFeedItem Q_OBJECT public: - // This one is used in NewFeed for incoming Wire posts. Only the group and msg ids are known at this point. - // It can be used for all apparences of wire posts. But in rder to merge comments from the previous versions of the post, the list of - // previous posts should be supplied. It's optional. If not supplied only the comments of the new version will be displayed. - WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool isHome, bool autoUpdate, const std::set& older_versions = std::set()); - WireNotifyPostItem(FeedHolder *parent, uint32_t feedId, const RsGroupMetaData& group_meta, const RsGxsMessageId& messageId, bool isHome, bool autoUpdate, const std::set& older_versions = std::set()); - //WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsWireGroup &group, bool isHome, bool autoUpdate); + WireNotifyPostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool autoUpdate, const std::set& older_versions = std::set()); virtual ~WireNotifyPostItem(); @@ -52,7 +47,6 @@ public: bool setPost(const RsWirePulse& pulse, bool doFill = true); void setGroup(const RsWireGroup &group); - bool isLoaded() const {return mLoaded;}; bool isUnread() const ; void setReadStatus(bool isNew, bool isUnread); @@ -89,7 +83,8 @@ private: private: bool mInFill; bool mCloseOnRead; - bool mLoaded; + + LoadingStatus mLoadingStatus; bool mLoadingMessage; bool mLoadingGroup; @@ -98,6 +93,7 @@ private: RsGroupMetaData mGroupMeta; RsWirePulse mPulse; + RsWireGroup mGroup; /** Qt Designer generated object */ Ui::WireNotifyPostItem *ui; diff --git a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.ui b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.ui index 46d2b5332..fbbf716cb 100644 --- a/retroshare-gui/src/gui/feeds/WireNotifyPostItem.ui +++ b/retroshare-gui/src/gui/feeds/WireNotifyPostItem.ui @@ -165,28 +165,28 @@
- - - - - 11 - false - true - - - - TextLabel - - - true - - - 8 + + + + + 11 + false + true + + + + TextLabel + + + true + + + @@ -212,78 +212,6 @@ - - - - - true - - - - 0 - - - - - - - I like this - - - - - - - - - - I dislike this - - - - - - - - - - Qt::FocusPolicy::NoFocus - - - Download - - - false - - - - - - - Qt::FocusPolicy::NoFocus - - - Play - - - - - - - Comments - - - - - - - fileLabel - - - Qt::AlignmentFlag::AlignRight|Qt::AlignmentFlag::AlignTrailing|Qt::AlignmentFlag::AlignVCenter - - - diff --git a/retroshare-gui/src/gui/feeds/WirePostItem.cpp b/retroshare-gui/src/gui/feeds/WirePostItem.cpp deleted file mode 100644 index ece70f37c..000000000 --- a/retroshare-gui/src/gui/feeds/WirePostItem.cpp +++ /dev/null @@ -1,693 +0,0 @@ -/******************************************************************************* - * gui/feeds/WirePostItem.cpp * - * * - * Copyright (c) 2012, Robert Fernie * - * * - * This program is free software: you can redistribute it and/or modify * - * it under the terms of the GNU Affero General Public License as * - * published by the Free Software Foundation, either version 3 of the * - * License, or (at your option) any later version. * - * * - * This program is distributed in the hope that it will be useful, * - * but WITHOUT ANY WARRANTY; without even the implied warranty of * - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * - * GNU Affero General Public License for more details. * - * * - * You should have received a copy of the GNU Affero General Public License * - * along with this program. If not, see . * - * * - *******************************************************************************/ - -#include - -#include "WirePostItem.h" -#include "ui_WirePostItem.h" - -#include "FeedHolder.h" -#include "util/qtthreadsutils.h" -#include "gui/RetroShareLink.h" -#include "gui/common/FilesDefs.h" -#include "gui/gxs/GxsIdDetails.h" -#include "util/stringutil.h" -#include "util/DateTime.h" -#include "util/misc.h" - -#include -#include - -/**** - * #define DEBUG_ITEM 1 - ****/ - -WirePostItem::WirePostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool isHome, bool autoUpdate, const std::set &older_versions) : - GxsFeedItem(feedHolder, feedId, groupId, messageId, isHome, rsWire, autoUpdate) // this one should be in GxsFeedItem -{ - QVector v; - //bool self = false; - - for(std::set::const_iterator it(older_versions.begin());it!=older_versions.end();++it) - v.push_back(*it) ; - - if(older_versions.find(messageId) == older_versions.end()) - v.push_back(messageId); - - mLoadingStatus = LOADING_STATUS_NO_DATA; - mLoadingMessage = false; - mLoadingGroup = false; - mLoadingComment = false; - - setMessageVersions(v) ; - setup(); -} - -void WirePostItem::paintEvent(QPaintEvent *e) -{ - /* This method employs a trick to trigger a deferred loading. The post and group is requested only - * when actually displayed on the screen. */ - - if(mLoadingStatus != LOADING_STATUS_FILLED && !mGroupMeta.mGroupId.isNull() && !mPulse.mMeta.mMsgId.isNull() ) - mLoadingStatus = LOADING_STATUS_HAS_DATA; - - if(mGroupMeta.mGroupId.isNull() && !mLoadingGroup) - requestGroup(); - - if(mPulse.mMeta.mMsgId.isNull() && !mLoadingMessage) - requestMessage(); - - switch(mLoadingStatus) - { - case LOADING_STATUS_FILLED: - case LOADING_STATUS_NO_DATA: - default: - break; - - case LOADING_STATUS_HAS_DATA: - fill(); - mLoadingStatus = LOADING_STATUS_FILLED; - break; - } - - GxsFeedItem::paintEvent(e) ; -} - -WirePostItem::~WirePostItem() -{ - auto timeout = std::chrono::steady_clock::now() + std::chrono::milliseconds(GROUP_ITEM_LOADING_TIMEOUT_ms); - - while( (mLoadingGroup || mLoadingMessage) - && std::chrono::steady_clock::now() < timeout) - { - RsDbg() << __PRETTY_FUNCTION__ << " is Waiting for " - << (mLoadingGroup ? "Group " : "") - << (mLoadingMessage ? "Message " : "") - << "loading." << std::endl; - std::this_thread::sleep_for(std::chrono::milliseconds(100)); - } - - delete ui; -} - -bool WirePostItem::isUnread() const -{ - return IS_MSG_UNREAD(mPulse.mMeta.mMsgStatus) ; -} - -void WirePostItem::setup() -{ - /* Invoke the Qt Designer generated object setup routine */ - - ui = new Ui::WirePostItem; - ui->setupUi(this); - - // Manually set icons to allow to use clever resource sharing that is missing in Qt for Icons loaded from Qt resource file. - // This is particularly important here because a wire may contain many posts, so duplicating the QImages here is deadly for the - // memory. - -// ui->logoLabel->setPixmap(FilesDefs::getPixmapFromQtResourcePath(":/images/thumb-default-video.png")); - //ui->warn_image_label->setPixmap(FilesDefs::getPixmapFromQtResourcePath(":/images/status_unknown.png")); - ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-unread.png")); -// ui->voteUpButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/vote_up.png")); -// ui->voteDownButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/vote_down.png")); -// ui->downloadButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/download.png")); -// ui->playButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/play.png")); - ui->commentButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/comment.png")); - //ui->editButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/pencil-edit-button.png")); -// ui->copyLinkButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/copy.png")); -// ui->expandButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/down-arrow.png")); -// ui->readAndClearButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/correct.png")); -// ui->clearButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/icons/png/exit2.png")); - - setAttribute(Qt::WA_DeleteOnClose, true); - - mCloseOnRead = false; - - /* clear ui */ - ui->titleLabel->setText(tr("Loading...")); - ui->titleLabel->setOpenExternalLinks(false); //To get linkActivated working - connect(ui->titleLabel, SIGNAL(linkActivated(QString)), this, SLOT(on_linkActivated(QString))); - ui->datetimelabel->clear(); - ui->filelabel->clear(); -// ui->newCommentLabel->hide(); -// ui->commLabel->hide(); - - /* general ones */ - connect(ui->expandButton, SIGNAL(clicked()), this, SLOT(toggle())); - connect(ui->clearButton, SIGNAL(clicked()), this, SLOT(removeItem())); - - /* specific */ - connect(ui->readAndClearButton, SIGNAL(clicked()), this, SLOT(readAndClearItem())); - connect(ui->unsubscribeButton, SIGNAL(clicked()), this, SLOT(unsubscribeChannel())); - - connect(ui->downloadButton, SIGNAL(clicked()), this, SLOT(download())); - // HACK FOR NOW. - ui->commentButton->hide();// hidden until properly enabled. - connect(ui->commentButton, SIGNAL(clicked()), this, SLOT(loadComments())); - - connect(ui->playButton, SIGNAL(clicked()), this, SLOT(play(void))); - //connect(ui->editButton, SIGNAL(clicked()), this, SLOT(edit(void))); - connect(ui->copyLinkButton, SIGNAL(clicked()), this, SLOT(copyMessageLink())); - - connect(ui->readButton, SIGNAL(toggled(bool)), this, SLOT(readToggled(bool))); - - // hide voting buttons, backend is not implemented yet - ui->voteUpButton->hide(); - ui->voteDownButton->hide(); - - ui->scoreLabel->hide(); - - // hide unsubscribe button not necessary - ui->unsubscribeButton->hide(); - - ui->downloadButton->hide(); - ui->playButton->hide(); - //ui->warn_image_label->hide(); - //ui->warning_label->hide(); - - ui->titleLabel->setMinimumWidth(100); - ui->subjectLabel->setMinimumWidth(100); - //ui->warning_label->setMinimumWidth(100); - ui->titleLabel->setEnabled(false); - - ui->feedFrame->setProperty("new", false); - ui->feedFrame->style()->unpolish(ui->feedFrame); - ui->feedFrame->style()->polish( ui->feedFrame); - - ui->expandFrame->hide(); -} - -QString WirePostItem::groupName() -{ - return QString::fromUtf8(mGroupMeta.mGroupName.c_str()); -} - -void WirePostItem::loadGroup() -{ -#ifdef DEBUG_ITEM - std::cerr << "WireNotifyGroupItem::loadGroup()"; - std::cerr << std::endl; -#endif - - mLoadingGroup = true; - - RsThread::async([this]() - { - // 1 - get group data - - std::vector groups; - const std::list groupIds = { groupId() }; - - if(!rsWire->getGroups(groupIds,groups)) // would be better to call channel Summaries for a single group - { - RsErr() << "WirePostItem::loadGroup() ERROR getting data" << std::endl; - mLoadingGroup = false; - return; - } - - if (groups.size() != 1) - { - std::cerr << "WirePostItem::loadGroup() Wrong number of Items"; - std::cerr << std::endl; - mLoadingGroup = false; - return; - } - - RsWireGroup group(groups[0]); - - RsQThreadUtils::postToObject( [group,this]() - { - /* Here it goes any code you want to be executed on the Qt Gui - * thread, for example to update the data model with new information - * after a blocking call to RetroShare API complete */ - - mGroupMeta = group.mMeta; - mLoadingGroup = false; - - update(); // this triggers a paintEvent if needed. - - }, this ); - }); -} - -void WirePostItem::loadMessage() -{ -#ifdef DEBUG_ITEM - std::cerr << "WirePostItem::loadMessage()"; - std::cerr << std::endl; -#endif - mLoadingMessage = true; - - RsThread::async([this]() - { - // 1 - get group data - - std::list groupIds; - std::list pulses; -// std::vector comments; -// std::vector votes; - //groupIds.push_back(groupId()); - - if(! rsWire->getPulsesForGroups(groupIds, pulses)) - { - RsErr() << "WirePostItem::loadMessage() ERROR getting data" << std::endl; - mLoadingMessage = false; - return; - } - - if (pulses.size() == 1) - { -#ifdef DEBUG_ITEM - std::cerr << (void*)this << ": Obtained post, with msgId = " << pulses[0].mMeta.mMsgId << std::endl; -#endif - const RsWirePulse& pulse(*pulses.front()); - - RsQThreadUtils::postToObject( [pulse,this]() - { - mPulse = pulse; - mLoadingMessage = false; - update(); // this triggers a paintEvent if needed. - }, this ); - } - -// else if(comments.size() == 1) -// { -// const RsGxsComment& cmt = comments[0]; -//#ifdef DEBUG_ITEM -// std::cerr << (void*)this << ": Obtained comment, setting messageId to threadID = " << cmt.mMeta.mThreadId << std::endl; -//#endif - -// RsQThreadUtils::postToObject( [cmt,this]() -// { -// ui->newCommentLabel->show(); -// ui->commLabel->show(); -// ui->commLabel->setText(QString::fromUtf8(cmt.mComment.c_str())); - -// //Change this item to be uploaded with thread element. -// setMessageId(cmt.mMeta.mThreadId); -// requestMessage(); - -// mLoadingMessage = false; -// }, this ); - -// } -// else -// { -//#ifdef DEBUG_ITEM -// std::cerr << "WirePostItem::loadMessage() Wrong number of Items. Remove It."; -// std::cerr << std::endl; -//#endif - -// RsQThreadUtils::postToObject( [this]() -// { -// removeItem(); -// mLoadingMessage = false; -// }, this ); -// } - }); -} - -void WirePostItem::loadComment() -{ -#ifdef DEBUG_ITEM - std::cerr << "WirePostItem::loadComment()"; - std::cerr << std::endl; -#endif -// mLoadingComment = true; - -// RsThread::async([this]() -// { -// // 1 - get group data - -// std::set msgIds; - -// for(auto MsgId: messageVersions()) -// msgIds.insert(MsgId); - -// std::vector posts; -// std::vector comments; - -// if(! rsGxsChannels->getChannelComments( groupId(),msgIds,comments)) -// { -// RsErr() << "GxsGxsChannelGroupItem::loadGroup() ERROR getting data" << std::endl; -// return; -// } - -// int comNb = comments.size(); - -// RsQThreadUtils::postToObject( [comNb,this]() -// { -// QString sComButText = tr("Comment"); -// if (comNb == 1) -// sComButText = sComButText.append("(1)"); -// else if(comNb > 1) -// sComButText = tr("Comments ").append("(%1)").arg(comNb); - -// ui->commentButton->setText(sComButText); -// mLoadingComment = false; - -// }, this ); -// }); -} - - -void WirePostItem::fill() -{ -#ifdef DEBUG_ITEM - std::cerr << "WirePostItem::fill()"; - std::cerr << std::endl; -#endif - - QString title; - QString msgText; - - ui->groupName->setText(QString::fromStdString(mGroup.mMeta.mGroupName)); - ui->groupName->setToolTip(QString::fromStdString(mGroup.mMeta.mGroupName) + "@" + QString::fromStdString(mGroup.mMeta.mAuthorId.toStdString())); - - if (mGroup.mHeadshot.mData ) - { - QPixmap pixmap; - if (GxsIdDetails::loadPixmapFromData( - mGroup.mHeadshot.mData, - mGroup.mHeadshot.mSize, - pixmap,GxsIdDetails::ORIGINAL)) - { - ui->logoLabel->setPixmap(pixmap); - } - } - else{ - // default. - QPixmap pixmap = FilesDefs::getPixmapFromQtResourcePath(":/icons/wire.png"); - ui->logoLabel->setPixmap(pixmap); - } - - if (!mIsHome) - { - if (mCloseOnRead && !IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { - removeItem(); - } - - title = tr("Wire Feed") + ": "; - RetroShareLink link = RetroShareLink::createGxsGroupLink(RetroShareLink::TYPE_WIRE, mGroup.mMeta.mGroupId, groupName()); - title += link.toHtml(); - ui->titleLabel->setText(title); - - msgText = tr("Pulse") + ": "; - RetroShareLink msgLink = RetroShareLink::createGxsMessageLink(RetroShareLink::TYPE_WIRE, mPulse.mMeta.mGroupId, mPulse.mMeta.mMsgId, messageName()); - msgText += msgLink.toHtml(); - ui->subjectLabel->setText(msgText); - - ui->pulseMessage->setText(QString::fromUtf8(mPulse.mPulseText.c_str())); - ui->datetimelabel->setText(DateTime::formatLongDateTime(mPulse.mRefPublishTs)); - - if (IS_GROUP_SUBSCRIBED(mGroupMeta.mSubscribeFlags) || IS_GROUP_ADMIN(mGroupMeta.mSubscribeFlags)) - { - ui->unsubscribeButton->setEnabled(true); - } - else - { - ui->unsubscribeButton->setEnabled(false); - } - ui->readButton->hide(); - ui->newLabel->hide(); - ui->copyLinkButton->hide(); - - if (IS_MSG_NEW(mPulse.mMeta.mMsgStatus)) { - mCloseOnRead = true; - } - } - else - { - - /* disable buttons: deletion facility not enabled with cache services yet */ - ui->clearButton->setEnabled(false); - ui->unsubscribeButton->setEnabled(false); - ui->clearButton->hide(); - ui->readAndClearButton->hide(); - ui->unsubscribeButton->hide(); - ui->copyLinkButton->show(); - - if (IS_GROUP_SUBSCRIBED(mGroupMeta.mSubscribeFlags) || IS_GROUP_ADMIN(mGroupMeta.mSubscribeFlags)) - { - ui->readButton->setVisible(true); - - setReadStatus(IS_MSG_NEW(mPulse.mMeta.mMsgStatus), IS_MSG_UNREAD(mPulse.mMeta.mMsgStatus) || IS_MSG_NEW(mPulse.mMeta.mMsgStatus)); - } - else - { - ui->readButton->setVisible(false); - ui->newLabel->setVisible(false); - } - - mCloseOnRead = false; - } - - // differences between Feed or Top of Comment. - if (mFeedHolder) - { - if (mIsHome) { - ui->commentButton->show(); - } else if (ui->commentButton->icon().isNull()){ - //Icon is seted if a comment received. - ui->commentButton->hide(); - } - -// THIS CODE IS doesn't compile - disabling until fixed. -#if 0 - if (post.mComments) - { - QString commentText = QString::number(post.mComments); - commentText += " "; - commentText += tr("Comments"); - ui->commentButton->setText(commentText); - } - else - { - ui->commentButton->setText(tr("Comment")); - } -#endif - - } - else - { - ui->commentButton->hide(); - } - - // disable voting buttons - if they have already voted. - /*if (post.mMeta.mMsgStatus & GXS_SERV::GXS_MSG_STATUS_VOTE_MASK) - { - voteUpButton->setEnabled(false); - voteDownButton->setEnabled(false); - }*/ - -// { -// QTextDocument doc; -// doc.setHtml( QString::fromUtf8(mPulse.mMsg.c_str()) ); - -// ui->msgFrame->setVisible(doc.toPlainText().length() > 0); -// } - -// if (wasExpanded() || ui->expandFrame->isVisible()) { -// fillExpandFrame(); -// } - -// if ( (mPulse.mAttachmentCount != 0) || (mPulse.mSize != 0) ) { -// ui->filelabel->setVisible(true); -// ui->filelabel->setText(QString("(%1 %2) %3").arg(mPulse.mAttachmentCount).arg( (mPulse.mAttachmentCount > 1)?tr("Files"):tr("File")).arg(misc::friendlyUnit(mPulse.mSize))); -// } else { -// ui->filelabel->setVisible(false); -// } - -// if (mFileItems.empty() == false) { -// std::list::iterator it; -// for(it = mFileItems.begin(); it != mFileItems.end(); ++it) -// { -// delete(*it); -// } -// mFileItems.clear(); -// } - -// std::list::const_iterator it; -// for(it = mPulse.mFiles.begin(); it != mPulse.mFiles.end(); ++it) -// { -// /* add file */ -// std::string path; -// SubFileItem *fi = new SubFileItem(it->mHash, it->mName, path, it->mSize, SFI_STATE_REMOTE | SFI_TYPE_CHANNEL, RsPeerId()); -// mFileItems.push_back(fi); - -// /* check if the file is a media file */ -// if (!misc::isPreviewable(QFileInfo(QString::fromUtf8(it->mName.c_str())).suffix())) -// { -// fi->mediatype(); -// /* check if the file is not a media file and change text */ -// ui->playButton->setText(tr("Open")); -// ui->playButton->setToolTip(tr("Open File")); -// } else { -// ui->playButton->setText(tr("Play")); -// ui->playButton->setToolTip(tr("Play Media")); -// } - -// QLayout *layout = ui->expandFrame->layout(); -// layout->addWidget(fi); -// } - -} - -QString WirePostItem::messageName() -{ - return QString::fromUtf8(mPulse.mMeta.mMsgName.c_str()); -} - - -void WirePostItem::doExpand(bool open) -{ - if (mFeedHolder) - { - mFeedHolder->lockLayout(this, true); - } - - if (open) - { - ui->expandFrame->show(); - ui->expandButton->setIcon(FilesDefs::getIconFromQtResourcePath(QString(":/icons/png/up-arrow.png"))); - ui->expandButton->setToolTip(tr("Hide")); - -// readToggled(false); - } - else - { - ui->expandFrame->hide(); - ui->expandButton->setIcon(FilesDefs::getIconFromQtResourcePath(QString(":/icons/png/down-arrow.png"))); - ui->expandButton->setToolTip(tr("Expand")); - } - - emit sizeChanged(this); - - if (mFeedHolder) - { - mFeedHolder->lockLayout(this, false); - } -} - - -void WirePostItem::setReadStatus(bool isNew, bool isUnread) -{ - if (isNew) - mPulse.mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_NEW; - else - mPulse.mMeta.mMsgStatus &= ~GXS_SERV::GXS_MSG_STATUS_GUI_NEW; - - if (isUnread) - { - mPulse.mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD; - whileBlocking(ui->readButton)->setChecked(true); - ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-unread.png")); - } - else - { - mPulse.mMeta.mMsgStatus &= ~GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD; - whileBlocking(ui->readButton)->setChecked(false); - ui->readButton->setIcon(FilesDefs::getIconFromQtResourcePath(":/images/message-state-read.png")); - } - - //ui->newLabel->setVisible(isNew); - - //ui->feedFrame->setProperty("new", isNew); - //ui->feedFrame->style()->unpolish(ui->feedFrame); - //ui->feedFrame->style()->polish( ui->feedFrame); -} - -/*void WirePostItem::setGroup(const RsWireGroup &group) -{ - ui->groupName->setText(QString::fromStdString(group.mMeta.mGroupName)); - ui->groupName->setToolTip(QString::fromStdString(group.mMeta.mGroupName) + "@" + QString::fromStdString(group.mMeta.mAuthorId.toStdString())); - - QString title; - - title = tr("Wire Feed") + ": "; - RetroShareLink link = RetroShareLink::createGxsGroupLink(RetroShareLink::TYPE_WIRE, group.mMeta.mGroupId, groupName()); - title += link.toHtml(); - ui->titleLabel->setText(title); - - if (group.mHeadshot.mData ) - { - QPixmap pixmap; - if (GxsIdDetails::loadPixmapFromData( - group.mHeadshot.mData, - group.mHeadshot.mSize, - pixmap,GxsIdDetails::ORIGINAL)) - { - ui->logoLabel->setPixmap(pixmap); - } - } - else - { - // default. - QPixmap pixmap = FilesDefs::getPixmapFromQtResourcePath(":/icons/wire.png"); - ui->logoLabel->setPixmap(pixmap); - } - -}*/ - -void WirePostItem::expandFill(bool first) -{ - GxsFeedItem::expandFill(first); - - if (first) { -// fillExpandFrame(); - } -} - -/*********** SPECIFIC FUNCTIONS ***********************/ - -void WirePostItem::readAndClearItem() -{ -#ifdef DEBUG_ITEM - std::cerr << "WirePostItem::readAndClearItem()"; - std::cerr << std::endl; -#endif - readToggled(false); - removeItem(); -} - -void WirePostItem::readToggled(bool /*checked*/) -{ - mCloseOnRead = false; - - RsGxsGrpMsgIdPair msgPair = std::make_pair(groupId(), messageId()); - - //rsWire->setMessageReadStatus(msgPair, isUnread()); - - //setReadStatus(false, checked); // Updated by events -} - -void WirePostItem::on_linkActivated(QString link) -{ - RetroShareLink rsLink(link); - - if (rsLink.valid() ) { - QList rsLinks; - rsLinks.append(rsLink); - RetroShareLink::process(rsLinks); - removeItem(); - return; - } -} diff --git a/retroshare-gui/src/gui/feeds/WirePostItem.h b/retroshare-gui/src/gui/feeds/WirePostItem.h deleted file mode 100644 index f0c295935..000000000 --- a/retroshare-gui/src/gui/feeds/WirePostItem.h +++ /dev/null @@ -1,108 +0,0 @@ -/******************************************************************************* - * gui/feeds/WirePostItem.h * - * * - * Copyright (c) 2012, Robert Fernie * - * * - * This program is free software: you can redistribute it and/or modify * - * it under the terms of the GNU Affero General Public License as * - * published by the Free Software Foundation, either version 3 of the * - * License, or (at your option) any later version. * - * * - * This program is distributed in the hope that it will be useful, * - * but WITHOUT ANY WARRANTY; without even the implied warranty of * - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * - * GNU Affero General Public License for more details. * - * * - * You should have received a copy of the GNU Affero General Public License * - * along with this program. If not, see . * - * * - *******************************************************************************/ -#ifndef WirePostItem_H -#define WirePostItem_H - -#include -#include - -#include -#include "gui/gxs/GxsFeedItem.h" -#include "gui/gxs/GxsGroupFeedItem.h" - -namespace Ui { -class WirePostItem; -} - -class FeedHolder; -class SubFileItem; - -class WirePostItem : public GxsFeedItem -{ - Q_OBJECT - -public: - // This one is used in NewFeed for incoming Wire posts. Only the group and msg ids are known at this point. - // It can be used for all apparences of wire posts. But in rder to merge comments from the previous versions of the post, the list of - // previous posts should be supplied. It's optional. If not supplied only the comments of the new version will be displayed. - WirePostItem(FeedHolder *feedHolder, uint32_t feedId, const RsGxsGroupId& groupId, const RsGxsMessageId &messageId, bool isHome, bool autoUpdate, const std::set& older_versions = std::set()); - -#ifdef UNUSED - WirePostItem(FeedHolder *parent, uint32_t feedId, const RsGroupMetaData& group_meta, const RsGxsMessageId& messageId, bool isHome, bool autoUpdate, const std::set& older_versions = std::set()); - //WirePostItem(FeedHolder *feedHolder, uint32_t feedId, const RsWireGroup &group, bool isHome, bool autoUpdate); -#endif - - virtual ~WirePostItem(); - - uint64_t uniqueIdentifier() const override { return hash_64bits("WirePostItem " + messageId().toStdString()); } - - bool isUnread() const ; - void setReadStatus(bool isNew, bool isUnread); - -protected: - - /* FeedItem */ - virtual void doExpand(bool open); - virtual void expandFill(bool first); - - virtual void paintEvent(QPaintEvent *) override; - - /* GxsGroupFeedItem */ - virtual QString groupName(); - virtual void loadGroup() override; - virtual RetroShareLink::enumType getLinkType() { return RetroShareLink::TYPE_WIRE; } - - /* GxsFeedItem */ -// virtual QString messageName(); - virtual void loadMessage(); - virtual void loadComment(); - virtual QString messageName() override; - -private slots: - /* default stuff */ - //void toggle() override; - void readAndClearItem(); - void readToggled(bool checked); - - void on_linkActivated(QString link); -private: - void setup(); - void fill(); - -private: - bool mCloseOnRead; - - LoadingStatus mLoadingStatus; - - bool mLoadingMessage; - bool mLoadingGroup; - bool mLoadingComment; - - RsGroupMetaData mGroupMeta; - RsWirePulse mPulse; - RsWireGroup mGroup; - - /** Qt Designer generated object */ - Ui::WirePostItem *ui; -}; - -Q_DECLARE_METATYPE(RsWirePulse) - -#endif // WirePostItem_H diff --git a/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.cpp b/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.cpp index dea307387..ef2089b4c 100644 --- a/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.cpp +++ b/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.cpp @@ -33,6 +33,7 @@ #include "gui/common/RSTreeWidget.h" #include "gui/common/UIStateHelper.h" #include "gui/common/UserNotify.h" +#include "gui/RsGUIEventManager.h" #include "util/qtthreadsutils.h" #include "retroshare/rsgxsifacetypes.h" #include "GxsCommentDialog.h" @@ -71,7 +72,7 @@ static const uint32_t DELAY_BETWEEN_GROUP_STATISTICS_UPDATE = 120; // do not upd /** Constructor */ GxsGroupFrameDialog::GxsGroupFrameDialog(RsGxsIfaceHelper *ifaceImpl,const QString& settings_name, QWidget *parent,bool allow_dist_sync) -: GxsStatisticsProvider(ifaceImpl,settings_name,parent) +: MainPage(parent), mSettingsName(settings_name) { /* Invoke the Qt Designer generated object setup routine */ ui = new Ui::GxsGroupFrameDialog(); @@ -172,7 +173,7 @@ void GxsGroupFrameDialog::initUi() processSettings(true); if (groupFrameSettingsType() != GroupFrameSettings::Nothing) { - //connect(NotifyQt::getInstance(), SIGNAL(settingsChanged()), this, SLOT(settingsChanged())); + connect(RsGUIEventManager::getInstance(), SIGNAL(settingsChanged()), this, SLOT(settingsChanged())); settingsChanged(); } diff --git a/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.h b/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.h index 055be83da..c2d75a23c 100644 --- a/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.h +++ b/retroshare-gui/src/gui/gxs/GxsGroupFrameDialog.h @@ -45,7 +45,7 @@ class UIStateHelper; struct RsGxsCommentService; class GxsCommentDialog; -class GxsGroupFrameDialog : public GxsStatisticsProvider +class GxsGroupFrameDialog : public MainPage, public GxsStatisticsProvider { Q_OBJECT @@ -75,13 +75,13 @@ public: GxsGroupFrameDialog(RsGxsIfaceHelper *ifaceImpl, const QString& settings_name,QWidget *parent = 0,bool allow_dist_sync=false); virtual ~GxsGroupFrameDialog(); - virtual bool navigate(const RsGxsGroupId &groupId, const RsGxsMessageId& msgId) override; + virtual bool navigate(const RsGxsGroupId &groupId, const RsGxsMessageId& msgId); virtual QString getHelpString() const =0; virtual void getGroupList(std::map &groups) ; - void getServiceStatistics(GxsServiceStatistic& stats) const ; + void getServiceStatistics(GxsServiceStatistic& stats) const override; static uint32_t checkDelay(uint32_t time_in_secs); @@ -182,7 +182,7 @@ private: // subscribe/unsubscribe ack. - virtual GxsMessageFrameWidget *messageWidget(const RsGxsGroupId &groupId) override; + virtual GxsMessageFrameWidget *messageWidget(const RsGxsGroupId &groupId); GxsMessageFrameWidget *createMessageWidget(const RsGxsGroupId &groupId); GxsCommentDialog *commentWidget(const RsGxsMessageId &msgId); @@ -191,8 +191,22 @@ protected: void updateSearchResults(const TurtleRequestId &sid); void updateSearchResults(); // update all searches - virtual void updateGroupStatistics(const RsGxsGroupId &groupId) override; - virtual void updateGroupStatisticsReal(const RsGxsGroupId &groupId) override; + virtual void updateGroupStatistics(const RsGxsGroupId &groupId); + virtual void updateGroupStatisticsReal(const RsGxsGroupId &groupId); + + // This needs to be overloaded by subclasses, possibly calling the blocking API, since it is used asynchronously. + virtual bool getGroupStatistics(const RsGxsGroupId& groupId, GxsGroupStatistic& stat) = 0; + + QString mSettingsName; + RsGxsIfaceHelper *mInterface; + bool mDistSyncAllowed; + std::map mCachedGroupStats; + bool mShouldUpdateGroupStatistics; + std::set mGroupStatisticsToUpdate; + bool mCountChildMsgs; + RsGxsGroupId mNavigatePendingGroupId; + RsGxsMessageId mNavigatePendingMsgId; + UIStateHelper *mStateHelper; private: GxsMessageFrameWidget *currentWidget() const; diff --git a/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.cpp b/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.cpp index 54766a251..47a77e983 100644 --- a/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.cpp +++ b/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.cpp @@ -18,43 +18,4 @@ * * *******************************************************************************/ -#include -#include -#include - #include "GxsStatisticsProvider.h" - -#include "gui/common/UserNotify.h" -#include "util/qtthreadsutils.h" -#include "retroshare/rsgxsifacetypes.h" - -#define TOKEN_TYPE_GROUP_SUMMARY 1 -//#define TOKEN_TYPE_SUBSCRIBE_CHANGE 2 -//#define TOKEN_TYPE_CURRENTGROUP 3 -#define TOKEN_TYPE_STATISTICS 4 - -#define MAX_COMMENT_TITLE 32 - -static const uint32_t DELAY_BETWEEN_GROUP_STATISTICS_UPDATE = 120; // do not update group statistics more often than once every 2 mins - -/* - * Transformation Notes: - * there are still a couple of things that the new groups differ from Old version. - * these will need to be addressed in the future. - * -> Child TS (for sorting) is not handled by GXS, this will probably have to be done in the GUI. - * -> Need to handle IDs properly. - * -> Much more to do. - */ - -/** Constructor */ -GxsStatisticsProvider::GxsStatisticsProvider(RsGxsIfaceHelper *ifaceImpl,const QString& settings_name, QWidget *parent,bool allow_dist_sync) -: MainPage(parent),mSettingsName(settings_name) -{ - mDistSyncAllowed = allow_dist_sync; - mInterface = ifaceImpl; - mShouldUpdateGroupStatistics = false; -} - -GxsStatisticsProvider::~GxsStatisticsProvider() -{ -} diff --git a/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.h b/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.h index ade29b1e8..3309e795b 100644 --- a/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.h +++ b/retroshare-gui/src/gui/gxs/GxsStatisticsProvider.h @@ -21,58 +21,15 @@ #ifndef GXSSTATISTICSPROVIDER_H #define GXSSTATISTICSPROVIDER_H -#include +#include "retroshare/rsgxsifacetypes.h" -#include "gui/gxs/RsGxsUpdateBroadcastPage.h" -#include "gui/RetroShareLink.h" -#include "gui/settings/rsharesettings.h" -#include "util/RsUserdata.h" +// Interface for GxsUserNotify to query service statistics. -#include - -#include "GxsIdTreeWidgetItem.h" -#include "GxsGroupDialog.h" - -class GroupTreeWidget; -class GroupItemInfo; -class GxsMessageFrameWidget; -class UIStateHelper; -struct RsGxsCommentService; -class GxsCommentDialog; - -class GxsStatisticsProvider : public MainPage +class GxsStatisticsProvider { - Q_OBJECT - public: - GxsStatisticsProvider(RsGxsIfaceHelper *ifaceImpl, const QString& settings_name,QWidget *parent = 0,bool allow_dist_sync=false); - virtual ~GxsStatisticsProvider(); - + virtual ~GxsStatisticsProvider() = default; virtual void getServiceStatistics(GxsServiceStatistic& stats) const = 0; - virtual bool navigate(const RsGxsGroupId &groupId, const RsGxsMessageId& msgId) = 0; - -protected: - virtual void updateGroupStatistics(const RsGxsGroupId &groupId) = 0; - virtual void updateGroupStatisticsReal(const RsGxsGroupId &groupId) = 0; - - // This needs to be overloaded by subsclasses, possibly calling the blocking API, since it is used asynchroneously. - virtual bool getGroupStatistics(const RsGxsGroupId& groupId,GxsGroupStatistic& stat) = 0; - - virtual GxsMessageFrameWidget *messageWidget(const RsGxsGroupId &groupId) = 0; - - QString mSettingsName; - RsGxsIfaceHelper *mInterface; - bool mDistSyncAllowed; - std::map mCachedGroupStats; - bool mShouldUpdateGroupStatistics; - std::set mGroupStatisticsToUpdate; - bool mCountChildMsgs; // Count unread child messages? - - RsGxsGroupId mNavigatePendingGroupId; - RsGxsMessageId mNavigatePendingMsgId; - UIStateHelper *mStateHelper; - -private: - virtual QString settingsGroupName() = 0; }; + #endif // GXSSTATISTICSPROVIDER_H diff --git a/retroshare-gui/src/gui/gxs/GxsUserNotify.h b/retroshare-gui/src/gui/gxs/GxsUserNotify.h index a42ec69c4..27f5099e2 100644 --- a/retroshare-gui/src/gui/gxs/GxsUserNotify.h +++ b/retroshare-gui/src/gui/gxs/GxsUserNotify.h @@ -24,7 +24,6 @@ #include #include "gui/common/UserNotify.h" #include "gui/gxs/GxsStatisticsProvider.h" -#include "gui/gxs/GxsGroupFrameDialog.h" class RsGxsIfaceHelper; class RsGxsUpdateBroadcastBase; diff --git a/retroshare-gui/src/gui/gxschannels/GxsChannelDialog.h b/retroshare-gui/src/gui/gxschannels/GxsChannelDialog.h index 7dab607be..0e8f9e6b5 100644 --- a/retroshare-gui/src/gui/gxschannels/GxsChannelDialog.h +++ b/retroshare-gui/src/gui/gxschannels/GxsChannelDialog.h @@ -71,7 +71,7 @@ private: /* GxsGroupFrameDialog */ virtual QString text(TextType type) override; virtual QString icon(IconType type) override; - virtual QString settingsGroupName() override { return "ChannelDialog"; } + virtual QString settingsGroupName() { return "ChannelDialog"; } virtual GxsGroupDialog *createNewGroupDialog() override; virtual GxsGroupDialog *createGroupDialog(GxsGroupDialog::Mode mode, RsGxsGroupId groupId) override; virtual int shareKeyType() override; diff --git a/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.cpp b/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.cpp index ce88231fc..46c5afaab 100644 --- a/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.cpp +++ b/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.cpp @@ -23,7 +23,7 @@ #include "gui/MainWindow.h" #include "gui/common/FilesDefs.h" -GxsChannelUserNotify::GxsChannelUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsGroupFrameDialog *g, QObject *parent) : +GxsChannelUserNotify::GxsChannelUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsStatisticsProvider *g, QObject *parent) : GxsUserNotify(ifaceImpl, g, parent) { } diff --git a/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.h b/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.h index 2604f5d34..94a787e91 100644 --- a/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.h +++ b/retroshare-gui/src/gui/gxschannels/GxsChannelUserNotify.h @@ -22,14 +22,13 @@ #define GXSCHANNELUSERNOTIFY_H #include "gui/gxs/GxsUserNotify.h" -#include "gui/gxs/GxsGroupFrameDialog.h" class GxsChannelUserNotify : public GxsUserNotify { Q_OBJECT public: - explicit GxsChannelUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsGroupFrameDialog *g, QObject *parent = 0); + explicit GxsChannelUserNotify(RsGxsIfaceHelper *ifaceImpl, const GxsStatisticsProvider *g, QObject *parent = 0); virtual bool hasSetting(QString *name, QString *group) override; diff --git a/retroshare-gui/src/gui/gxsforums/GxsForumsDialog.h b/retroshare-gui/src/gui/gxsforums/GxsForumsDialog.h index 75d10a1e1..24bb5e057 100644 --- a/retroshare-gui/src/gui/gxsforums/GxsForumsDialog.h +++ b/retroshare-gui/src/gui/gxsforums/GxsForumsDialog.h @@ -53,7 +53,7 @@ private: /* GxsGroupFrameDialog */ QString text(TextType type)override ; QString icon(IconType type)override ; - QString settingsGroupName() override { return "ForumsDialog"; } + QString settingsGroupName() { return "ForumsDialog"; } GxsGroupDialog *createNewGroupDialog() override; GxsGroupDialog *createGroupDialog(GxsGroupDialog::Mode mode, RsGxsGroupId groupId) override; diff --git a/retroshare-gui/src/gui/settings/rsharesettings.cpp b/retroshare-gui/src/gui/settings/rsharesettings.cpp index bb69af532..2c1f28598 100644 --- a/retroshare-gui/src/gui/settings/rsharesettings.cpp +++ b/retroshare-gui/src/gui/settings/rsharesettings.cpp @@ -1119,8 +1119,8 @@ static QString groupFrameSettingsTypeToString(GroupFrameSettings::Type type) case GroupFrameSettings::Posted: return "Posted"; #ifdef RS_USE_WIRE - case GroupFrameSettings::Wire: - return "Wire" ; + case GroupFrameSettings::Wire: + return "Wire"; #endif } diff --git a/retroshare-gui/src/retroshare-gui.pro b/retroshare-gui/src/retroshare-gui.pro index 4f2da7bff..b33ada159 100644 --- a/retroshare-gui/src/retroshare-gui.pro +++ b/retroshare-gui/src/retroshare-gui.pro @@ -623,7 +623,6 @@ HEADERS += rshare.h \ gui/NetworkDialog/pgpid_item_model.h \ gui/NetworkDialog/pgpid_item_proxy.h \ gui/common/RsCollection.h \ - gui/common/NotifyWidget.h \ util/retroshareWin32.h FORMS += gui/StartDialog.ui \ @@ -717,7 +716,6 @@ FORMS += gui/StartDialog.ui \ gui/common/RsCollectionDialog.ui \ gui/common/HeaderFrame.ui \ gui/common/RSFeedWidget.ui \ - gui/common/NotifyWidget.ui \ gui/style/StyleDialog.ui \ gui/statistics/BandwidthGraphWindow.ui \ gui/statistics/BandwidthStatsWidget.ui \ @@ -895,7 +893,6 @@ SOURCES += main.cpp \ gui/common/FlowLayout.cpp \ gui/common/PictureFlow.cpp \ gui/common/ToasterNotify.cpp \ - gui/common/NotifyWidget.cpp \ gui/style/RSStyle.cpp \ gui/style/StyleDialog.cpp \ gui/settings/RSPermissionMatrixWidget.cpp \