mirror of
https://github.com/RetroShare/RetroShare.git
synced 2025-04-28 19:06:10 -04:00
fixed merge
This commit is contained in:
commit
c81bdd9932
3
.gitmodules
vendored
3
.gitmodules
vendored
@ -32,3 +32,6 @@
|
|||||||
path = libretroshare
|
path = libretroshare
|
||||||
url = ../libretroshare
|
url = ../libretroshare
|
||||||
branch = master
|
branch = master
|
||||||
|
[submodule "retroshare-webui"]
|
||||||
|
path = retroshare-webui
|
||||||
|
url = git@github.com:Retroshare/RSNewWebUI
|
||||||
|
@ -68,6 +68,13 @@ retroshare_plugins {
|
|||||||
plugins.target = plugins
|
plugins.target = plugins
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rs_webui {
|
||||||
|
SUBDIRS += retroshare-webui
|
||||||
|
retroshare-webui.file = retroshare-webui/webui.pro
|
||||||
|
retroshare-webui.target = rs_webui
|
||||||
|
retroshare-webui.depends = retroshare_gui
|
||||||
|
}
|
||||||
|
|
||||||
wikipoos {
|
wikipoos {
|
||||||
SUBDIRS += pegmarkdown
|
SUBDIRS += pegmarkdown
|
||||||
pegmarkdown.file = supportlibs/pegmarkdown/pegmarkdown.pro
|
pegmarkdown.file = supportlibs/pegmarkdown/pegmarkdown.pro
|
||||||
|
@ -1 +1 @@
|
|||||||
Subproject commit 2ddc86fb575a61170f4c06a00152e3e7dc74c8f4
|
Subproject commit 659423769541169457c41f71c8a038e2d64ba079
|
@ -1 +1 @@
|
|||||||
Subproject commit a9d4447c5660337b4f7945d20e0f4ffd68d918e9
|
Subproject commit 74cd958cf8a3c8b3e2d3f8a22657b5e16bdad476
|
@ -357,8 +357,8 @@ void CreateCircleDialog::addMember(const QString& keyId, const QString& idtype,
|
|||||||
member->setText(RSCIRCLEID_COL_IDTYPE, idtype);
|
member->setText(RSCIRCLEID_COL_IDTYPE, idtype);
|
||||||
|
|
||||||
tree->addTopLevelItem(member);
|
tree->addTopLevelItem(member);
|
||||||
|
|
||||||
ui.members_groupBox->setTitle( tr("Invited Members") + " (" + QString::number(ui.treeWidget_membership->topLevelItemCount()) + ")" );
|
updateMembership();
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Maybe we can use RsGxsCircleGroup instead of RsGxsCircleDetails ??? (TODO)**/
|
/** Maybe we can use RsGxsCircleGroup instead of RsGxsCircleDetails ??? (TODO)**/
|
||||||
@ -413,6 +413,8 @@ void CreateCircleDialog::removeMember()
|
|||||||
|
|
||||||
// does this just work? (TODO)
|
// does this just work? (TODO)
|
||||||
delete(item);
|
delete(item);
|
||||||
|
|
||||||
|
updateMembership();
|
||||||
}
|
}
|
||||||
|
|
||||||
void CreateCircleDialog::createCircle()
|
void CreateCircleDialog::createCircle()
|
||||||
@ -952,3 +954,8 @@ void CreateCircleDialog::MembershipListCustomPopupMenu( QPoint )
|
|||||||
contextMnu.exec(QCursor::pos());
|
contextMnu.exec(QCursor::pos());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CreateCircleDialog::updateMembership()
|
||||||
|
{
|
||||||
|
ui.members_groupBox->setTitle( tr("Invited Members") + " (" + QString::number(ui.treeWidget_membership->topLevelItemCount()) + ")" );
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -56,6 +56,7 @@ private slots:
|
|||||||
void filterChanged(const QString &text);
|
void filterChanged(const QString &text);
|
||||||
void createNewGxsId();
|
void createNewGxsId();
|
||||||
void idTypeChanged();
|
void idTypeChanged();
|
||||||
|
void updateMembership();
|
||||||
|
|
||||||
/** Create the context popup menu and it's submenus */
|
/** Create the context popup menu and it's submenus */
|
||||||
void IdListCustomPopupMenu( QPoint point );
|
void IdListCustomPopupMenu( QPoint point );
|
||||||
|
@ -21,6 +21,7 @@
|
|||||||
#include "TransfersDialog.h"
|
#include "TransfersDialog.h"
|
||||||
|
|
||||||
#include "gui/notifyqt.h"
|
#include "gui/notifyqt.h"
|
||||||
|
#include "gui/SoundManager.h"
|
||||||
#include "gui/RetroShareLink.h"
|
#include "gui/RetroShareLink.h"
|
||||||
#include "gui/common/FilesDefs.h"
|
#include "gui/common/FilesDefs.h"
|
||||||
#include "gui/common/RsCollection.h"
|
#include "gui/common/RsCollection.h"
|
||||||
@ -1110,9 +1111,16 @@ void TransfersDialog::handleEvent_main_thread(std::shared_ptr<const RsEvent> eve
|
|||||||
if(!fe)
|
if(!fe)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
FileInfo nfo ;
|
||||||
|
if(!rsFiles->FileDetails(fe->mHash, RS_FILE_HINTS_DOWNLOAD, nfo))
|
||||||
|
return ;
|
||||||
|
|
||||||
switch (fe->mFileTransferEventCode)
|
switch (fe->mFileTransferEventCode)
|
||||||
{
|
{
|
||||||
case RsFileTransferEventCode::DOWNLOAD_COMPLETE:
|
case RsFileTransferEventCode::DOWNLOAD_COMPLETE:
|
||||||
|
SoundManager::play(SOUND_DOWNLOAD_COMPLETE);
|
||||||
|
if (Settings->getNotifyFlags() & RS_POPUP_DOWNLOAD)
|
||||||
|
NotifyQt::getInstance()->addToaster(RS_POPUP_DOWNLOAD, fe->mHash.toStdString(), nfo.fname.c_str(),"");
|
||||||
case RsFileTransferEventCode::COMPLETED_FILES_REMOVED:
|
case RsFileTransferEventCode::COMPLETED_FILES_REMOVED:
|
||||||
|
|
||||||
getUserNotify()->updateIcon();
|
getUserNotify()->updateIcon();
|
||||||
|
@ -1628,6 +1628,11 @@ NATStatus *MainWindow::natstatusInstance()
|
|||||||
return natstatus;
|
return natstatus;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void MainWindow::torstatusReset()
|
||||||
|
{
|
||||||
|
if(torstatus != nullptr)
|
||||||
|
torstatus->reset();
|
||||||
|
}
|
||||||
DHTStatus *MainWindow::dhtstatusInstance()
|
DHTStatus *MainWindow::dhtstatusInstance()
|
||||||
{
|
{
|
||||||
return dhtstatus;
|
return dhtstatus;
|
||||||
|
@ -187,6 +187,7 @@ public:
|
|||||||
RSComboBox *statusComboBoxInstance();
|
RSComboBox *statusComboBoxInstance();
|
||||||
PeerStatus *peerstatusInstance();
|
PeerStatus *peerstatusInstance();
|
||||||
NATStatus *natstatusInstance();
|
NATStatus *natstatusInstance();
|
||||||
|
void torstatusReset();
|
||||||
DHTStatus *dhtstatusInstance();
|
DHTStatus *dhtstatusInstance();
|
||||||
HashingStatus *hashingstatusInstance();
|
HashingStatus *hashingstatusInstance();
|
||||||
DiscStatus *discstatusInstance();
|
DiscStatus *discstatusInstance();
|
||||||
|
@ -441,6 +441,8 @@ void NewsFeed::handleConnectionEvent(std::shared_ptr<const RsEvent> event)
|
|||||||
{
|
{
|
||||||
case RsConnectionEventCode::PEER_CONNECTED:
|
case RsConnectionEventCode::PEER_CONNECTED:
|
||||||
addFeedItemIfUnique(new PeerItem(this, NEWSFEED_PEERLIST, e.mSslId, PEER_TYPE_CONNECT, false), true);
|
addFeedItemIfUnique(new PeerItem(this, NEWSFEED_PEERLIST, e.mSslId, PEER_TYPE_CONNECT, false), true);
|
||||||
|
if (Settings->getNotifyFlags() & RS_POPUP_CONNECT)
|
||||||
|
NotifyQt::getInstance()->addToaster(RS_POPUP_CONNECT, e.mSslId.toStdString().c_str(), "", "");
|
||||||
break;
|
break;
|
||||||
case RsConnectionEventCode::PEER_DISCONNECTED: // not handled yet
|
case RsConnectionEventCode::PEER_DISCONNECTED: // not handled yet
|
||||||
break;
|
break;
|
||||||
@ -476,6 +478,7 @@ void NewsFeed::handleSecurityEvent(std::shared_ptr<const RsEvent> event)
|
|||||||
addFeedItemIfUnique(new PeerItem(this, NEWSFEED_PEERLIST, e.mSslId, PEER_TYPE_HELLO, false), true );
|
addFeedItemIfUnique(new PeerItem(this, NEWSFEED_PEERLIST, e.mSslId, PEER_TYPE_HELLO, false), true );
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
uint32_t FeedItemType=0;
|
uint32_t FeedItemType=0;
|
||||||
|
|
||||||
@ -504,6 +507,9 @@ void NewsFeed::handleSecurityEvent(std::shared_ptr<const RsEvent> event)
|
|||||||
|
|
||||||
if (Settings->getMessageFlags() & RS_MESSAGE_CONNECT_ATTEMPT)
|
if (Settings->getMessageFlags() & RS_MESSAGE_CONNECT_ATTEMPT)
|
||||||
MessageComposer::addConnectAttemptMsg(e.mPgpId, e.mSslId, QString::fromStdString(det.name + "(" + det.location + ")"));
|
MessageComposer::addConnectAttemptMsg(e.mPgpId, e.mSslId, QString::fromStdString(det.name + "(" + det.location + ")"));
|
||||||
|
|
||||||
|
if (Settings->getNotifyFlags() & RS_POPUP_CONNECT_ATTEMPT)
|
||||||
|
NotifyQt::getInstance()->addToaster(RS_POPUP_CONNECT_ATTEMPT, e.mPgpId.toStdString().c_str(), det.location, e.mSslId.toStdString().c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
void NewsFeed::testFeeds(uint /*notifyFlags*/)
|
void NewsFeed::testFeeds(uint /*notifyFlags*/)
|
||||||
|
@ -29,10 +29,10 @@ PulseMessage::PulseMessage(QWidget *parent)
|
|||||||
{
|
{
|
||||||
setupUi(this);
|
setupUi(this);
|
||||||
|
|
||||||
connect(label_image1, SIGNAL(clicked()), this, SLOT(viewPicture()));
|
connect(label_image1, SIGNAL(clicked()), this, SLOT(viewPictureOne()));
|
||||||
connect(label_image2, SIGNAL(clicked()), this, SLOT(viewPicture()));
|
connect(label_image2, SIGNAL(clicked()), this, SLOT(viewPictureTwo()));
|
||||||
connect(label_image3, SIGNAL(clicked()), this, SLOT(viewPicture()));
|
connect(label_image3, SIGNAL(clicked()), this, SLOT(viewPictureThree()));
|
||||||
connect(label_image4, SIGNAL(clicked()), this, SLOT(viewPicture()));
|
connect(label_image4, SIGNAL(clicked()), this, SLOT(viewPictureFour()));
|
||||||
}
|
}
|
||||||
|
|
||||||
void PulseMessage::setup(RsWirePulseSPtr pulse)
|
void PulseMessage::setup(RsWirePulseSPtr pulse)
|
||||||
@ -148,7 +148,7 @@ void PulseMessage::setRefImageCount(uint32_t count)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void PulseMessage::viewPicture()
|
void PulseMessage::viewPictureOne()
|
||||||
{
|
{
|
||||||
PhotoView *photoView = new PhotoView(this);
|
PhotoView *photoView = new PhotoView(this);
|
||||||
|
|
||||||
@ -158,21 +158,69 @@ void PulseMessage::viewPicture()
|
|||||||
pixmap.loadFromData(mPulse->mImage1.mData, mPulse->mImage1.mSize);
|
pixmap.loadFromData(mPulse->mImage1.mData, mPulse->mImage1.mSize);
|
||||||
photoView->setPixmap(pixmap);
|
photoView->setPixmap(pixmap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString timestamp = misc::timeRelativeToNow(mPulse->mRefPublishTs);
|
||||||
|
|
||||||
|
photoView->setTitle(QString::fromStdString(mPulse->mPulseText));
|
||||||
|
photoView->setGroupNameString(QString::fromStdString(mPulse->mRefGroupName));
|
||||||
|
photoView->setTime(timestamp);
|
||||||
|
//photoView->setGroupId(mPulse->mRefGroupId);
|
||||||
|
|
||||||
|
photoView->show();
|
||||||
|
|
||||||
|
/* window will destroy itself! */
|
||||||
|
}
|
||||||
|
|
||||||
|
void PulseMessage::viewPictureTwo()
|
||||||
|
{
|
||||||
|
PhotoView *photoView = new PhotoView(this);
|
||||||
|
|
||||||
if (!mPulse->mImage2.empty()) {
|
if (!mPulse->mImage2.empty()) {
|
||||||
// install image.
|
// install image.
|
||||||
QPixmap pixmap;
|
QPixmap pixmap;
|
||||||
pixmap.loadFromData(mPulse->mImage2.mData, mPulse->mImage2.mSize);
|
pixmap.loadFromData(mPulse->mImage2.mData, mPulse->mImage2.mSize);
|
||||||
photoView->setPixmap(pixmap);
|
photoView->setPixmap(pixmap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString timestamp = misc::timeRelativeToNow(mPulse->mRefPublishTs);
|
||||||
|
|
||||||
|
photoView->setTitle(QString::fromStdString(mPulse->mPulseText));
|
||||||
|
photoView->setGroupNameString(QString::fromStdString(mPulse->mRefGroupName));
|
||||||
|
photoView->setTime(timestamp);
|
||||||
|
//photoView->setGroupId(mPulse->mRefGroupId);
|
||||||
|
|
||||||
|
photoView->show();
|
||||||
|
|
||||||
|
/* window will destroy itself! */
|
||||||
|
}
|
||||||
|
|
||||||
|
void PulseMessage::viewPictureThree()
|
||||||
|
{
|
||||||
|
PhotoView *photoView = new PhotoView(this);
|
||||||
|
|
||||||
if (!mPulse->mImage3.empty()) {
|
if (!mPulse->mImage3.empty()) {
|
||||||
// install image.
|
// install image.
|
||||||
QPixmap pixmap;
|
QPixmap pixmap;
|
||||||
pixmap.loadFromData(mPulse->mImage3.mData, mPulse->mImage3.mSize);
|
pixmap.loadFromData(mPulse->mImage3.mData, mPulse->mImage3.mSize);
|
||||||
photoView->setPixmap(pixmap);
|
photoView->setPixmap(pixmap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString timestamp = misc::timeRelativeToNow(mPulse->mRefPublishTs);
|
||||||
|
|
||||||
|
photoView->setTitle(QString::fromStdString(mPulse->mPulseText));
|
||||||
|
photoView->setGroupNameString(QString::fromStdString(mPulse->mRefGroupName));
|
||||||
|
photoView->setTime(timestamp);
|
||||||
|
//photoView->setGroupId(mPulse->mRefGroupId);
|
||||||
|
|
||||||
|
photoView->show();
|
||||||
|
|
||||||
|
/* window will destroy itself! */
|
||||||
|
}
|
||||||
|
|
||||||
|
void PulseMessage::viewPictureFour()
|
||||||
|
{
|
||||||
|
PhotoView *photoView = new PhotoView(this);
|
||||||
|
|
||||||
if (!mPulse->mImage4.empty()) {
|
if (!mPulse->mImage4.empty()) {
|
||||||
// install image.
|
// install image.
|
||||||
QPixmap pixmap;
|
QPixmap pixmap;
|
||||||
|
@ -37,7 +37,10 @@ public:
|
|||||||
void setRefImageCount(uint32_t count);
|
void setRefImageCount(uint32_t count);
|
||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void viewPicture();
|
void viewPictureOne();
|
||||||
|
void viewPictureTwo();
|
||||||
|
void viewPictureThree();
|
||||||
|
void viewPictureFour();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
RsWirePulseSPtr mPulse;
|
RsWirePulseSPtr mPulse;
|
||||||
|
@ -51,7 +51,7 @@ static QHash<QString, QPixmap> iconcache;
|
|||||||
void Emoticons::load()
|
void Emoticons::load()
|
||||||
{
|
{
|
||||||
loadSmiley();
|
loadSmiley();
|
||||||
filters << "*.png" << "*.jpg" << "*.gif" << "*.webp";
|
filters << "*.png" << "*.jpg" << "*.jpeg" << "*.gif" << "*.webp";
|
||||||
stickerFolders << (QString::fromStdString(RsAccounts::AccountDirectory()) + "/stickers"); //under account, unique for user
|
stickerFolders << (QString::fromStdString(RsAccounts::AccountDirectory()) + "/stickers"); //under account, unique for user
|
||||||
stickerFolders << (QString::fromStdString(RsAccounts::ConfigDirectory()) + "/stickers"); //under .retroshare, shared between users
|
stickerFolders << (QString::fromStdString(RsAccounts::ConfigDirectory()) + "/stickers"); //under .retroshare, shared between users
|
||||||
stickerFolders << (QString::fromStdString(RsAccounts::systemDataDirectory()) + "/stickers"); //exe's folder, shipped with RS
|
stickerFolders << (QString::fromStdString(RsAccounts::systemDataDirectory()) + "/stickers"); //exe's folder, shipped with RS
|
||||||
|
@ -33,11 +33,11 @@
|
|||||||
|
|
||||||
#include "GxsChannelPostFilesModel.h"
|
#include "GxsChannelPostFilesModel.h"
|
||||||
|
|
||||||
//#define DEBUG_CHANNEL_MODEL
|
//#define DEBUG_CHANNEL_FILES_MODEL
|
||||||
|
|
||||||
Q_DECLARE_METATYPE(ChannelPostFileInfo)
|
Q_DECLARE_METATYPE(ChannelPostFileInfo)
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
static std::ostream& operator<<(std::ostream& o, const QModelIndex& i);// defined elsewhere
|
static std::ostream& operator<<(std::ostream& o, const QModelIndex& i);// defined elsewhere
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -161,8 +161,8 @@ QModelIndex RsGxsChannelPostFilesModel::index(int row, int column, const QModelI
|
|||||||
|
|
||||||
quintptr ref = getChildRef(parent.internalId(),row);
|
quintptr ref = getChildRef(parent.internalId(),row);
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
std::cerr << "index-3(" << row << "," << column << " parent=" << parent << ") : " << createIndex(row,column,ref) << std::endl;
|
RsDbg() << "index-3(" << row << "," << column << " parent=" << parent << ") : " << createIndex(row,column,ref) ;
|
||||||
#endif
|
#endif
|
||||||
return createIndex(row,column,ref) ;
|
return createIndex(row,column,ref) ;
|
||||||
}
|
}
|
||||||
@ -242,7 +242,7 @@ QVariant RsGxsChannelPostFilesModel::headerData(int section, Qt::Orientation /*o
|
|||||||
|
|
||||||
QVariant RsGxsChannelPostFilesModel::data(const QModelIndex &index, int role) const
|
QVariant RsGxsChannelPostFilesModel::data(const QModelIndex &index, int role) const
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
std::cerr << "calling data(" << index << ") role=" << role << std::endl;
|
std::cerr << "calling data(" << index << ") role=" << role << std::endl;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -259,13 +259,13 @@ QVariant RsGxsChannelPostFilesModel::data(const QModelIndex &index, int role) co
|
|||||||
quintptr ref = (index.isValid())?index.internalId():0 ;
|
quintptr ref = (index.isValid())?index.internalId():0 ;
|
||||||
uint32_t entry = 0;
|
uint32_t entry = 0;
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
std::cerr << "data(" << index << ")" ;
|
std::cerr << "data(" << index << ")" ;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if(!ref)
|
if(!ref)
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
std::cerr << " [empty]" << std::endl;
|
std::cerr << " [empty]" << std::endl;
|
||||||
#endif
|
#endif
|
||||||
return QVariant() ;
|
return QVariant() ;
|
||||||
@ -273,7 +273,7 @@ QVariant RsGxsChannelPostFilesModel::data(const QModelIndex &index, int role) co
|
|||||||
|
|
||||||
if(!convertRefPointerToTabEntry(ref,entry) || entry >= mFilteredFiles.size())
|
if(!convertRefPointerToTabEntry(ref,entry) || entry >= mFilteredFiles.size())
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
std::cerr << "Bad pointer: " << (void*)ref << std::endl;
|
std::cerr << "Bad pointer: " << (void*)ref << std::endl;
|
||||||
#endif
|
#endif
|
||||||
return QVariant() ;
|
return QVariant() ;
|
||||||
@ -426,7 +426,6 @@ QVariant RsGxsChannelPostFilesModel::userRole(const ChannelPostFileInfo& fmpe,in
|
|||||||
|
|
||||||
void RsGxsChannelPostFilesModel::clear()
|
void RsGxsChannelPostFilesModel::clear()
|
||||||
{
|
{
|
||||||
|
|
||||||
initEmptyHierarchy();
|
initEmptyHierarchy();
|
||||||
|
|
||||||
emit channelLoaded();
|
emit channelLoaded();
|
||||||
@ -444,7 +443,7 @@ void RsGxsChannelPostFilesModel::setFiles(const std::list<ChannelPostFileInfo> &
|
|||||||
for(uint32_t i=0;i<mFiles.size();++i)
|
for(uint32_t i=0;i<mFiles.size();++i)
|
||||||
mFilteredFiles.push_back(i);
|
mFilteredFiles.push_back(i);
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
// debug_dump();
|
// debug_dump();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -463,3 +462,61 @@ void RsGxsChannelPostFilesModel::setFiles(const std::list<ChannelPostFileInfo> &
|
|||||||
|
|
||||||
postMods();
|
postMods();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RsGxsChannelPostFilesModel::update_files(std::set<ChannelPostFileInfo>& added_files,std::set<ChannelPostFileInfo>& removed_files)
|
||||||
|
{
|
||||||
|
// 1 - remove common files from both lists
|
||||||
|
|
||||||
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
|
RsDbg() << "RsGxsChannelPostsFilesModel:: updating files." ;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
for(auto afit=added_files.begin();afit!=added_files.end();)
|
||||||
|
{
|
||||||
|
auto rfit = removed_files.find(*afit);
|
||||||
|
|
||||||
|
if(rfit != removed_files.end())
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
|
RsDbg() << " Eliminating common file " << rfit->mName ;
|
||||||
|
#endif
|
||||||
|
removed_files.erase(rfit);
|
||||||
|
auto tmp = afit;
|
||||||
|
++tmp;
|
||||||
|
added_files.erase(afit);
|
||||||
|
afit = tmp;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
++afit;
|
||||||
|
}
|
||||||
|
|
||||||
|
RsDbg() << " Remains: " << added_files.size() << " added files and " << removed_files.size() << " removed files" ;
|
||||||
|
|
||||||
|
// 2 - add whatever file remains,
|
||||||
|
|
||||||
|
for(const auto& f:removed_files)
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
|
RsDbg() << " Removing deleted file " << f.mName ;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
for(uint32_t i=0;i<mFiles.size();++i)
|
||||||
|
if(mFiles[i].mHash == f.mHash)
|
||||||
|
{
|
||||||
|
mFiles[i] = mFiles.back();
|
||||||
|
mFiles.pop_back();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 3 - add other files. We do not check that they are duplicates, because the list of files includes duplicates.
|
||||||
|
|
||||||
|
for(const auto& f:added_files )
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_CHANNEL_FILES_MODEL
|
||||||
|
RsDbg() << " Adding new file " << f.mName ;
|
||||||
|
#endif
|
||||||
|
mFilteredFiles.push_back(mFiles.size());
|
||||||
|
mFiles.push_back(f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -41,34 +41,34 @@ class QTimer;
|
|||||||
struct ChannelPostFileInfo: public RsGxsFile
|
struct ChannelPostFileInfo: public RsGxsFile
|
||||||
{
|
{
|
||||||
ChannelPostFileInfo(const RsGxsFile& gxs_file,rstime_t t)
|
ChannelPostFileInfo(const RsGxsFile& gxs_file,rstime_t t)
|
||||||
: RsGxsFile(gxs_file),mPublishTime(t)
|
: RsGxsFile(gxs_file),mPublishTime(t)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
ChannelPostFileInfo() : mPublishTime(0) {}
|
ChannelPostFileInfo() : mPublishTime(0) {}
|
||||||
|
|
||||||
rstime_t mPublishTime;
|
rstime_t mPublishTime; // related post publish time
|
||||||
};
|
};
|
||||||
|
|
||||||
// This class is the item model used by Qt to display the information
|
// This class is the item model used by Qt to display the information
|
||||||
|
|
||||||
class RsGxsChannelPostFilesModel : public QAbstractItemModel
|
class RsGxsChannelPostFilesModel : public QAbstractItemModel
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit RsGxsChannelPostFilesModel(QObject *parent = NULL);
|
explicit RsGxsChannelPostFilesModel(QObject *parent = NULL);
|
||||||
~RsGxsChannelPostFilesModel(){}
|
~RsGxsChannelPostFilesModel(){}
|
||||||
|
|
||||||
enum Columns {
|
enum Columns {
|
||||||
COLUMN_FILES_NAME = 0x00,
|
COLUMN_FILES_NAME = 0x00,
|
||||||
COLUMN_FILES_SIZE = 0x01,
|
COLUMN_FILES_SIZE = 0x01,
|
||||||
COLUMN_FILES_FILE = 0x02,
|
COLUMN_FILES_FILE = 0x02,
|
||||||
COLUMN_FILES_DATE = 0x03,
|
COLUMN_FILES_DATE = 0x03,
|
||||||
COLUMN_FILES_NB_COLUMNS = 0x04
|
COLUMN_FILES_NB_COLUMNS = 0x04
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Roles{ SortRole = Qt::UserRole+1,
|
enum Roles{ SortRole = Qt::UserRole+1,
|
||||||
FilterRole = Qt::UserRole+2,
|
FilterRole = Qt::UserRole+2,
|
||||||
};
|
};
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
@ -77,22 +77,25 @@ public:
|
|||||||
};
|
};
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
QModelIndex root() const{ return createIndex(0,0,(void*)NULL) ;}
|
QModelIndex root() const{ return createIndex(0,0,(void*)NULL) ;}
|
||||||
|
|
||||||
// This method will asynchroneously update the data
|
// This method will asynchroneously update the data
|
||||||
void setFiles(const std::list<ChannelPostFileInfo>& files);
|
void setFiles(const std::list<ChannelPostFileInfo>& files);
|
||||||
void setFilter(const QStringList &strings, uint32_t &count) ;
|
void setFilter(const QStringList &strings, uint32_t &count) ;
|
||||||
|
|
||||||
|
// This method adds/removes the given lists of files. Useful when a single post is updated
|
||||||
|
void update_files(std::set<ChannelPostFileInfo> &added_files, std::set<ChannelPostFileInfo> &removed_files);
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
QModelIndex getIndexOfFile(const RsFileHash& hash) const;
|
QModelIndex getIndexOfFile(const RsFileHash& hash) const;
|
||||||
void setSortMode(SortMode mode) ;
|
void setSortMode(SortMode mode) ;
|
||||||
|
|
||||||
void setTextColorRead (QColor color) { mTextColorRead = color;}
|
void setTextColorRead (QColor color) { mTextColorRead = color;}
|
||||||
void setTextColorUnread (QColor color) { mTextColorUnread = color;}
|
void setTextColorUnread (QColor color) { mTextColorUnread = color;}
|
||||||
void setTextColorUnreadChildren(QColor color) { mTextColorUnreadChildren = color;}
|
void setTextColorUnreadChildren(QColor color) { mTextColorUnreadChildren = color;}
|
||||||
void setTextColorNotSubscribed (QColor color) { mTextColorNotSubscribed = color;}
|
void setTextColorNotSubscribed (QColor color) { mTextColorNotSubscribed = color;}
|
||||||
void setTextColorMissing (QColor color) { mTextColorMissing = color;}
|
void setTextColorMissing (QColor color) { mTextColorMissing = color;}
|
||||||
void setAuthorOpinion(const QModelIndex& indx,RsOpinion op);
|
void setAuthorOpinion(const QModelIndex& indx,RsOpinion op);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Helper functions
|
// Helper functions
|
||||||
@ -112,25 +115,25 @@ public:
|
|||||||
Qt::ItemFlags flags(const QModelIndex& index) const override;
|
Qt::ItemFlags flags(const QModelIndex& index) const override;
|
||||||
|
|
||||||
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
|
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
|
||||||
QVariant headerData(int section, Qt::Orientation orientation, int role) const override;
|
QVariant headerData(int section, Qt::Orientation orientation, int role) const override;
|
||||||
|
|
||||||
// Custom item roles
|
// Custom item roles
|
||||||
|
|
||||||
QVariant sizeHintRole (int col) const;
|
QVariant sizeHintRole (int col) const;
|
||||||
QVariant displayRole (const ChannelPostFileInfo& fmpe, int col) const;
|
QVariant displayRole (const ChannelPostFileInfo& fmpe, int col) const;
|
||||||
QVariant toolTipRole (const ChannelPostFileInfo& fmpe, int col) const;
|
QVariant toolTipRole (const ChannelPostFileInfo& fmpe, int col) const;
|
||||||
QVariant userRole (const ChannelPostFileInfo& fmpe, int col) const;
|
QVariant userRole (const ChannelPostFileInfo& fmpe, int col) const;
|
||||||
QVariant sortRole (const ChannelPostFileInfo& fmpe, int col) const;
|
QVariant sortRole (const ChannelPostFileInfo& fmpe, int col) const;
|
||||||
QVariant filterRole (const ChannelPostFileInfo& fmpe, int col) const;
|
QVariant filterRole (const ChannelPostFileInfo& fmpe, int col) const;
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
QVariant decorationRole(const ForumModelPostEntry& fmpe, int col) const;
|
QVariant decorationRole(const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant pinnedRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant pinnedRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant missingRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant missingRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant statusRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant statusRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant authorRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant authorRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant fontRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant fontRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant textColorRole (const ForumModelPostEntry& fmpe, int col) const;
|
QVariant textColorRole (const ForumModelPostEntry& fmpe, int col) const;
|
||||||
QVariant backgroundRole(const ForumModelPostEntry& fmpe, int col) const;
|
QVariant backgroundRole(const ForumModelPostEntry& fmpe, int col) const;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
@ -151,20 +154,20 @@ private:
|
|||||||
bool mFilteringEnabled;
|
bool mFilteringEnabled;
|
||||||
SortMode mSortMode;
|
SortMode mSortMode;
|
||||||
#endif
|
#endif
|
||||||
void preMods() ;
|
void preMods() ;
|
||||||
void postMods() ;
|
void postMods() ;
|
||||||
|
|
||||||
quintptr getParentRow(quintptr ref,int& row) const;
|
quintptr getParentRow(quintptr ref,int& row) const;
|
||||||
quintptr getChildRef(quintptr ref, int index) const;
|
quintptr getChildRef(quintptr ref, int index) const;
|
||||||
int getChildrenCount(quintptr ref) const;
|
int getChildrenCount(quintptr ref) const;
|
||||||
|
|
||||||
static bool convertTabEntryToRefPointer(uint32_t entry, quintptr& ref);
|
static bool convertTabEntryToRefPointer(uint32_t entry, quintptr& ref);
|
||||||
static bool convertRefPointerToTabEntry(quintptr ref,uint32_t& entry);
|
static bool convertRefPointerToTabEntry(quintptr ref,uint32_t& entry);
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
static void generateMissingItem(const RsGxsMessageId &msgId,ChannelPostsModelPostEntry& entry);
|
static void generateMissingItem(const RsGxsMessageId &msgId,ChannelPostsModelPostEntry& entry);
|
||||||
#endif
|
#endif
|
||||||
void initEmptyHierarchy();
|
void initEmptyHierarchy();
|
||||||
|
|
||||||
std::vector<int> mFilteredFiles ; // store the list of files for the post
|
std::vector<int> mFilteredFiles ; // store the list of files for the post
|
||||||
std::vector<ChannelPostFileInfo> mFiles ; // store the list of files for the post
|
std::vector<ChannelPostFileInfo> mFiles ; // store the list of files for the post
|
||||||
|
@ -35,10 +35,10 @@
|
|||||||
#include "GxsChannelPostsModel.h"
|
#include "GxsChannelPostsModel.h"
|
||||||
#include "GxsChannelPostFilesModel.h"
|
#include "GxsChannelPostFilesModel.h"
|
||||||
|
|
||||||
#define DEBUG_CHANNEL_MODEL
|
//#define DEBUG_CHANNEL_MODEL_DATA
|
||||||
|
//#define DEBUG_CHANNEL_MODEL
|
||||||
|
|
||||||
Q_DECLARE_METATYPE(RsMsgMetaData)
|
Q_DECLARE_METATYPE(RsMsgMetaData)
|
||||||
|
|
||||||
Q_DECLARE_METATYPE(RsGxsChannelPost)
|
Q_DECLARE_METATYPE(RsGxsChannelPost)
|
||||||
|
|
||||||
std::ostream& operator<<(std::ostream& o, const QModelIndex& i);// defined elsewhere
|
std::ostream& operator<<(std::ostream& o, const QModelIndex& i);// defined elsewhere
|
||||||
@ -47,14 +47,6 @@ RsGxsChannelPostsModel::RsGxsChannelPostsModel(QObject *parent)
|
|||||||
: QAbstractItemModel(parent), mTreeMode(RsGxsChannelPostsModel::TREE_MODE_GRID), mColumns(6)
|
: QAbstractItemModel(parent), mTreeMode(RsGxsChannelPostsModel::TREE_MODE_GRID), mColumns(6)
|
||||||
{
|
{
|
||||||
initEmptyHierarchy();
|
initEmptyHierarchy();
|
||||||
|
|
||||||
mEventHandlerId = 0;
|
|
||||||
// Needs to be asynced because this function is called by another thread!
|
|
||||||
|
|
||||||
rsEvents->registerEventsHandler( [this](std::shared_ptr<const RsEvent> event)
|
|
||||||
{
|
|
||||||
RsQThreadUtils::postToObject([=](){ handleEvent_main_thread(event); }, this );
|
|
||||||
}, mEventHandlerId, RsEventType::GXS_CHANNELS );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
RsGxsChannelPostsModel::~RsGxsChannelPostsModel()
|
RsGxsChannelPostsModel::~RsGxsChannelPostsModel()
|
||||||
@ -72,7 +64,7 @@ void RsGxsChannelPostsModel::setMode(TreeMode mode)
|
|||||||
triggerViewUpdate();
|
triggerViewUpdate();
|
||||||
}
|
}
|
||||||
|
|
||||||
void updateCommentCounts( std::vector<RsGxsChannelPost>& posts, std::vector<RsGxsComment>& comments)
|
void RsGxsChannelPostsModel::computeCommentCounts( std::vector<RsGxsChannelPost>& posts, std::vector<RsGxsComment>& comments)
|
||||||
{
|
{
|
||||||
// Store posts IDs in a std::map to avoid a quadratic cost
|
// Store posts IDs in a std::map to avoid a quadratic cost
|
||||||
|
|
||||||
@ -108,99 +100,6 @@ void updateCommentCounts( std::vector<RsGxsChannelPost>& posts, std::vector<RsGx
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void RsGxsChannelPostsModel::handleEvent_main_thread(std::shared_ptr<const RsEvent> event)
|
|
||||||
{
|
|
||||||
const RsGxsChannelEvent *e = dynamic_cast<const RsGxsChannelEvent*>(event.get());
|
|
||||||
|
|
||||||
if(!e)
|
|
||||||
return;
|
|
||||||
|
|
||||||
switch(e->mChannelEventCode)
|
|
||||||
{
|
|
||||||
case RsChannelEventCode::UPDATED_MESSAGE:
|
|
||||||
case RsChannelEventCode::READ_STATUS_CHANGED:
|
|
||||||
{
|
|
||||||
// Normally we should just emit dataChanged() on the index of the data that has changed:
|
|
||||||
// We need to update the data!
|
|
||||||
|
|
||||||
// make a copy of e, so as to avoid destruction of the shared pointer during async thread execution, since [e] doesn't actually tell
|
|
||||||
// the original shared_ptr that it is copied! So no counter is updated in event, which will be destroyed (as e will be) during or even before
|
|
||||||
// the execution of the lambda.
|
|
||||||
|
|
||||||
RsGxsChannelEvent E(*e);
|
|
||||||
|
|
||||||
if(E.mChannelGroupId == mChannelGroup.mMeta.mGroupId)
|
|
||||||
RsThread::async([this, E]()
|
|
||||||
{
|
|
||||||
// 1 - get message data from p3GxsChannels. No need for pointers here, because we send only a single post to postToObject()
|
|
||||||
// At this point we dont know what kind of msg id we have. It can be a vote, a comment or an actual message.
|
|
||||||
|
|
||||||
std::vector<RsGxsChannelPost> posts;
|
|
||||||
std::vector<RsGxsComment> comments;
|
|
||||||
std::vector<RsGxsVote> votes;
|
|
||||||
std::set<RsGxsMessageId> msg_ids{ E.mChannelMsgId };
|
|
||||||
|
|
||||||
if(!rsGxsChannels->getChannelContent(E.mChannelGroupId,msg_ids, posts,comments,votes))
|
|
||||||
{
|
|
||||||
std::cerr << __PRETTY_FUNCTION__ << " failed to retrieve channel message data for channel/msg " << E.mChannelGroupId << "/" << E.mChannelMsgId << std::endl;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check if what we have actually is a comment or a vote. If so we need to update the actual message they refer to
|
|
||||||
|
|
||||||
if(posts.empty()) // means we have a comment or a vote
|
|
||||||
{
|
|
||||||
msg_ids.clear();
|
|
||||||
|
|
||||||
for(auto c:comments) msg_ids.insert(c.mMeta.mThreadId);
|
|
||||||
for(auto v:votes ) msg_ids.insert(v.mMeta.mThreadId);
|
|
||||||
|
|
||||||
comments.clear();
|
|
||||||
votes.clear();
|
|
||||||
|
|
||||||
if(!rsGxsChannels->getChannelContent(E.mChannelGroupId,msg_ids,posts,comments,votes))
|
|
||||||
{
|
|
||||||
std::cerr << __PRETTY_FUNCTION__ << " failed to retrieve channel message data for channel/msg " << E.mChannelGroupId << "/" << E.mChannelMsgId << std::endl;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Need to call this in order to get the actuall comment count. The previous call only retrieves the message, since we supplied the message ID.
|
|
||||||
// another way to go would be to save the comment ids of the existing message and re-insert them before calling getChannelContent.
|
|
||||||
|
|
||||||
if(!rsGxsChannels->getChannelComments(E.mChannelGroupId,msg_ids,comments))
|
|
||||||
{
|
|
||||||
std::cerr << __PRETTY_FUNCTION__ << " failed to retrieve message comment data for channel/msg " << E.mChannelGroupId << "/" << E.mChannelMsgId << std::endl;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
updateCommentCounts(posts,comments);
|
|
||||||
|
|
||||||
// 2 - update the model in the UI thread.
|
|
||||||
|
|
||||||
RsQThreadUtils::postToObject( [posts,this]()
|
|
||||||
{
|
|
||||||
for(uint32_t i=0;i<posts.size();++i)
|
|
||||||
{
|
|
||||||
// linear search. Not good at all, but normally this is for a single post.
|
|
||||||
|
|
||||||
for(uint32_t j=0;j<mPosts.size();++j)
|
|
||||||
if(mPosts[j].mMeta.mMsgId == posts[i].mMeta.mMsgId)
|
|
||||||
{
|
|
||||||
mPosts[j] = posts[i];
|
|
||||||
|
|
||||||
triggerViewUpdate();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},this);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void RsGxsChannelPostsModel::initEmptyHierarchy()
|
void RsGxsChannelPostsModel::initEmptyHierarchy()
|
||||||
{
|
{
|
||||||
beginResetModel();
|
beginResetModel();
|
||||||
@ -241,7 +140,31 @@ void RsGxsChannelPostsModel::getFilesList(std::list<ChannelPostFileInfo>& files)
|
|||||||
files.push_back(it.second);
|
files.push_back(it.second);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RsGxsChannelPostsModel::postPassesFilter(const RsGxsChannelPost& post,const QStringList& strings,bool only_unread) const
|
||||||
|
{
|
||||||
|
bool passes_strings = true;
|
||||||
|
|
||||||
|
for(auto& s:strings)
|
||||||
|
passes_strings = passes_strings && QString::fromStdString(post.mMeta.mMsgName).contains(s,Qt::CaseInsensitive);
|
||||||
|
|
||||||
|
if(strings.empty())
|
||||||
|
passes_strings = true;
|
||||||
|
|
||||||
|
if(passes_strings && (!only_unread || (IS_MSG_UNREAD(post.mMeta.mMsgStatus) || IS_MSG_NEW(post.mMeta.mMsgStatus))))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
void RsGxsChannelPostsModel::setFilter(const QStringList& strings,bool only_unread, uint32_t& count)
|
void RsGxsChannelPostsModel::setFilter(const QStringList& strings,bool only_unread, uint32_t& count)
|
||||||
|
{
|
||||||
|
mFilteredStrings = strings;
|
||||||
|
mFilterUnread = only_unread;
|
||||||
|
|
||||||
|
updateFilter(count);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RsGxsChannelPostsModel::updateFilter(uint32_t& count)
|
||||||
{
|
{
|
||||||
preMods();
|
preMods();
|
||||||
|
|
||||||
@ -252,18 +175,8 @@ void RsGxsChannelPostsModel::setFilter(const QStringList& strings,bool only_unre
|
|||||||
endResetModel();
|
endResetModel();
|
||||||
|
|
||||||
for(size_t i=0;i<mPosts.size();++i)
|
for(size_t i=0;i<mPosts.size();++i)
|
||||||
{
|
if(postPassesFilter(mPosts[i],mFilteredStrings,mFilterUnread))
|
||||||
bool passes_strings = true;
|
mFilteredPosts.push_back(i);
|
||||||
|
|
||||||
for(auto& s:strings)
|
|
||||||
passes_strings = passes_strings && QString::fromStdString(mPosts[i].mMeta.mMsgName).contains(s,Qt::CaseInsensitive);
|
|
||||||
|
|
||||||
if(strings.empty())
|
|
||||||
passes_strings = true;
|
|
||||||
|
|
||||||
if(passes_strings && (!only_unread || (IS_MSG_UNREAD(mPosts[i].mMeta.mMsgStatus) || IS_MSG_NEW(mPosts[i].mMeta.mMsgStatus))))
|
|
||||||
mFilteredPosts.push_back(i);
|
|
||||||
}
|
|
||||||
|
|
||||||
count = mFilteredPosts.size();
|
count = mFilteredPosts.size();
|
||||||
|
|
||||||
@ -292,7 +205,7 @@ int RsGxsChannelPostsModel::rowCount(const QModelIndex& parent) const
|
|||||||
return mFilteredPosts.size();
|
return mFilteredPosts.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
RsErr() << __PRETTY_FUNCTION__ << " rowCount cannot figure out the porper number of rows." << std::endl;
|
RsErr() << __PRETTY_FUNCTION__ << " rowCount cannot figure out the proper number of rows." ;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -370,7 +283,7 @@ QModelIndex RsGxsChannelPostsModel::index(int row, int column, const QModelIndex
|
|||||||
|
|
||||||
quintptr ref = getChildRef(parent.internalId(),(mTreeMode == TREE_MODE_GRID)?(column + row*mColumns):row);
|
quintptr ref = getChildRef(parent.internalId(),(mTreeMode == TREE_MODE_GRID)?(column + row*mColumns):row);
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_MODEL_DATA
|
||||||
std::cerr << "index-3(" << row << "," << column << " parent=" << parent << ") : " << createIndex(row,column,ref) << std::endl;
|
std::cerr << "index-3(" << row << "," << column << " parent=" << parent << ") : " << createIndex(row,column,ref) << std::endl;
|
||||||
#endif
|
#endif
|
||||||
return createIndex(row,column,ref) ;
|
return createIndex(row,column,ref) ;
|
||||||
@ -460,7 +373,7 @@ int RsGxsChannelPostsModel::getChildrenCount(quintptr ref) const
|
|||||||
|
|
||||||
QVariant RsGxsChannelPostsModel::data(const QModelIndex &index, int role) const
|
QVariant RsGxsChannelPostsModel::data(const QModelIndex &index, int role) const
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_MODEL_DATA
|
||||||
std::cerr << "calling data(" << index << ") role=" << role << std::endl;
|
std::cerr << "calling data(" << index << ") role=" << role << std::endl;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -477,13 +390,13 @@ QVariant RsGxsChannelPostsModel::data(const QModelIndex &index, int role) const
|
|||||||
quintptr ref = (index.isValid())?index.internalId():0 ;
|
quintptr ref = (index.isValid())?index.internalId():0 ;
|
||||||
uint32_t entry = 0;
|
uint32_t entry = 0;
|
||||||
|
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_MODEL_DATA
|
||||||
std::cerr << "data(" << index << ")" ;
|
std::cerr << "data(" << index << ")" ;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if(!ref)
|
if(!ref)
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_MODEL_DATA
|
||||||
std::cerr << " [empty]" << std::endl;
|
std::cerr << " [empty]" << std::endl;
|
||||||
#endif
|
#endif
|
||||||
return QVariant() ;
|
return QVariant() ;
|
||||||
@ -491,7 +404,7 @@ QVariant RsGxsChannelPostsModel::data(const QModelIndex &index, int role) const
|
|||||||
|
|
||||||
if(!convertRefPointerToTabEntry(ref,entry) || entry >= mFilteredPosts.size())
|
if(!convertRefPointerToTabEntry(ref,entry) || entry >= mFilteredPosts.size())
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_CHANNEL_MODEL
|
#ifdef DEBUG_CHANNEL_MODEL_DATA
|
||||||
std::cerr << "Bad pointer: " << (void*)ref << std::endl;
|
std::cerr << "Bad pointer: " << (void*)ref << std::endl;
|
||||||
#endif
|
#endif
|
||||||
return QVariant() ;
|
return QVariant() ;
|
||||||
@ -564,6 +477,79 @@ bool operator<(const RsGxsChannelPost& p1,const RsGxsChannelPost& p2)
|
|||||||
return p1.mMeta.mPublishTs > p2.mMeta.mPublishTs;
|
return p1.mMeta.mPublishTs > p2.mMeta.mPublishTs;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RsGxsChannelPostsModel::updateSinglePost(const RsGxsChannelPost& post,std::set<RsGxsFile>& added_files,std::set<RsGxsFile>& removed_files)
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_CHANNEL_MODEL
|
||||||
|
RsDbg() << "updating single post for group id=" << currentGroupId() << " and msg id=" << post.mMeta.mMsgId ;
|
||||||
|
#endif
|
||||||
|
added_files.clear();
|
||||||
|
removed_files.clear();
|
||||||
|
|
||||||
|
emit layoutAboutToBeChanged();
|
||||||
|
|
||||||
|
// linear search. Not good at all, but normally this is just for a single post.
|
||||||
|
|
||||||
|
bool found = false;
|
||||||
|
const auto& new_post_meta(post.mMeta);
|
||||||
|
|
||||||
|
for(uint32_t j=0;j<mPosts.size();++j)
|
||||||
|
if(new_post_meta.mMsgId == mPosts[j].mMeta.mMsgId) // same post updated
|
||||||
|
{
|
||||||
|
added_files.insert(post.mFiles.begin(),post.mFiles.end());
|
||||||
|
removed_files.insert(mPosts[j].mFiles.begin(),mPosts[j].mFiles.end());
|
||||||
|
|
||||||
|
auto save_ucc = mPosts[j].mUnreadCommentCount;
|
||||||
|
auto save_cc = mPosts[j].mCommentCount;
|
||||||
|
|
||||||
|
mPosts[j] = post;
|
||||||
|
|
||||||
|
mPosts[j].mUnreadCommentCount = save_ucc;
|
||||||
|
mPosts[j].mCommentCount = save_cc;
|
||||||
|
|
||||||
|
#ifdef DEBUG_CHANNEL_MODEL
|
||||||
|
RsDbg() << " post is an updated existing post." ;
|
||||||
|
#endif
|
||||||
|
found=true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else if( (new_post_meta.mOrigMsgId == mPosts[j].mMeta.mOrigMsgId || new_post_meta.mOrigMsgId == mPosts[j].mMeta.mMsgId)
|
||||||
|
&& mPosts[j].mMeta.mPublishTs < new_post_meta.mPublishTs) // new post version
|
||||||
|
{
|
||||||
|
added_files.insert(post.mFiles.begin(),post.mFiles.end());
|
||||||
|
removed_files.insert(mPosts[j].mFiles.begin(),mPosts[j].mFiles.end());
|
||||||
|
|
||||||
|
auto old_post_id = mPosts[j].mMeta.mMsgId;
|
||||||
|
auto save_ucc = mPosts[j].mUnreadCommentCount;
|
||||||
|
auto save_cc = mPosts[j].mCommentCount;
|
||||||
|
|
||||||
|
mPosts[j] = post;
|
||||||
|
|
||||||
|
mPosts[j].mCommentCount += save_cc;
|
||||||
|
mPosts[j].mUnreadCommentCount += save_ucc;
|
||||||
|
mPosts[j].mOlderVersions.insert(old_post_id);
|
||||||
|
#ifdef DEBUG_CHANNEL_MODEL
|
||||||
|
RsDbg() << " post is an new version of an existing post." ;
|
||||||
|
#endif
|
||||||
|
found=true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!found)
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_CHANNEL_MODEL
|
||||||
|
RsDbg() << " post is an new post.";
|
||||||
|
#endif
|
||||||
|
added_files.insert(post.mFiles.begin(),post.mFiles.end());
|
||||||
|
mPosts.push_back(post);
|
||||||
|
}
|
||||||
|
std::sort(mPosts.begin(),mPosts.end());
|
||||||
|
|
||||||
|
uint32_t count;
|
||||||
|
updateFilter(count);
|
||||||
|
|
||||||
|
triggerViewUpdate();
|
||||||
|
}
|
||||||
|
|
||||||
void RsGxsChannelPostsModel::setPosts(const RsGxsChannelGroup& group, std::vector<RsGxsChannelPost>& posts)
|
void RsGxsChannelPostsModel::setPosts(const RsGxsChannelGroup& group, std::vector<RsGxsChannelPost>& posts)
|
||||||
{
|
{
|
||||||
preMods();
|
preMods();
|
||||||
@ -593,6 +579,8 @@ void RsGxsChannelPostsModel::setPosts(const RsGxsChannelGroup& group, std::vecto
|
|||||||
emit channelPostsLoaded();
|
emit channelPostsLoaded();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void RsGxsChannelPostsModel::update_posts(const RsGxsGroupId& group_id)
|
void RsGxsChannelPostsModel::update_posts(const RsGxsGroupId& group_id)
|
||||||
{
|
{
|
||||||
if(group_id.isNull())
|
if(group_id.isNull())
|
||||||
@ -635,7 +623,7 @@ void RsGxsChannelPostsModel::update_posts(const RsGxsGroupId& group_id)
|
|||||||
// This shouldn't be needed normally. We need it until a background process computes the number of comments per
|
// This shouldn't be needed normally. We need it until a background process computes the number of comments per
|
||||||
// post and stores it in the service string. Since we request all data, this process isn't costing much anyway.
|
// post and stores it in the service string. Since we request all data, this process isn't costing much anyway.
|
||||||
|
|
||||||
updateCommentCounts(*posts,*comments);
|
computeCommentCounts(*posts,*comments);
|
||||||
|
|
||||||
// 2 - update the model in the UI thread.
|
// 2 - update the model in the UI thread.
|
||||||
|
|
||||||
@ -945,8 +933,28 @@ void RsGxsChannelPostsModel::setAllMsgReadStatus(bool read_status)
|
|||||||
if(!rsGxsChannels->setMessageReadStatus(p,read_status))
|
if(!rsGxsChannels->setMessageReadStatus(p,read_status))
|
||||||
RsErr() << "setAllMsgReadStatus: failed to change status of msg " << p.first << " in group " << p.second << " to status " << read_status << std::endl;
|
RsErr() << "setAllMsgReadStatus: failed to change status of msg " << p.first << " in group " << p.second << " to status " << read_status << std::endl;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 3 - update the local model data, since we don't catch the READ_STATUS_CHANGED event later, to avoid re-loading the msg.
|
||||||
|
|
||||||
|
for(uint32_t i=0;i<mPosts.size();++i)
|
||||||
|
if(read_status)
|
||||||
|
mPosts[i].mMeta.mMsgStatus &= ~(GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD | GXS_SERV::GXS_MSG_STATUS_GUI_NEW);
|
||||||
|
else
|
||||||
|
mPosts[i].mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD ;
|
||||||
|
|
||||||
|
emit dataChanged(createIndex(0,0,(void*)NULL), createIndex(rowCount()-1,mColumns-1,(void*)NULL));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RsGxsChannelPostsModel::updatePostWithNewComment(const RsGxsMessageId& msg_id)
|
||||||
|
{
|
||||||
|
for(uint32_t i=0;i<mPosts.size();++i)
|
||||||
|
if(mPosts[i].mMeta.mMsgId == msg_id)
|
||||||
|
{
|
||||||
|
++mPosts[i].mUnreadCommentCount;
|
||||||
|
emit dataChanged(createIndex(0,0,(void*)NULL), createIndex(rowCount()-1,mColumns-1,(void*)NULL)); // update everything because we don't know the index.
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
void RsGxsChannelPostsModel::setMsgReadStatus(const QModelIndex& i,bool read_status)
|
void RsGxsChannelPostsModel::setMsgReadStatus(const QModelIndex& i,bool read_status)
|
||||||
{
|
{
|
||||||
if(!i.isValid())
|
if(!i.isValid())
|
||||||
@ -961,6 +969,18 @@ void RsGxsChannelPostsModel::setMsgReadStatus(const QModelIndex& i,bool read_sta
|
|||||||
return ;
|
return ;
|
||||||
|
|
||||||
rsGxsChannels->setMessageReadStatus(RsGxsGrpMsgIdPair(mPosts[mFilteredPosts[entry]].mMeta.mGroupId,mPosts[mFilteredPosts[entry]].mMeta.mMsgId),read_status);
|
rsGxsChannels->setMessageReadStatus(RsGxsGrpMsgIdPair(mPosts[mFilteredPosts[entry]].mMeta.mGroupId,mPosts[mFilteredPosts[entry]].mMeta.mMsgId),read_status);
|
||||||
|
|
||||||
|
// Quick update to the msg itself. Normally setMsgReadStatus will launch an event,
|
||||||
|
// that we can catch to update the msg, but all the information is already here.
|
||||||
|
|
||||||
|
if(read_status)
|
||||||
|
mPosts[mFilteredPosts[entry]].mMeta.mMsgStatus &= ~(GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD | GXS_SERV::GXS_MSG_STATUS_GUI_NEW);
|
||||||
|
else
|
||||||
|
mPosts[mFilteredPosts[entry]].mMeta.mMsgStatus |= GXS_SERV::GXS_MSG_STATUS_GUI_UNREAD;
|
||||||
|
|
||||||
|
mPosts[mFilteredPosts[entry]].mUnreadCommentCount = 0;
|
||||||
|
|
||||||
|
emit dataChanged(i,i);
|
||||||
}
|
}
|
||||||
|
|
||||||
QModelIndex RsGxsChannelPostsModel::getIndexOfMessage(const RsGxsMessageId& mid) const
|
QModelIndex RsGxsChannelPostsModel::getIndexOfMessage(const RsGxsMessageId& mid) const
|
||||||
|
@ -101,6 +101,7 @@ public:
|
|||||||
SORT_MODE_CHILDREN_PUBLISH_TS = 0x01,
|
SORT_MODE_CHILDREN_PUBLISH_TS = 0x01,
|
||||||
};
|
};
|
||||||
#endif
|
#endif
|
||||||
|
static void computeCommentCounts( std::vector<RsGxsChannelPost>& posts, std::vector<RsGxsComment>& comments);
|
||||||
|
|
||||||
QModelIndex root() const{ return createIndex(0,0,(void*)NULL) ;}
|
QModelIndex root() const{ return createIndex(0,0,(void*)NULL) ;}
|
||||||
QModelIndex getIndexOfMessage(const RsGxsMessageId& mid) const;
|
QModelIndex getIndexOfMessage(const RsGxsMessageId& mid) const;
|
||||||
@ -138,8 +139,11 @@ public:
|
|||||||
|
|
||||||
void setMsgReadStatus(const QModelIndex &i, bool read_status);
|
void setMsgReadStatus(const QModelIndex &i, bool read_status);
|
||||||
void setAllMsgReadStatus(bool read_status);
|
void setAllMsgReadStatus(bool read_status);
|
||||||
|
void updatePostWithNewComment(const RsGxsMessageId& msg_id);
|
||||||
|
|
||||||
void setFilter(const QStringList &strings, bool only_unread,uint32_t &count) ;
|
void setFilter(const QStringList &strings, bool only_unread,uint32_t &count) ;
|
||||||
|
bool postPassesFilter(const RsGxsChannelPost &post, const QStringList &strings, bool only_unread) const;
|
||||||
|
void updateFilter(uint32_t& count);
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
void setAuthorOpinion(const QModelIndex& indx,RsOpinion op);
|
void setAuthorOpinion(const QModelIndex& indx,RsOpinion op);
|
||||||
@ -215,6 +219,8 @@ private:
|
|||||||
|
|
||||||
void update_posts(const RsGxsGroupId& group_id);
|
void update_posts(const RsGxsGroupId& group_id);
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
void setForumMessageSummary(const std::vector<RsGxsForumMsg>& messages);
|
void setForumMessageSummary(const std::vector<RsGxsForumMsg>& messages);
|
||||||
#endif
|
#endif
|
||||||
@ -232,8 +238,13 @@ private:
|
|||||||
void old_createPostsArray(std::vector<RsGxsChannelPost> &posts);
|
void old_createPostsArray(std::vector<RsGxsChannelPost> &posts);
|
||||||
void createPostsArray(std::vector<RsGxsChannelPost>& posts);
|
void createPostsArray(std::vector<RsGxsChannelPost>& posts);
|
||||||
void setPosts(const RsGxsChannelGroup& group, std::vector<RsGxsChannelPost> &posts);
|
void setPosts(const RsGxsChannelGroup& group, std::vector<RsGxsChannelPost> &posts);
|
||||||
void initEmptyHierarchy();
|
public:
|
||||||
void handleEvent_main_thread(std::shared_ptr<const RsEvent> event);
|
void updateSinglePost(const RsGxsChannelPost& post, std::set<RsGxsFile>& added_files, std::set<RsGxsFile>& removed_files);
|
||||||
|
private:
|
||||||
|
void initEmptyHierarchy();
|
||||||
|
|
||||||
|
QStringList mFilteredStrings;
|
||||||
|
bool mFilterUnread;
|
||||||
|
|
||||||
std::vector<int> mFilteredPosts; // stores the list of displayes indices due to filtering.
|
std::vector<int> mFilteredPosts; // stores the list of displayes indices due to filtering.
|
||||||
std::vector<RsGxsChannelPost> mPosts ; // store the list of posts updated from rsForums.
|
std::vector<RsGxsChannelPost> mPosts ; // store the list of posts updated from rsForums.
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -104,11 +104,11 @@ public:
|
|||||||
|
|
||||||
/* GxsMessageFrameWidget */
|
/* GxsMessageFrameWidget */
|
||||||
virtual QIcon groupIcon() override;
|
virtual QIcon groupIcon() override;
|
||||||
virtual void groupIdChanged() override { updateDisplay(true); }
|
virtual void groupIdChanged() override { updateDisplay(true,true); }
|
||||||
virtual QString groupName(bool) override;
|
virtual QString groupName(bool) override;
|
||||||
virtual bool navigate(const RsGxsMessageId&) override;
|
virtual bool navigate(const RsGxsMessageId&) override;
|
||||||
|
|
||||||
void updateDisplay(bool complete);
|
void updateDisplay(bool update_group_data, bool update_posts);
|
||||||
|
|
||||||
#ifdef TODO
|
#ifdef TODO
|
||||||
/* FeedHolder */
|
/* FeedHolder */
|
||||||
@ -141,7 +141,7 @@ protected:
|
|||||||
|
|
||||||
private slots:
|
private slots:
|
||||||
void showPostDetails();
|
void showPostDetails();
|
||||||
void updateGroupData();
|
void updateData(bool update_group_data,bool update_posts);
|
||||||
void download();
|
void download();
|
||||||
void updateDAll_PB();
|
void updateDAll_PB();
|
||||||
void createMsg();
|
void createMsg();
|
||||||
|
@ -387,12 +387,11 @@ void RsMessageModel::setFilter(FilterType filter_type, const QStringList& string
|
|||||||
std::cerr << std::endl;
|
std::cerr << std::endl;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
preMods();
|
|
||||||
|
|
||||||
mFilterType = filter_type;
|
mFilterType = filter_type;
|
||||||
mFilterStrings = strings;
|
mFilterStrings = strings;
|
||||||
|
|
||||||
postMods();
|
if(rowCount() > 0)
|
||||||
|
emit dataChanged(createIndex(0,0),createIndex(rowCount()-1,RsMessageModel::columnCount()-1));
|
||||||
}
|
}
|
||||||
|
|
||||||
QVariant RsMessageModel::toolTipRole(const Rs::Msgs::MsgInfoSummary& fmpe,int column) const
|
QVariant RsMessageModel::toolTipRole(const Rs::Msgs::MsgInfoSummary& fmpe,int column) const
|
||||||
|
@ -23,6 +23,7 @@
|
|||||||
#include "gui/notifyqt.h"
|
#include "gui/notifyqt.h"
|
||||||
#include "gui/MainWindow.h"
|
#include "gui/MainWindow.h"
|
||||||
#include "util/qtthreadsutils.h"
|
#include "util/qtthreadsutils.h"
|
||||||
|
#include "gui/settings/rsharesettings.h"
|
||||||
|
|
||||||
#include "gui/msgs/MessageInterface.h"
|
#include "gui/msgs/MessageInterface.h"
|
||||||
|
|
||||||
@ -91,8 +92,18 @@ void MessageUserNotify::handleEvent_main_thread(std::shared_ptr<const RsEvent> e
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::set<RsMailMessageId>::const_iterator it;
|
||||||
|
|
||||||
switch (fe->mMailStatusEventCode) {
|
switch (fe->mMailStatusEventCode) {
|
||||||
case RsMailStatusEventCode::NEW_MESSAGE:
|
case RsMailStatusEventCode::NEW_MESSAGE:
|
||||||
|
if (Settings->getNotifyFlags() & RS_POPUP_MSG)
|
||||||
|
for (it = fe->mChangedMsgIds.begin(); it != fe->mChangedMsgIds.end(); ++it) {
|
||||||
|
MessageInfo msgInfo;
|
||||||
|
if (rsMail->getMessage(*it, msgInfo)) {
|
||||||
|
NotifyQt::getInstance()->addToaster(RS_POPUP_MSG, msgInfo.msgId.c_str(), msgInfo.title.c_str(), msgInfo.msg.c_str() );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
case RsMailStatusEventCode::MESSAGE_CHANGED:
|
case RsMailStatusEventCode::MESSAGE_CHANGED:
|
||||||
case RsMailStatusEventCode::MESSAGE_REMOVED:
|
case RsMailStatusEventCode::MESSAGE_REMOVED:
|
||||||
updateIcon();
|
updateIcon();
|
||||||
|
@ -1162,3 +1162,82 @@ void NotifyQt::runningTick()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void NotifyQt::addToaster(uint notifyFlags, const std::string& id, const std::string& title, const std::string& msg)
|
||||||
|
{
|
||||||
|
uint pos = 0;
|
||||||
|
|
||||||
|
while (notifyFlags) {
|
||||||
|
uint type = notifyFlags & (1 << pos);
|
||||||
|
notifyFlags &= ~(1 << pos);
|
||||||
|
++pos;
|
||||||
|
|
||||||
|
ToasterItem *toaster = NULL;
|
||||||
|
|
||||||
|
switch(type)
|
||||||
|
{
|
||||||
|
case RS_POPUP_ENCRYPTED_MSG:
|
||||||
|
SoundManager::play(SOUND_MESSAGE_ARRIVED);
|
||||||
|
|
||||||
|
toaster = new ToasterItem(new MessageToaster(std::string(), tr("Unknown title"), QString("[%1]").arg(tr("Encrypted message"))));
|
||||||
|
break;
|
||||||
|
case RS_POPUP_MSG:
|
||||||
|
SoundManager::play(SOUND_MESSAGE_ARRIVED);
|
||||||
|
|
||||||
|
toaster = new ToasterItem(new MessageToaster(id, QString::fromUtf8(title.c_str()), QString::fromUtf8(msg.c_str())));
|
||||||
|
break;
|
||||||
|
case RS_POPUP_CONNECT:
|
||||||
|
SoundManager::play(SOUND_USER_ONLINE);
|
||||||
|
|
||||||
|
toaster = new ToasterItem(new OnlineToaster(RsPeerId(id)));
|
||||||
|
break;
|
||||||
|
case RS_POPUP_DOWNLOAD:
|
||||||
|
SoundManager::play(SOUND_DOWNLOAD_COMPLETE);
|
||||||
|
|
||||||
|
toaster = new ToasterItem(new DownloadToaster(RsFileHash(id), QString::fromUtf8(title.c_str())));
|
||||||
|
break;
|
||||||
|
case RS_POPUP_CHAT:
|
||||||
|
toaster = new ToasterItem(new ChatToaster(RsPeerId(id), QString::fromUtf8(msg.c_str())));
|
||||||
|
break;
|
||||||
|
case RS_POPUP_GROUPCHAT:
|
||||||
|
#ifdef RS_DIRECT_CHAT
|
||||||
|
toaster = new ToasterItem(new GroupChatToaster(RsPeerId(id), QString::fromUtf8(msg.c_str())));
|
||||||
|
#endif // RS_DIRECT_CHAT
|
||||||
|
break;
|
||||||
|
case RS_POPUP_CHATLOBBY:
|
||||||
|
{
|
||||||
|
ChatId chat_id(id);
|
||||||
|
|
||||||
|
ChatDialog *chatDialog = ChatDialog::getChat(chat_id);
|
||||||
|
ChatWidget *chatWidget;
|
||||||
|
if (chatDialog && (chatWidget = chatDialog->getChatWidget()) && chatWidget->isActive()) {
|
||||||
|
// do not show when active
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
ChatLobbyDialog *chatLobbyDialog = dynamic_cast<ChatLobbyDialog*>(chatDialog);
|
||||||
|
|
||||||
|
RsGxsId sender(title);
|
||||||
|
if (!chatLobbyDialog || chatLobbyDialog->isParticipantMuted(sender))
|
||||||
|
break; // participant is muted
|
||||||
|
|
||||||
|
toaster = new ToasterItem(new ChatLobbyToaster(chat_id.toLobbyId(), sender, QString::fromUtf8(msg.c_str())));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case RS_POPUP_CONNECT_ATTEMPT:
|
||||||
|
// id = gpgid
|
||||||
|
// title = ssl name
|
||||||
|
// msg = peer id
|
||||||
|
toaster = new ToasterItem(new FriendRequestToaster(RsPgpId(id), QString::fromUtf8(title.c_str()), RsPeerId(msg)));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (toaster) {
|
||||||
|
/* init attributes */
|
||||||
|
toaster->widget->setWindowFlags(Qt::ToolTip | Qt::WindowStaysOnTopHint);
|
||||||
|
|
||||||
|
/* add toaster to waiting list */
|
||||||
|
//QMutexLocker lock(&waitingToasterMutex);
|
||||||
|
waitingToasterList.push_back(toaster);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -95,6 +95,7 @@ class NotifyQt: public QObject, public NotifyClient
|
|||||||
void testToaster(ToasterNotify *toasterNotify, /*RshareSettings::enumToasterPosition*/ int position, QPoint margin);
|
void testToaster(ToasterNotify *toasterNotify, /*RshareSettings::enumToasterPosition*/ int position, QPoint margin);
|
||||||
void testToaster(QString tag, ToasterNotify *toasterNotify, /*RshareSettings::enumToasterPosition*/ int position, QPoint margin);
|
void testToaster(QString tag, ToasterNotify *toasterNotify, /*RshareSettings::enumToasterPosition*/ int position, QPoint margin);
|
||||||
|
|
||||||
|
void addToaster(uint notifyFlags, const std::string& id, const std::string& title, const std::string& msg);
|
||||||
void notifySettingsChanged();
|
void notifySettingsChanged();
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
|
@ -21,6 +21,7 @@
|
|||||||
#include "ServerPage.h"
|
#include "ServerPage.h"
|
||||||
|
|
||||||
#include <gui/notifyqt.h>
|
#include <gui/notifyqt.h>
|
||||||
|
#include "gui/MainWindow.h"
|
||||||
#include "rshare.h"
|
#include "rshare.h"
|
||||||
#include "rsharesettings.h"
|
#include "rsharesettings.h"
|
||||||
#include "util/i2pcommon.h"
|
#include "util/i2pcommon.h"
|
||||||
@ -1366,6 +1367,7 @@ void ServerPage::saveAddressesHiddenNode()
|
|||||||
|
|
||||||
void ServerPage::updateOutProxyIndicator()
|
void ServerPage::updateOutProxyIndicator()
|
||||||
{
|
{
|
||||||
|
MainWindow::getInstance()->torstatusReset();
|
||||||
QTcpSocket socket ;
|
QTcpSocket socket ;
|
||||||
|
|
||||||
// Tor
|
// Tor
|
||||||
@ -1382,22 +1384,39 @@ void ServerPage::updateOutProxyIndicator()
|
|||||||
ui.iconlabel_tor_outgoing->setToolTip(tr("Tor proxy is not enabled")) ;
|
ui.iconlabel_tor_outgoing->setToolTip(tr("Tor proxy is not enabled")) ;
|
||||||
}
|
}
|
||||||
|
|
||||||
// I2P - SAM
|
if (mHiddenType == RS_HIDDEN_TYPE_I2P && mSamSettings.enable)
|
||||||
// Note: there is only "the SAM port", there is no additional proxy port!
|
|
||||||
samStatus ss;
|
|
||||||
rsAutoProxyMonitor::taskSync(autoProxyType::I2PSAM3, autoProxyTask::status, &ss);
|
|
||||||
if(ss.state == samStatus::samState::online)
|
|
||||||
{
|
{
|
||||||
socket.disconnectFromHost();
|
// I2P - SAM
|
||||||
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_OK)) ;
|
// Note: there is only "the SAM port", there is no additional proxy port!
|
||||||
ui.iconlabel_i2p_outgoing->setToolTip(tr("Proxy seems to work.")) ;
|
samStatus ss;
|
||||||
|
rsAutoProxyMonitor::taskSync(autoProxyType::I2PSAM3, autoProxyTask::status, &ss);
|
||||||
|
if(ss.state == samStatus::samState::online)
|
||||||
|
{
|
||||||
|
socket.disconnectFromHost();
|
||||||
|
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_OK)) ;
|
||||||
|
ui.iconlabel_i2p_outgoing->setToolTip(tr("Proxy seems to work.")) ;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_UNKNOWN)) ;
|
||||||
|
ui.iconlabel_i2p_outgoing->setToolTip(tr("I2P proxy is not enabled")) ;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_UNKNOWN)) ;
|
socket.connectToHost(ui.hiddenpage_proxyAddress_i2p->text(),ui.hiddenpage_proxyPort_i2p->text().toInt());
|
||||||
ui.iconlabel_i2p_outgoing->setToolTip(tr("I2P proxy is not enabled")) ;
|
if(socket.waitForConnected(500))
|
||||||
|
{
|
||||||
|
socket.disconnectFromHost();
|
||||||
|
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_OK)) ;
|
||||||
|
ui.iconlabel_i2p_outgoing->setToolTip(tr("Proxy seems to work.")) ;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ui.iconlabel_i2p_outgoing->setPixmap(FilesDefs::getPixmapFromQtResourcePath(ICON_STATUS_UNKNOWN)) ;
|
||||||
|
ui.iconlabel_i2p_outgoing->setToolTip(tr("I2P proxy is not enabled")) ;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
socket.connectToHost(ui.hiddenpage_proxyAddress_i2p_2->text(), 7656);
|
socket.connectToHost(ui.hiddenpage_proxyAddress_i2p_2->text(), 7656);
|
||||||
if(true == (mSamAccessible = socket.waitForConnected(1000)))
|
if(true == (mSamAccessible = socket.waitForConnected(1000)))
|
||||||
{
|
{
|
||||||
|
@ -168,7 +168,7 @@ void TorStatus::getTorStatus()
|
|||||||
torstatusLabel->setToolTip( text + tr("Tor proxy is not available"));
|
torstatusLabel->setToolTip( text + tr("Tor proxy is not available"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(hiddentype == RS_HIDDEN_TYPE_I2P)
|
else if(hiddentype == RS_HIDDEN_TYPE_I2P)
|
||||||
{
|
{
|
||||||
statusTor->setText("<strong>" + tr("I2P") + ":</strong>");
|
statusTor->setText("<strong>" + tr("I2P") + ":</strong>");
|
||||||
rsPeers->getProxyServer(RS_HIDDEN_TYPE_I2P, proxyaddr, proxyport, status);
|
rsPeers->getProxyServer(RS_HIDDEN_TYPE_I2P, proxyaddr, proxyport, status);
|
||||||
@ -185,6 +185,11 @@ void TorStatus::getTorStatus()
|
|||||||
torstatusLabel->setToolTip( text + tr("i2p proxy is not available"));
|
torstatusLabel->setToolTip( text + tr("i2p proxy is not available"));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
torstatusLabel->setPixmap(FilesDefs::getPixmapFromQtResourcePath(":/icons/tile_inactive_48.png").scaledToHeight(S,Qt::SmoothTransformation));
|
||||||
|
torstatusLabel->setToolTip(tr("No tor configuration"));
|
||||||
|
}
|
||||||
_updated = true;
|
_updated = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -21,7 +21,11 @@
|
|||||||
#include "MessageToaster.h"
|
#include "MessageToaster.h"
|
||||||
#include "../MainWindow.h"
|
#include "../MainWindow.h"
|
||||||
|
|
||||||
|
#include <retroshare/rsmsgs.h>
|
||||||
#include <retroshare/rspeers.h>
|
#include <retroshare/rspeers.h>
|
||||||
|
#include <retroshare/rsidentity.h>
|
||||||
|
|
||||||
|
#include "gui/msgs/MessageInterface.h"
|
||||||
|
|
||||||
MessageToaster::MessageToaster(const std::string &peerId, const QString &title, const QString &message) : QWidget(NULL)
|
MessageToaster::MessageToaster(const std::string &peerId, const QString &title, const QString &message) : QWidget(NULL)
|
||||||
{
|
{
|
||||||
@ -39,8 +43,24 @@ MessageToaster::MessageToaster(const std::string &peerId, const QString &title,
|
|||||||
ui.textLabel->setText(message);
|
ui.textLabel->setText(message);
|
||||||
ui.textLabel->setToolTip(message);
|
ui.textLabel->setToolTip(message);
|
||||||
|
|
||||||
std::string name = (!RsPeerId(peerId).isNull())? (rsPeers->getPeerName(RsPeerId(peerId))): (rsPeers->getGPGName(RsPgpId(peerId))) ;
|
MessageInfo mi;
|
||||||
ui.toasterLabel->setText(ui.toasterLabel->text() + " " + QString::fromUtf8(name.c_str()));
|
|
||||||
|
if (!rsMail->getMessage(peerId, mi))
|
||||||
|
return;
|
||||||
|
|
||||||
|
QString srcName;
|
||||||
|
|
||||||
|
if(mi.msgflags & RS_MSG_DISTANT)
|
||||||
|
{
|
||||||
|
RsIdentityDetails details ;
|
||||||
|
rsIdentity->getIdDetails(mi.from.toGxsId(), details) ;
|
||||||
|
|
||||||
|
srcName = QString::fromUtf8(details.mNickname.c_str());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
srcName = QString::fromUtf8(rsPeers->getPeerName(mi.from.toRsPeerId()).c_str());
|
||||||
|
|
||||||
|
ui.toasterLabel->setText(ui.toasterLabel->text() + " " + srcName);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MessageToaster::openmessageClicked()
|
void MessageToaster::openmessageClicked()
|
||||||
|
1
retroshare-webui
Submodule
1
retroshare-webui
Submodule
@ -0,0 +1 @@
|
|||||||
|
Subproject commit 5cc37b3e5ad6b64b247e9d2066a9b6c8acae67ce
|
Loading…
x
Reference in New Issue
Block a user