mirror of
https://github.com/RetroShare/RetroShare.git
synced 2024-10-01 02:35:48 -04:00
added choice for default auto-download directory per channel.
git-svn-id: http://svn.code.sf.net/p/retroshare/code/trunk@6376 b45a01b8-16f6-495d-af2f-9b41ad6348cc
This commit is contained in:
parent
2986e81f7e
commit
c2fa746991
@ -61,6 +61,7 @@ class ChannelInfo
|
||||
uint32_t pngImageLen;
|
||||
|
||||
time_t lastPost;
|
||||
std::string destination_directory ;
|
||||
};
|
||||
|
||||
//! for storing a channel msgs thumbnail picture
|
||||
@ -263,6 +264,10 @@ virtual void getPubKeysAvailableGrpIds(std::list<std::string>& chanIds) = 0;
|
||||
*/
|
||||
virtual bool channelSetAutoDl(const std::string& chId, bool autoDl) = 0;
|
||||
|
||||
// sets the defautl destination directory for files downloaded in this channel.
|
||||
// Default is "" which means Downloads/
|
||||
|
||||
virtual bool channelSetDestinationDirectory(const std::string& cid,const std::string& dir) = 0 ;
|
||||
|
||||
/*!
|
||||
* get what autoDl is set to for the given channel id
|
||||
|
@ -85,7 +85,23 @@ void RsChannelReadStatus::clear()
|
||||
return;
|
||||
|
||||
}
|
||||
std::ostream& RsChannelDestDirConfigItem::print(std::ostream &out, uint16_t indent = 0)
|
||||
{
|
||||
|
||||
printRsItemBase(out, "RsChannelDestDirConfigItem", indent);
|
||||
uint16_t int_Indent = indent + 2;
|
||||
|
||||
RsDistribChildConfig::print(out, int_Indent);
|
||||
|
||||
for(uint32_t i=0;i<dest_dirs.size();++i)
|
||||
{
|
||||
printIndent(out, int_Indent); out << "channel id : " << dest_dirs[i].first ;
|
||||
out << ". Dir = " << dest_dirs[i].second << std::endl;
|
||||
}
|
||||
|
||||
printRsItemEnd(out, "RsChannelDestDirConfigItem", indent);
|
||||
return out;
|
||||
}
|
||||
std::ostream& RsChannelReadStatus::print(std::ostream &out, uint16_t indent = 0)
|
||||
{
|
||||
|
||||
@ -257,6 +273,25 @@ RsChannelMsg *RsChannelSerialiser::deserialiseMsg(void *data, uint32_t *pktsize)
|
||||
}
|
||||
|
||||
|
||||
uint32_t RsChannelSerialiser::sizeDestDirConfig(RsChannelDestDirConfigItem *item)
|
||||
{
|
||||
uint32_t s = 8; /* header */
|
||||
/* RsDistribChildConfig stuff */
|
||||
|
||||
s += 4; /* save_type */
|
||||
|
||||
/* RsChannelReadStatus stuff */
|
||||
|
||||
s += 4; /* size */
|
||||
|
||||
for(uint32_t i=0;i<item->dest_dirs.size();++i)
|
||||
{
|
||||
s += GetTlvStringSize(item->dest_dirs[i].first) ;
|
||||
s += GetTlvStringSize(item->dest_dirs[i].second) ;
|
||||
}
|
||||
|
||||
return s;
|
||||
}
|
||||
uint32_t RsChannelSerialiser::sizeReadStatus(RsChannelReadStatus *item)
|
||||
{
|
||||
uint32_t s = 8; /* header */
|
||||
@ -279,6 +314,54 @@ uint32_t RsChannelSerialiser::sizeReadStatus(RsChannelReadStatus *item)
|
||||
return s;
|
||||
}
|
||||
|
||||
/* serialise the data to the buffer */
|
||||
bool RsChannelSerialiser::serialiseDestDirConfig(RsChannelDestDirConfigItem *item, void *data, uint32_t *pktsize)
|
||||
{
|
||||
uint32_t tlvsize = sizeDestDirConfig(item);
|
||||
uint32_t offset = 0;
|
||||
|
||||
if (*pktsize < tlvsize)
|
||||
return false; /* not enough space */
|
||||
|
||||
*pktsize = tlvsize;
|
||||
|
||||
bool ok = true;
|
||||
|
||||
ok &= setRsItemHeader(data, tlvsize, item->PacketId(), tlvsize);
|
||||
#ifdef RSSERIAL_DEBUG
|
||||
std::cerr << "RsChannelSerialiser::serialiseDestDirConfig() Header: " << ok << std::endl;
|
||||
std::cerr << "RsChannelSerialiser::serialiseDestDirConfig() Size: " << tlvsize << std::endl;
|
||||
#endif
|
||||
|
||||
/* skip the header */
|
||||
offset += 8;
|
||||
|
||||
/* RsDistribMsg first */
|
||||
|
||||
ok &= setRawUInt32(data, tlvsize, &offset, item->save_type);
|
||||
#ifdef RSSERIAL_DEBUG
|
||||
std::cerr << "RsChannelSerialiser::serialiseDestDirConfig() save_type: " << ok << std::endl;
|
||||
#endif
|
||||
ok &= setRawUInt32(data, tlvsize, &offset, item->dest_dirs.size()); /* value */
|
||||
|
||||
for(uint32_t i=0;i<item->dest_dirs.size();++i)
|
||||
{
|
||||
ok &= SetTlvString(data, tlvsize, &offset, TLV_TYPE_STR_GROUPID, item->dest_dirs[i].first) ;
|
||||
ok &= SetTlvString(data, tlvsize, &offset, TLV_TYPE_STR_PATH, item->dest_dirs[i].second) ;
|
||||
}
|
||||
|
||||
#ifdef RSSERIAL_DEBUG
|
||||
std::cerr << "RsChannelSerialiser::serialiseDestDirConfig() msgReadStatus: " << ok << std::endl;
|
||||
#endif
|
||||
|
||||
if (offset != tlvsize)
|
||||
{
|
||||
ok = false;
|
||||
std::cerr << "RsChannelSerialiser::serialiseDestDirConfig() Size Error! " << std::endl;
|
||||
}
|
||||
|
||||
return ok;
|
||||
}
|
||||
/* serialise the data to the buffer */
|
||||
bool RsChannelSerialiser::serialiseReadStatus(RsChannelReadStatus *item, void *data, uint32_t *pktsize)
|
||||
{
|
||||
@ -337,7 +420,63 @@ bool RsChannelSerialiser::serialiseReadStatus(RsChannelReadStatus *item, voi
|
||||
return ok;
|
||||
}
|
||||
|
||||
RsChannelDestDirConfigItem *RsChannelSerialiser::deserialiseDestDirConfig(void *data, uint32_t *pktsize)
|
||||
{
|
||||
/* get the type and size */
|
||||
uint32_t rstype = getRsItemId(data);
|
||||
uint32_t rssize = getRsItemSize(data);
|
||||
|
||||
uint32_t offset = 0;
|
||||
|
||||
|
||||
if ((RS_PKT_VERSION_SERVICE != getRsItemVersion(rstype)) || (RS_SERVICE_TYPE_CHANNEL != getRsItemService(rstype)) || (RS_PKT_SUBTYPE_CHANNEL_DEST_DIR != getRsItemSubType(rstype)))
|
||||
return NULL; /* wrong type */
|
||||
|
||||
if (*pktsize < rssize) /* check size */
|
||||
return NULL; /* not enough data */
|
||||
|
||||
/* set the packet length */
|
||||
*pktsize = rssize;
|
||||
|
||||
bool ok = true;
|
||||
|
||||
/* ready to load */
|
||||
RsChannelDestDirConfigItem *item = new RsChannelDestDirConfigItem();
|
||||
item->clear();
|
||||
|
||||
/* skip the header */
|
||||
offset += 8;
|
||||
|
||||
/* RsDistribMsg first */
|
||||
ok &= getRawUInt32(data, rssize, &offset, &(item->save_type));
|
||||
|
||||
uint32_t size ;
|
||||
ok &= getRawUInt32(data, rssize, &offset, &size) ;
|
||||
|
||||
for(uint32_t i=0;i<size;++i)
|
||||
{
|
||||
std::string chid, path ;
|
||||
|
||||
ok &= GetTlvString(data, rssize, &offset, TLV_TYPE_STR_GROUPID, chid) ;
|
||||
ok &= GetTlvString(data, rssize, &offset, TLV_TYPE_STR_PATH , path) ;
|
||||
|
||||
item->dest_dirs.push_back(std::pair<std::string,std::string>(chid,path)) ;
|
||||
}
|
||||
|
||||
if(offset != rssize)
|
||||
{
|
||||
ok = false;
|
||||
std::cerr << "RsChannelSerialiser::deserialiseDestDirConfig() Size Error! " << std::endl;
|
||||
}
|
||||
|
||||
if (!ok)
|
||||
{
|
||||
delete item;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return item;
|
||||
}
|
||||
|
||||
RsChannelReadStatus *RsChannelSerialiser::deserialiseReadStatus(void *data, uint32_t *pktsize)
|
||||
{
|
||||
@ -413,6 +552,7 @@ uint32_t RsChannelSerialiser::size(RsItem *item)
|
||||
{
|
||||
RsChannelMsg* dcm;
|
||||
RsChannelReadStatus* drs;
|
||||
RsChannelDestDirConfigItem* dd;
|
||||
|
||||
if( NULL != ( dcm = dynamic_cast<RsChannelMsg*>(item)))
|
||||
{
|
||||
@ -422,6 +562,10 @@ uint32_t RsChannelSerialiser::size(RsItem *item)
|
||||
{
|
||||
return sizeReadStatus(drs);
|
||||
}
|
||||
else if(NULL != (dd = dynamic_cast<RsChannelDestDirConfigItem* >(item)))
|
||||
{
|
||||
return sizeDestDirConfig(dd);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
@ -430,6 +574,7 @@ bool RsChannelSerialiser::serialise(RsItem *item, void *data, uint32_t *pkts
|
||||
{
|
||||
RsChannelMsg* dcm;
|
||||
RsChannelReadStatus* drs;
|
||||
RsChannelDestDirConfigItem* dd;
|
||||
|
||||
if( NULL != ( dcm = dynamic_cast<RsChannelMsg*>(item)))
|
||||
{
|
||||
@ -439,12 +584,19 @@ bool RsChannelSerialiser::serialise(RsItem *item, void *data, uint32_t *pkts
|
||||
{
|
||||
return serialiseReadStatus(drs, data, pktsize);
|
||||
}
|
||||
else if(NULL != (dd = dynamic_cast<RsChannelDestDirConfigItem* >(item)))
|
||||
{
|
||||
return serialiseDestDirConfig(dd, data, pktsize);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
RsItem *RsChannelSerialiser::deserialise(void *data, uint32_t *pktsize)
|
||||
{
|
||||
if(data == NULL)
|
||||
return NULL ;
|
||||
|
||||
/* get the type and size */
|
||||
uint32_t rstype = getRsItemId(data);
|
||||
|
||||
@ -460,6 +612,8 @@ RsItem *RsChannelSerialiser::deserialise(void *data, uint32_t *pktsize)
|
||||
return deserialiseMsg(data, pktsize);
|
||||
case RS_PKT_SUBTYPE_CHANNEL_READ_STATUS:
|
||||
return deserialiseReadStatus(data, pktsize);
|
||||
case RS_PKT_SUBTYPE_CHANNEL_DEST_DIR:
|
||||
return deserialiseDestDirConfig(data, pktsize);
|
||||
default:
|
||||
return NULL;
|
||||
}
|
||||
|
@ -37,6 +37,7 @@
|
||||
|
||||
const uint8_t RS_PKT_SUBTYPE_CHANNEL_MSG = 0x01;
|
||||
const uint8_t RS_PKT_SUBTYPE_CHANNEL_READ_STATUS = 0x02;
|
||||
const uint8_t RS_PKT_SUBTYPE_CHANNEL_DEST_DIR = 0x03;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
@ -85,8 +86,25 @@ public:
|
||||
/// a map which contains the read for messages within a forum
|
||||
std::map<std::string, uint32_t> msgReadStatus;
|
||||
|
||||
std::string destination_directory ;
|
||||
};
|
||||
/*!
|
||||
* This is used to store the destination directories of each channel
|
||||
*/
|
||||
class RsChannelDestDirConfigItem : public RsDistribChildConfig
|
||||
{
|
||||
public:
|
||||
RsChannelDestDirConfigItem()
|
||||
: RsDistribChildConfig(RS_SERVICE_TYPE_CHANNEL, RS_PKT_SUBTYPE_CHANNEL_DEST_DIR)
|
||||
{ return; }
|
||||
|
||||
virtual ~RsChannelDestDirConfigItem() {}
|
||||
|
||||
virtual void clear() { dest_dirs.clear() ; }
|
||||
virtual std::ostream& print(std::ostream &out, uint16_t indent);
|
||||
|
||||
std::vector<std::pair<std::string, std::string> > dest_dirs;
|
||||
};
|
||||
class RsChannelSerialiser: public RsSerialType
|
||||
{
|
||||
public:
|
||||
@ -111,6 +129,9 @@ virtual uint32_t sizeReadStatus(RsChannelReadStatus* );
|
||||
virtual bool serialiseReadStatus(RsChannelReadStatus* item, void* data, uint32_t *size);
|
||||
virtual RsChannelReadStatus *deserialiseReadStatus(void* data, uint32_t *size);
|
||||
|
||||
virtual uint32_t sizeDestDirConfig(RsChannelDestDirConfigItem* );
|
||||
virtual bool serialiseDestDirConfig(RsChannelDestDirConfigItem* item, void* data, uint32_t *size);
|
||||
virtual RsChannelDestDirConfigItem *deserialiseDestDirConfig(void* data, uint32_t *size);
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
@ -117,6 +117,7 @@ bool p3Channels::getChannelInfo(const std::string &cId, ChannelInfo &ci)
|
||||
|
||||
ci.pop = gi->sources.size();
|
||||
ci.lastPost = gi->lastPost;
|
||||
ci.destination_directory = (mDestinationDirectories.find(cId)==mDestinationDirectories.end())?"":(mDestinationDirectories[cId]) ;
|
||||
|
||||
ci.pngChanImage = gi->grpIcon.pngImageData;
|
||||
|
||||
@ -666,6 +667,16 @@ void p3Channels::getPubKeysAvailableGrpIds(std::list<std::string>& grpIds)
|
||||
|
||||
}
|
||||
|
||||
bool p3Channels::channelSetDestinationDirectory(const std::string& chId, const std::string& dest_dir)
|
||||
{
|
||||
RsStackMutex stack(distribMtx);
|
||||
|
||||
mDestinationDirectories[chId] = dest_dir ;
|
||||
IndicateConfigChanged() ;
|
||||
|
||||
return true ;
|
||||
}
|
||||
|
||||
bool p3Channels::channelSetAutoDl(const std::string& chId, bool autoDl)
|
||||
{
|
||||
|
||||
@ -988,18 +999,28 @@ void p3Channels::locked_notifyGroupChanged(GroupInfo &grp, uint32_t flags, bool
|
||||
bool p3Channels::childLoadList(std::list<RsItem* >& configSaves)
|
||||
{
|
||||
RsChannelReadStatus* drs = NULL;
|
||||
std::list<RsItem* >::iterator it;
|
||||
RsChannelDestDirConfigItem *dd = NULL ;
|
||||
|
||||
for(it = configSaves.begin(); it != configSaves.end(); it++)
|
||||
for(std::list<RsItem* >::iterator it = configSaves.begin(); it != configSaves.end(); it++)
|
||||
{
|
||||
if(NULL != (drs = dynamic_cast<RsChannelReadStatus* >(*it)))
|
||||
processChanReadStatus(drs); // don't delete, since it's used later on.
|
||||
else if(NULL != (dd = dynamic_cast<RsChannelDestDirConfigItem*>(*it)))
|
||||
{
|
||||
processChanReadStatus(drs);
|
||||
mDestinationDirectories.clear() ;
|
||||
|
||||
for(uint32_t i=0;i<dd->dest_dirs.size();++i)
|
||||
{
|
||||
mDestinationDirectories[dd->dest_dirs[i].first] = dd->dest_dirs[i].second ;
|
||||
|
||||
std::cerr << "p3Channels: setDestination directory or ChId " << dd->dest_dirs[i].first << " to " << dd->dest_dirs[i].second <<std::endl;
|
||||
}
|
||||
|
||||
delete *it ;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cerr << "p3Channels::childLoadList(): Configs items loaded were incorrect!"
|
||||
<< std::endl;
|
||||
std::cerr << "p3Channels::childLoadList(): Configs items loaded were incorrect!" << std::endl;
|
||||
|
||||
if(*it != NULL)
|
||||
delete *it;
|
||||
@ -1011,9 +1032,8 @@ bool p3Channels::childLoadList(std::list<RsItem* >& configSaves)
|
||||
|
||||
void p3Channels::processChanReadStatus(RsChannelReadStatus* drs)
|
||||
{
|
||||
// mReadStatus.push_back(drs);
|
||||
|
||||
|
||||
mReadStatus.push_back(drs);
|
||||
std::string chId = drs->channelId;
|
||||
|
||||
statMap::iterator sit = drs->msgReadStatus.find(chId);
|
||||
@ -1030,13 +1050,10 @@ void p3Channels::processChanReadStatus(RsChannelReadStatus* drs)
|
||||
mReadStatus.push_back(drs);
|
||||
|
||||
saveList.push_back(drs);
|
||||
|
||||
|
||||
}
|
||||
|
||||
std::list<RsItem *> p3Channels::childSaveList()
|
||||
{
|
||||
|
||||
std::list<RsChannelReadStatus* >::iterator lit = mReadStatus.begin();
|
||||
statMap::iterator sit, mit;
|
||||
|
||||
@ -1057,7 +1074,17 @@ std::list<RsItem *> p3Channels::childSaveList()
|
||||
}
|
||||
}
|
||||
|
||||
return saveList;
|
||||
// Make a copy of saveList and add additional items we want to save.
|
||||
//
|
||||
std::list<RsItem*> to_return = saveList ;
|
||||
RsChannelDestDirConfigItem *dd = new RsChannelDestDirConfigItem ;
|
||||
|
||||
for(std::map<std::string,std::string>::const_iterator it(mDestinationDirectories.begin());it!=mDestinationDirectories.end();++it)
|
||||
dd->dest_dirs.push_back(*it) ;
|
||||
|
||||
to_return.push_back(dd) ;
|
||||
|
||||
return to_return;
|
||||
}
|
||||
|
||||
/****************************************/
|
||||
|
@ -85,6 +85,7 @@ virtual bool channelEditInfo(const std::string &chId, ChannelInfo &ci);
|
||||
virtual void getPubKeysAvailableGrpIds(std::list<std::string>& grpIds);
|
||||
virtual bool channelSetAutoDl(const std::string& chId, bool autoDl);
|
||||
virtual bool channelGetAutoDl(const std::string& chId, bool& autoDl);
|
||||
virtual bool channelSetDestinationDirectory(const std::string& chId,const std::string& dest_dir) ;
|
||||
|
||||
/***************************************************************************************/
|
||||
/****************** Event Feedback (Overloaded form p3distrib) *************************/
|
||||
@ -123,6 +124,7 @@ void removeChannelReadStatusEntry(const std::string& cId);
|
||||
|
||||
chanStatMap mMsgReadStatus;
|
||||
statMap mChannelStatus;
|
||||
std::map<std::string,std::string> mDestinationDirectories ;
|
||||
};
|
||||
|
||||
|
||||
|
@ -21,6 +21,7 @@
|
||||
|
||||
#include <QMenu>
|
||||
#include <QTimer>
|
||||
#include <QFile>
|
||||
#include <QStandardItemModel>
|
||||
#include <QMessageBox>
|
||||
|
||||
@ -29,6 +30,8 @@
|
||||
#include <set>
|
||||
#include <map>
|
||||
|
||||
#include <retroshare/rsfiles.h>
|
||||
|
||||
#include "ChannelFeed.h"
|
||||
|
||||
#include "feeds/ChanMsgItem.h"
|
||||
@ -197,6 +200,51 @@ void ChannelFeed::channelListCustomPopupMenu( QPoint /*point*/ )
|
||||
contextMnu.addAction( shareKeyAct );
|
||||
}
|
||||
|
||||
if(ci.channelFlags & RS_DISTRIB_SUBSCRIBED)
|
||||
{
|
||||
QMenu *directoryMenu = contextMnu.addMenu(QIcon(":/images/folderopen.png"),tr("Set destination directory")) ;
|
||||
|
||||
QAction *specifyDestinationDirectoryAct = new QAction(QIcon(":/images/filefind.png"), tr("Other..."), &contextMnu);
|
||||
directoryMenu->addAction(specifyDestinationDirectoryAct);
|
||||
|
||||
// Now get the list of existing directories.
|
||||
|
||||
std::list<SharedDirInfo> dirs ;
|
||||
rsFiles->getSharedDirectories(dirs) ;
|
||||
bool found = false ;
|
||||
|
||||
for(std::list<SharedDirInfo>::const_iterator it(dirs.begin());it!=dirs.end();++it)
|
||||
{
|
||||
// check for existence of directory name
|
||||
QFile directory(QString::fromUtf8((*it).filename.c_str())) ;
|
||||
|
||||
if(!directory.exists()) continue ;
|
||||
if(!(directory.permissions() & QFile::WriteOwner)) continue ;
|
||||
|
||||
QAction *act ;
|
||||
|
||||
if(ci.destination_directory == (*it).filename)
|
||||
{
|
||||
act = new QAction(QIcon(":/images/start.png"),QString::fromUtf8((*it).virtualname.c_str()),directoryMenu) ;
|
||||
found = true ;
|
||||
}
|
||||
else
|
||||
act = new QAction(QString::fromUtf8((*it).virtualname.c_str()),directoryMenu) ;
|
||||
|
||||
act->setData(QString::fromUtf8((*it).filename.c_str())) ;
|
||||
connect(act,SIGNAL(triggered()),this,SLOT(setDestinationDirectory())) ;
|
||||
directoryMenu->addAction(act) ;
|
||||
}
|
||||
QAction *defaultDestinationDirectoryAct = new QAction(tr("[Default]"), &contextMnu);
|
||||
defaultDestinationDirectoryAct->setData(QString()) ;
|
||||
connect(defaultDestinationDirectoryAct,SIGNAL(triggered()),this,SLOT(setDestinationDirectory())) ;
|
||||
|
||||
directoryMenu->addAction(defaultDestinationDirectoryAct);
|
||||
|
||||
if(!found)
|
||||
defaultDestinationDirectoryAct->setIcon(QIcon(":/images/start.png")) ;
|
||||
}
|
||||
|
||||
if(ci.channelFlags & RS_DISTRIB_SUBSCRIBED)
|
||||
{
|
||||
contextMnu.addAction( unsubscribechannelAct );
|
||||
@ -220,6 +268,17 @@ void ChannelFeed::channelListCustomPopupMenu( QPoint /*point*/ )
|
||||
|
||||
contextMnu.exec(QCursor::pos());
|
||||
}
|
||||
void ChannelFeed::setDestinationDirectory()
|
||||
{
|
||||
ChannelInfo ci;
|
||||
if (!rsChannels->getChannelInfo(mChannelId, ci))
|
||||
return;
|
||||
|
||||
std::string dest_dir(qobject_cast<QAction*>(sender())->data().toString().toUtf8().data()) ;
|
||||
|
||||
std::cerr << "Setting new directory " << dest_dir << " to channel " << mChannelId << std::endl;
|
||||
rsChannels->channelSetDestinationDirectory(mChannelId,dest_dir) ;
|
||||
}
|
||||
|
||||
void ChannelFeed::createChannel()
|
||||
{
|
||||
|
@ -79,6 +79,7 @@ private slots:
|
||||
void editChannelDetail();
|
||||
void shareKey();
|
||||
void copyChannelLink();
|
||||
void setDestinationDirectory();
|
||||
|
||||
void channelMsgReadSatusChanged(const QString& channelId, const QString& msgId, int status);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user