2012-01-17 15:36:36 -05:00
/****************************************************************
*
* RetroShare is distributed under the following license :
*
* Copyright ( C ) 2011 , RetroShare Team
*
* This program is free software ; you can redistribute it and / or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation ; either version 2
* of the License , or ( at your option ) any later version .
*
* This program is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU General Public License for more details .
*
* You should have received a copy of the GNU General Public License
* along with this program ; if not , write to the Free Software
* Foundation , Inc . , 51 Franklin Street , Fifth Floor ,
* Boston , MA 02110 - 1301 , USA .
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
# include <QMessageBox>
2012-01-27 09:49:48 -05:00
# include <QCloseEvent>
2012-01-17 15:36:36 -05:00
# include "ChatDialog.h"
# include "gui/common/PeerDefs.h"
# include "PopupChatDialog.h"
2013-04-16 17:13:42 -04:00
# include "PopupDistantChatDialog.h"
2012-01-17 15:36:36 -05:00
# include "ChatLobbyDialog.h"
# include "PopupChatWindow.h"
# include "gui/settings/rsharesettings.h"
2012-01-22 17:58:23 -05:00
# include "gui/SoundManager.h"
2012-01-17 15:36:36 -05:00
# include <retroshare/rsiface.h>
# include <retroshare/rsnotify.h>
# include <retroshare/rspeers.h>
2014-03-17 16:56:06 -04:00
static std : : map < RsPeerId , ChatDialog * > chatDialogs ;
2012-01-17 15:36:36 -05:00
2013-10-18 17:10:33 -04:00
ChatDialog : : ChatDialog ( QWidget * parent , Qt : : WindowFlags flags ) :
2012-01-17 15:36:36 -05:00
QWidget ( parent , flags )
{
2012-01-27 09:49:48 -05:00
setAttribute ( Qt : : WA_DeleteOnClose , true ) ;
2012-01-17 15:36:36 -05:00
}
ChatDialog : : ~ ChatDialog ( )
{
2014-03-17 16:56:06 -04:00
std : : map < RsPeerId , ChatDialog * > : : iterator it ;
2012-01-17 15:36:36 -05:00
if ( chatDialogs . end ( ) ! = ( it = chatDialogs . find ( getPeerId ( ) ) ) ) {
chatDialogs . erase ( it ) ;
}
}
2012-01-27 09:49:48 -05:00
void ChatDialog : : closeEvent ( QCloseEvent * event )
{
if ( ! canClose ( ) ) {
event - > ignore ( ) ;
return ;
}
emit dialogClose ( this ) ;
}
2014-03-17 16:56:06 -04:00
void ChatDialog : : init ( const RsPeerId & peerId , const QString & title )
2012-01-17 15:36:36 -05:00
{
this - > peerId = peerId ;
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
2012-01-17 19:32:15 -05:00
cw - > init ( peerId , title ) ;
2012-01-17 15:36:36 -05:00
connect ( cw , SIGNAL ( infoChanged ( ChatWidget * ) ) , this , SLOT ( chatInfoChanged ( ChatWidget * ) ) ) ;
connect ( cw , SIGNAL ( newMessage ( ChatWidget * ) ) , this , SLOT ( chatNewMessage ( ChatWidget * ) ) ) ;
}
}
2014-03-17 16:56:06 -04:00
/*static*/ ChatDialog * ChatDialog : : getExistingChat ( const RsPeerId & peerId )
2012-01-17 15:36:36 -05:00
{
2014-03-17 16:56:06 -04:00
std : : map < RsPeerId , ChatDialog * > : : iterator it ;
2012-01-17 15:36:36 -05:00
if ( chatDialogs . end ( ) ! = ( it = chatDialogs . find ( peerId ) ) ) {
/* exists already */
return it - > second ;
}
return NULL ;
}
2014-03-17 16:56:06 -04:00
/*static*/ ChatDialog * ChatDialog : : getChat ( const RsPeerId & peerId , uint chatflags )
2012-01-17 15:36:36 -05:00
{
/* see if it already exists */
ChatDialog * cd = getExistingChat ( peerId ) ;
if ( cd = = NULL ) {
2013-04-16 17:13:42 -04:00
ChatLobbyId lobby_id = 0 ;
2012-01-17 15:36:36 -05:00
if ( rsMsgs - > isLobbyId ( peerId , lobby_id ) ) {
2013-06-29 12:15:33 -04:00
// chatflags = RS_CHAT_OPEN | RS_CHAT_FOCUS; // use own flags
2012-01-17 15:36:36 -05:00
}
2013-04-16 17:13:42 -04:00
2013-04-18 17:41:13 -04:00
uint32_t distant_peer_status ;
2014-03-17 16:56:06 -04:00
RsPgpId distant_chat_pgp_id ;
2013-04-18 17:41:13 -04:00
2013-04-23 18:43:19 -04:00
if ( rsMsgs - > getDistantChatStatus ( peerId , distant_peer_status , distant_chat_pgp_id ) )
2013-04-16 17:13:42 -04:00
chatflags = RS_CHAT_OPEN | RS_CHAT_FOCUS ; // use own flags
2012-01-17 15:36:36 -05:00
if ( chatflags & RS_CHAT_OPEN ) {
if ( lobby_id ) {
std : : list < ChatLobbyInfo > linfos ;
rsMsgs - > getChatLobbyList ( linfos ) ;
for ( std : : list < ChatLobbyInfo > : : const_iterator it ( linfos . begin ( ) ) ; it ! = linfos . end ( ) ; + + it ) {
if ( ( * it ) . lobby_id = = lobby_id ) {
cd = new ChatLobbyDialog ( lobby_id ) ;
chatDialogs [ peerId ] = cd ;
cd - > init ( peerId , QString : : fromUtf8 ( ( * it ) . lobby_name . c_str ( ) ) ) ;
}
}
2013-04-18 17:41:13 -04:00
} else if ( distant_peer_status > 0 ) {
2013-04-16 17:13:42 -04:00
cd = new PopupDistantChatDialog ( ) ;
chatDialogs [ peerId ] = cd ;
2013-04-23 18:43:19 -04:00
std : : string peer_name = rsPeers - > getGPGName ( distant_chat_pgp_id ) ;
2014-03-17 16:56:06 -04:00
cd - > init ( peerId , tr ( " Talking to " ) + QString : : fromStdString ( peer_name ) + " (PGP id= " + QString : : fromStdString ( distant_chat_pgp_id . toStdString ( ) ) + " ) " ) ;
2013-04-23 18:43:19 -04:00
2012-01-17 15:36:36 -05:00
} else {
RsPeerDetails sslDetails ;
if ( rsPeers - > getPeerDetails ( peerId , sslDetails ) ) {
2014-01-01 19:56:46 -05:00
cd = new PopupChatDialog ( ) ;
2012-01-17 15:36:36 -05:00
chatDialogs [ peerId ] = cd ;
cd - > init ( peerId , PeerDefs : : nameWithLocation ( sslDetails ) ) ;
}
}
}
}
if ( cd = = NULL ) {
return NULL ;
}
cd - > insertChatMsgs ( ) ;
cd - > showDialog ( chatflags ) ;
return cd ;
}
/*static*/ void ChatDialog : : cleanupChat ( )
{
PopupChatWindow : : cleanup ( ) ;
/* ChatDialog destuctor removes the entry from the map */
std : : list < ChatDialog * > list ;
2014-03-17 16:56:06 -04:00
std : : map < RsPeerId , ChatDialog * > : : iterator it ;
2012-01-17 15:36:36 -05:00
for ( it = chatDialogs . begin ( ) ; it ! = chatDialogs . end ( ) ; it + + ) {
if ( it - > second ) {
list . push_back ( it - > second ) ;
}
}
chatDialogs . clear ( ) ;
std : : list < ChatDialog * > : : iterator it1 ;
for ( it1 = list . begin ( ) ; it1 ! = list . end ( ) ; it1 + + ) {
delete ( * it1 ) ;
}
}
/*static*/ void ChatDialog : : chatChanged ( int list , int type )
{
if ( list = = NOTIFY_LIST_PRIVATE_INCOMING_CHAT & & type = = NOTIFY_TYPE_ADD ) {
2012-01-22 17:58:23 -05:00
// play sound when recv a message
2012-10-21 17:38:55 -04:00
soundManager - > play ( SOUND_NEW_CHAT_MESSAGE ) ;
2012-01-22 17:58:23 -05:00
2014-03-17 16:56:06 -04:00
std : : list < RsPeerId > ids ;
2012-01-17 15:36:36 -05:00
if ( rsMsgs - > getPrivateChatQueueIds ( true , ids ) ) {
uint chatflags = Settings - > getChatFlags ( ) ;
2014-03-17 16:56:06 -04:00
std : : list < RsPeerId > : : iterator id ;
2012-01-17 15:36:36 -05:00
for ( id = ids . begin ( ) ; id ! = ids . end ( ) ; id + + ) {
ChatDialog * cd = getChat ( * id , chatflags ) ;
if ( cd ) {
cd - > insertChatMsgs ( ) ;
}
}
}
}
/* now notify all open priavate chat windows */
2014-03-17 16:56:06 -04:00
std : : map < RsPeerId , ChatDialog * > : : iterator it ;
2012-01-17 15:36:36 -05:00
for ( it = chatDialogs . begin ( ) ; it ! = chatDialogs . end ( ) ; it + + ) {
if ( it - > second ) {
it - > second - > onChatChanged ( list , type ) ;
}
}
}
2014-03-17 16:56:06 -04:00
/*static*/ void ChatDialog : : closeChat ( const RsPeerId & peerId )
2012-01-17 15:36:36 -05:00
{
ChatDialog * chatDialog = getExistingChat ( peerId ) ;
if ( chatDialog ) {
delete ( chatDialog ) ;
}
}
2014-03-17 16:56:06 -04:00
/*static*/ void ChatDialog : : chatFriend ( const RsPeerId & peerId , const bool forceFocus )
2012-01-17 15:36:36 -05:00
{
2014-03-17 16:56:06 -04:00
if ( peerId . isNull ( ) ) {
2012-01-17 15:36:36 -05:00
return ;
}
2014-03-17 16:56:06 -04:00
RsPgpId distant_chat_pgp_id ;
2013-06-16 10:39:44 -04:00
uint32_t distant_peer_status ;
if ( rsMsgs - > getDistantChatStatus ( peerId , distant_peer_status , distant_chat_pgp_id ) )
{
2013-06-29 12:15:33 -04:00
getChat ( peerId , forceFocus ? RS_CHAT_OPEN | RS_CHAT_FOCUS : RS_CHAT_OPEN ) ; // use own flags
2013-06-16 10:39:44 -04:00
return ;
}
2012-01-17 15:36:36 -05:00
ChatLobbyId lid ;
if ( rsMsgs - > isLobbyId ( peerId , lid ) ) {
2013-06-29 12:15:33 -04:00
getChat ( peerId , ( forceFocus ? ( RS_CHAT_OPEN | RS_CHAT_FOCUS ) : RS_CHAT_OPEN ) ) ;
2012-01-17 15:36:36 -05:00
}
RsPeerDetails detail ;
if ( ! rsPeers - > getPeerDetails ( peerId , detail ) )
return ;
if ( detail . isOnlyGPGdetail ) {
2014-03-17 16:56:06 -04:00
std : : list < RsPeerId > onlineIds ;
2012-02-22 19:09:41 -05:00
//let's get the ssl child details
2014-03-17 16:56:06 -04:00
std : : list < RsPeerId > sslIds ;
2012-01-17 15:36:36 -05:00
rsPeers - > getAssociatedSSLIds ( detail . gpg_id , sslIds ) ;
2012-02-22 19:09:41 -05:00
if ( sslIds . size ( ) = = 1 ) {
// chat with the one ssl id (online or offline)
2013-06-29 12:15:33 -04:00
getChat ( sslIds . front ( ) , forceFocus ? RS_CHAT_OPEN | RS_CHAT_FOCUS : RS_CHAT_OPEN ) ;
2012-02-22 19:09:41 -05:00
return ;
}
// more than one ssl ids available, check for online
2014-03-17 16:56:06 -04:00
for ( std : : list < RsPeerId > : : iterator it = sslIds . begin ( ) ; it ! = sslIds . end ( ) ; + + it ) {
2012-02-22 19:09:41 -05:00
if ( rsPeers - > isOnline ( * it ) ) {
onlineIds . push_back ( * it ) ;
2012-01-17 15:36:36 -05:00
}
}
2012-02-22 19:09:41 -05:00
if ( onlineIds . size ( ) = = 1 ) {
// chat with the online ssl id
2013-06-29 12:15:33 -04:00
getChat ( onlineIds . front ( ) , forceFocus ? RS_CHAT_OPEN | RS_CHAT_FOCUS : RS_CHAT_OPEN ) ;
2012-01-17 15:36:36 -05:00
return ;
}
2012-02-22 19:09:41 -05:00
// more than one ssl ids online or all offline
QMessageBox mb ( QMessageBox : : Warning , " RetroShare " , tr ( " Your friend has more than one locations. \n Please choose one of it to chat with. " ) , QMessageBox : : Ok ) ;
mb . setWindowIcon ( QIcon ( " :/images/rstray3.png " ) ) ;
mb . exec ( ) ;
2012-01-17 15:36:36 -05:00
} else {
2013-06-29 12:15:33 -04:00
getChat ( peerId , forceFocus ? RS_CHAT_OPEN | RS_CHAT_FOCUS : RS_CHAT_OPEN ) ;
2012-01-17 15:36:36 -05:00
}
}
void ChatDialog : : addToParent ( QWidget * newParent )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
cw - > addToParent ( newParent ) ;
}
}
void ChatDialog : : removeFromParent ( QWidget * oldParent )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
cw - > removeFromParent ( oldParent ) ;
}
}
bool ChatDialog : : isTyping ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
return cw - > isTyping ( ) ;
}
return false ;
}
bool ChatDialog : : hasNewMessages ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
return cw - > hasNewMessages ( ) ;
}
return false ;
}
2014-03-17 16:56:06 -04:00
QString ChatDialog : : getPeerName ( const RsPeerId & id ) const
2013-06-18 16:13:58 -04:00
{
return QString : : fromUtf8 ( rsPeers - > getPeerName ( id ) . c_str ( ) ) ;
}
2013-06-17 17:58:26 -04:00
void ChatDialog : : setPeerStatus ( uint32_t status )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw )
2014-03-17 16:56:06 -04:00
cw - > updateStatus ( QString : : fromStdString ( getPeerId ( ) . toStdString ( ) ) , status ) ;
2013-06-17 17:58:26 -04:00
}
2012-01-17 15:36:36 -05:00
int ChatDialog : : getPeerStatus ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
return cw - > getPeerStatus ( ) ;
}
return 0 ;
}
QString ChatDialog : : getTitle ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
2012-01-17 19:32:15 -05:00
return cw - > getTitle ( ) ;
2012-01-17 15:36:36 -05:00
}
return " " ;
}
void ChatDialog : : focusDialog ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
cw - > focusDialog ( ) ;
}
}
bool ChatDialog : : setStyle ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
return cw - > setStyle ( ) ;
}
return false ;
}
const RSStyle * ChatDialog : : getStyle ( )
{
ChatWidget * cw = getChatWidget ( ) ;
if ( cw ) {
return cw - > getStyle ( ) ;
}
return NULL ;
}
void ChatDialog : : chatInfoChanged ( ChatWidget * )
{
emit infoChanged ( this ) ;
}
void ChatDialog : : chatNewMessage ( ChatWidget * )
{
emit newMessage ( this ) ;
}
void ChatDialog : : insertChatMsgs ( )
{
2014-03-17 16:56:06 -04:00
RsPeerId peerId = getPeerId ( ) ;
2012-01-17 15:36:36 -05:00
std : : list < ChatInfo > newchat ;
if ( ! rsMsgs - > getPrivateChatQueue ( true , peerId , newchat ) ) {
return ;
}
std : : list < ChatInfo > : : iterator it ;
for ( it = newchat . begin ( ) ; it ! = newchat . end ( ) ; it + + )
{
/* are they public? */
if ( ( it - > chatflags & RS_CHAT_PRIVATE ) = = 0 ) {
/* this should not happen */
continue ;
}
addIncomingChatMsg ( * it ) ;
}
rsMsgs - > clearPrivateChatQueue ( true , peerId ) ;
}