FeedReader: Message of a local feed can be added as forum and board message

This commit is contained in:
thunder2 2023-04-16 17:44:50 +02:00
parent bcb4e52768
commit b14fecfc2a
7 changed files with 237 additions and 7 deletions

View File

@ -36,8 +36,12 @@
#include "gui/settings/rsharesettings.h" #include "gui/settings/rsharesettings.h"
#include "util/HandleRichText.h" #include "util/HandleRichText.h"
#include "util/QtVersion.h" #include "util/QtVersion.h"
#include "gui/Posted/PostedCreatePostDialog.h"
#include "gui/gxsforums/CreateGxsForumMsg.h"
#include "retroshare/rsiface.h" #include "retroshare/rsiface.h"
#include "retroshare/rsgxsforums.h"
#include "retroshare/rsposted.h"
#define COLUMN_MSG_COUNT 4 #define COLUMN_MSG_COUNT 4
#define COLUMN_MSG_TITLE 0 #define COLUMN_MSG_TITLE 0
@ -350,6 +354,20 @@ void FeedReaderMessageWidget::msgTreeCustomPopupMenu(QPoint /*point*/)
action = contextMnu.addAction(QIcon(""), tr("Remove"), this, SLOT(removeMsg())); action = contextMnu.addAction(QIcon(""), tr("Remove"), this, SLOT(removeMsg()));
action->setEnabled(!selectedItems.empty()); action->setEnabled(!selectedItems.empty());
if (selectedItems.size() == 1 && (mFeedReader->forums() || mFeedReader->posted())) {
contextMnu.addSeparator();
if (mFeedReader->forums()) {
QMenu *menu = contextMnu.addMenu(tr("Add to forum"));
connect(menu, SIGNAL(aboutToShow()), this, SLOT(fillForumMenu()));
}
if (mFeedReader->posted()) {
QMenu *menu = contextMnu.addMenu(tr("Add to board"));
connect(menu, SIGNAL(aboutToShow()), this, SLOT(fillPostedMenu()));
}
}
contextMnu.addSeparator(); contextMnu.addSeparator();
action = contextMnu.addAction(QIcon(""), tr("Retransform"), this, SLOT(retransformMsg())); action = contextMnu.addAction(QIcon(""), tr("Retransform"), this, SLOT(retransformMsg()));
@ -850,3 +868,104 @@ void FeedReaderMessageWidget::openLinkMsg()
QDesktopServices::openUrl(QUrl(link)); QDesktopServices::openUrl(QUrl(link));
} }
void FeedReaderMessageWidget::fillForumMenu()
{
QMenu *menu = dynamic_cast<QMenu*>(sender()) ;
if (!menu) {
return;
}
disconnect(menu, SIGNAL(aboutToShow()), this, SLOT(fillForumMenu()));
std::vector<RsGxsForumGroup> groups;
if (mFeedReader->getForumGroups(groups, true)) {
for (std::vector<RsGxsForumGroup>::iterator it = groups.begin(); it != groups.end(); ++it) {
const RsGxsForumGroup &group = *it;
QAction *action = menu->addAction(QString::fromUtf8(group.mMeta.mGroupName.c_str()), this, SLOT(addToForum()));
action->setData(QString::fromUtf8(group.mMeta.mGroupId.toStdString().c_str()));
}
}
}
void FeedReaderMessageWidget::fillPostedMenu()
{
QMenu *menu = dynamic_cast<QMenu*>(sender()) ;
if (!menu) {
return;
}
disconnect(menu, SIGNAL(aboutToShow()), this, SLOT(fillPostedMenu()));
std::vector<RsPostedGroup> groups;
if (mFeedReader->getPostedGroups(groups, true)) {
for (std::vector<RsPostedGroup>::iterator it = groups.begin(); it != groups.end(); ++it) {
const RsPostedGroup &group = *it;
QAction *action = menu->addAction(QString::fromUtf8(group.mMeta.mGroupName.c_str()), this, SLOT(addToPosted()));
action->setData(QString::fromUtf8(group.mMeta.mGroupId.toStdString().c_str()));
}
}
}
void FeedReaderMessageWidget::addToForum()
{
QAction *action = dynamic_cast<QAction*>(sender()) ;
if (!action) {
return;
}
QString id = action->data().toString();
if (id.isEmpty()) {
return;
}
QList<QTreeWidgetItem*> selectedItems = ui->msgTreeWidget->selectedItems();
if (selectedItems.size() != 1) {
return;
}
std::string msgId = selectedItems[0]->data(COLUMN_MSG_DATA, ROLE_MSG_ID).toString().toStdString();
FeedMsgInfo msgInfo;
if (!mFeedReader->getMsgInfo(mFeedId, msgId, msgInfo)) {
return;
}
RsGxsGroupId forumId(id.toStdString());
CreateGxsForumMsg *msgDialog = new CreateGxsForumMsg(forumId, RsGxsMessageId(), RsGxsMessageId(), RsGxsId()) ;
msgDialog->setSubject(QString::fromUtf8(msgInfo.title.c_str()));
msgDialog->insertPastedText(QString::fromUtf8(msgInfo.description.c_str()));
msgDialog->show();
}
void FeedReaderMessageWidget::addToPosted()
{
QAction *action = dynamic_cast<QAction*>(sender()) ;
if (!action) {
return;
}
QString id = action->data().toString();
if (id.isEmpty()) {
return;
}
QList<QTreeWidgetItem*> selectedItems = ui->msgTreeWidget->selectedItems();
if (selectedItems.size() != 1) {
return;
}
std::string msgId = selectedItems[0]->data(COLUMN_MSG_DATA, ROLE_MSG_ID).toString().toStdString();
FeedMsgInfo msgInfo;
if (!mFeedReader->getMsgInfo(mFeedId, msgId, msgInfo)) {
return;
}
RsGxsGroupId postedId(id.toStdString());
PostedCreatePostDialog *msgDialog = new PostedCreatePostDialog(mFeedReader->posted(), postedId);
msgDialog->setTitle(QString::fromUtf8(msgInfo.title.c_str()));
msgDialog->setNotes(QString::fromUtf8(msgInfo.description.c_str()));
msgDialog->setLink(QString::fromUtf8(msgInfo.link.c_str()));
msgDialog->show();
}

View File

@ -73,6 +73,10 @@ private slots:
void openLinkMsg(); void openLinkMsg();
void copyLinkMsg(); void copyLinkMsg();
void retransformMsg(); void retransformMsg();
void fillForumMenu();
void fillPostedMenu();
void addToForum();
void addToPosted();
/* FeedReaderNotify */ /* FeedReaderNotify */
void feedChanged(uint32_t feedId, int type); void feedChanged(uint32_t feedId, int type);

View File

@ -25,8 +25,13 @@
#include <inttypes.h> #include <inttypes.h>
#include <string> #include <string>
#include <list> #include <list>
#include <vector>
class RsFeedReader; class RsFeedReader;
class RsGxsForums;
class RsPosted;
class RsGxsForumGroup;
class RsPostedGroup;
extern RsFeedReader *rsFeedReader; extern RsFeedReader *rsFeedReader;
enum RsFeedReaderErrorState { enum RsFeedReaderErrorState {
@ -232,6 +237,11 @@ public:
virtual bool retransformMsg(uint32_t feedId, const std::string &msgId) = 0; virtual bool retransformMsg(uint32_t feedId, const std::string &msgId) = 0;
virtual bool clearMessageCache(uint32_t feedId) = 0; virtual bool clearMessageCache(uint32_t feedId) = 0;
virtual RsGxsForums* forums() = 0;
virtual RsPosted* posted() = 0;
virtual bool getForumGroups(std::vector<RsGxsForumGroup> &groups, bool onlyOwn) = 0;
virtual bool getPostedGroups(std::vector<RsPostedGroup> &groups, bool onlyOwn) = 0;
virtual RsFeedReaderErrorState processXPath(const std::list<std::string> &xpathsToUse, const std::list<std::string> &xpathsToRemove, std::string &description, std::string &errorString) = 0; virtual RsFeedReaderErrorState processXPath(const std::list<std::string> &xpathsToUse, const std::list<std::string> &xpathsToRemove, std::string &description, std::string &errorString) = 0;
virtual RsFeedReaderErrorState processXslt(const std::string &xslt, std::string &description, std::string &errorString) = 0; virtual RsFeedReaderErrorState processXslt(const std::string &xslt, std::string &description, std::string &errorString) = 0;
}; };

View File

@ -194,8 +194,8 @@
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
</message> </message>
<message> <message>
<location line="+192"/> <location line="+206"/>
<location line="+148"/> <location line="+150"/>
<location line="+15"/> <location line="+15"/>
<source>Edit feed</source> <source>Edit feed</source>
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
@ -530,7 +530,7 @@
</message> </message>
<message> <message>
<location line="+26"/> <location line="+26"/>
<location filename="../gui/FeedReaderMessageWidget.cpp" line="+115"/> <location filename="../gui/FeedReaderMessageWidget.cpp" line="+117"/>
<source>Title</source> <source>Title</source>
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
</message> </message>
@ -616,13 +616,23 @@
<source>Remove</source> <source>Remove</source>
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
</message> </message>
<message>
<location line="+7"/>
<source>Add to forum</source>
<translation type="unfinished"></translation>
</message>
<message> <message>
<location line="+5"/> <location line="+5"/>
<source>Add to board</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+7"/>
<source>Retransform</source> <source>Retransform</source>
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
</message> </message>
<message> <message>
<location line="+385"/> <location line="+374"/>
<source>Hide</source> <source>Hide</source>
<translation type="unfinished"></translation> <translation type="unfinished"></translation>
</message> </message>

View File

@ -2532,3 +2532,85 @@ bool p3FeedReader::waitForToken(RsGxsIfaceHelper *interface, uint32_t token)
return false; return false;
} }
bool p3FeedReader::getForumGroups(std::vector<RsGxsForumGroup> &groups, bool onlyOwn)
{
if (!mForums) {
std::cerr << "p3FeedReader::getForumGroups - can't get groups, member mForums is not set" << std::endl;
return false;
}
RsTokReqOptions opts;
opts.mReqType = GXS_REQUEST_TYPE_GROUP_DATA;
uint32_t token;
if (!mForums->requestGroupInfo(token, opts)) {
std::cerr << "p3FeedReader::getForumGroups - can't get group list" << std::endl;
return false;
}
if (!waitForToken(mForums, token)) {
std::cerr << "p3FeedReader::getForumGroups - waitForToken for list failed" << std::endl;
return false;
}
if (!mForums->getGroupData(token, groups)) {
std::cerr << "p3FeedReader::getForumGroups - getGroupData failed" << std::endl;
return false;
}
if (onlyOwn) {
// filter groups
for (std::vector<RsGxsForumGroup>::iterator it = groups.begin(); it != groups.end(); ) {
const RsGxsForumGroup &group = *it;
if (IS_GROUP_PUBLISHER(group.mMeta.mSubscribeFlags) && IS_GROUP_ADMIN(group.mMeta.mSubscribeFlags)) {
++it;
} else {
it = groups.erase(it);
}
}
}
return true;
}
bool p3FeedReader::getPostedGroups(std::vector<RsPostedGroup> &groups, bool onlyOwn)
{
if (!mPosted) {
std::cerr << "p3FeedReader::getPostedGroups - can't get groups, member mPosted is not set" << std::endl;
return false;
}
RsTokReqOptions opts;
opts.mReqType = GXS_REQUEST_TYPE_GROUP_DATA;
uint32_t token;
if (!mPosted->requestGroupInfo(token, opts)) {
std::cerr << "p3FeedReader::getPostedGroups - can't get group list" << std::endl;
return false;
}
if (!waitForToken(mPosted, token)) {
std::cerr << "p3FeedReader::getPostedGroups - waitForToken for list failed" << std::endl;
return false;
}
if (!mPosted->getGroupData(token, groups)) {
std::cerr << "p3FeedReader::getForumGroups - getGroupData failed" << std::endl;
return false;
}
if (onlyOwn) {
// filter groups
for (std::vector<RsPostedGroup>::iterator it = groups.begin(); it != groups.end(); ) {
const RsPostedGroup &group = *it;
if (IS_GROUP_PUBLISHER(group.mMeta.mSubscribeFlags) && IS_GROUP_ADMIN(group.mMeta.mSubscribeFlags)) {
++it;
} else {
it = groups.erase(it);
}
}
}
return true;
}

View File

@ -75,6 +75,11 @@ public:
virtual bool retransformMsg(uint32_t feedId, const std::string &msgId); virtual bool retransformMsg(uint32_t feedId, const std::string &msgId);
virtual bool clearMessageCache(uint32_t feedId); virtual bool clearMessageCache(uint32_t feedId);
virtual RsGxsForums* forums() { return mForums; }
virtual RsPosted* posted() { return mPosted; }
virtual bool getForumGroups(std::vector<RsGxsForumGroup> &groups, bool onlyOwn);
virtual bool getPostedGroups(std::vector<RsPostedGroup> &groups, bool onlyOwn);
virtual RsFeedReaderErrorState processXPath(const std::list<std::string> &xpathsToUse, const std::list<std::string> &xpathsToRemove, std::string &description, std::string &errorString); virtual RsFeedReaderErrorState processXPath(const std::list<std::string> &xpathsToUse, const std::list<std::string> &xpathsToRemove, std::string &description, std::string &errorString);
virtual RsFeedReaderErrorState processXslt(const std::string &xslt, std::string &description, std::string &errorString); virtual RsFeedReaderErrorState processXslt(const std::string &xslt, std::string &description, std::string &errorString);

View File

@ -68,19 +68,19 @@ CreateGxsForumMsg::CreateGxsForumMsg(const RsGxsGroupId &fId, const RsGxsMessage
mStateHelper->addWidget(CREATEGXSFORUMMSG_FORUMINFO, ui->postButton); mStateHelper->addWidget(CREATEGXSFORUMMSG_FORUMINFO, ui->postButton);
mStateHelper->addWidget(CREATEGXSFORUMMSG_FORUMINFO, ui->innerFrame); mStateHelper->addWidget(CREATEGXSFORUMMSG_FORUMINFO, ui->innerFrame);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_FORUMINFO, ui->forumName); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_FORUMINFO, ui->forumName);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_FORUMINFO, ui->forumSubject); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_FORUMINFO, ui->forumSubject, false);
mStateHelper->addClear(CREATEGXSFORUMMSG_FORUMINFO, ui->forumName); mStateHelper->addClear(CREATEGXSFORUMMSG_FORUMINFO, ui->forumName);
mStateHelper->addWidget(CREATEGXSFORUMMSG_PARENTMSG, ui->postButton); mStateHelper->addWidget(CREATEGXSFORUMMSG_PARENTMSG, ui->postButton);
mStateHelper->addWidget(CREATEGXSFORUMMSG_PARENTMSG, ui->innerFrame); mStateHelper->addWidget(CREATEGXSFORUMMSG_PARENTMSG, ui->innerFrame);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_PARENTMSG, ui->forumName); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_PARENTMSG, ui->forumName);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_PARENTMSG, ui->forumSubject); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_PARENTMSG, ui->forumSubject, false);
mStateHelper->addClear(CREATEGXSFORUMMSG_PARENTMSG, ui->forumName); mStateHelper->addClear(CREATEGXSFORUMMSG_PARENTMSG, ui->forumName);
mStateHelper->addWidget(CREATEGXSFORUMMSG_ORIGMSG, ui->postButton); mStateHelper->addWidget(CREATEGXSFORUMMSG_ORIGMSG, ui->postButton);
mStateHelper->addWidget(CREATEGXSFORUMMSG_ORIGMSG, ui->innerFrame); mStateHelper->addWidget(CREATEGXSFORUMMSG_ORIGMSG, ui->innerFrame);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_ORIGMSG, ui->forumName); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_ORIGMSG, ui->forumName);
mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_ORIGMSG, ui->forumSubject); mStateHelper->addLoadPlaceholder(CREATEGXSFORUMMSG_ORIGMSG, ui->forumSubject, false);
mStateHelper->addClear(CREATEGXSFORUMMSG_ORIGMSG, ui->forumName); mStateHelper->addClear(CREATEGXSFORUMMSG_ORIGMSG, ui->forumName);