Logo Search packages:      
Sourcecode: kmess version File versions  Download package

contactlistviewitem.cpp

/***************************************************************************
                          contactlistviewitem.cpp  -  description
                             -------------------
    begin                : Fri Mar 28 2003
    copyright            : (C) 2003 by Mike K. Bennett
                           (C) 2005 by Diederik van der Boor
    email                : mkb137b@hotmail.com
                           vdboor --at-- codingdomain.com
 ***************************************************************************/

/***************************************************************************
 *                                                                         *
 *   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.                                   *
 *                                                                         *
 ***************************************************************************/

#include "contactlistviewitem.h"

#include <qobject.h>
#include <qregexp.h>
#include <qstylesheet.h>

#include <kdebug.h>
#include <kiconloader.h>
#include <kstandarddirs.h>
#include <klocale.h>

#include "kmessdebug.h"
#include "currentaccount.h"
#include "contact/contact.h"
#include "emoticonmanager.h"

#ifdef KMESSDEBUG_CONTACTLISTVIEWITEM
#define KMESSDEBUG_CONTACTLISTVIEWITEM_GENERAL
#endif


// The constructor
ContactListViewItem::ContactListViewItem(QListView *parent, Contact *contact)
 : QObject(0, "listItem"),
   KMessListViewItem( parent ),
   contact_(contact),
   onlineStatus_(0)
{
  // Do general construction
  construct();
}



// The constructor
ContactListViewItem::ContactListViewItem(QListViewItem *parent, Contact *contact)
 : QObject(0, "listItem"),
   KMessListViewItem( parent ),
   contact_(contact),
   onlineStatus_(0)
{
  // Do general construction
  construct();
}



// // Compare
// int ContactListViewItem::compare( QListViewItem *item, int col, bool asc) const
// {
// #ifdef KMESSTEST
//   ASSERT( dynamic_cast<KMessListViewItem *>(item) != 0 );
// #endif
// 
//   ContactListViewItem *that;
// 
//   int thatType = static_cast<KMessListViewItem *>(item) -> getType();
//   int result   = 0;
//   int first    = 0;
//   int second   = 0;
// 
// 
//   // Determine the sorting based on the object type.
//   if(thatType == LISTTYPE_CONTACT)
//   {
// #ifdef KMESSTEST
//     ASSERT( dynamic_cast<ContactListViewItem *>(item) != 0 );
// #endif
// 
//     that = static_cast<ContactListViewItem *>(item);
// 
//     QString thisId = this->identifier_.lower();
//     QString thatId = that->identifier_.lower();
// 
//     first  = that->onlineStatus_ - this->onlineStatus_;
//     second = thisId.localeAwareCompare( thatId );
// 
//     // Determine the sorting
//                     result = first;
//     if(result == 0) result = second;
//   }
//   else
//   {
//     // Groups
//     result = KMessListViewItem::compare(item, col, asc);
//   }
// 
// 
// 
//   // Return the correct value for the sorting algorithm.
//   if(result < 0) return -1;  // "this" is smaller then "that"
//   if(result > 0) return 1;   // "this" is greater then "that"
//   return 0;                  // "this" and "that" are equal.
// }



// Do general construction
void ContactListViewItem::construct()
{
  emoticons_ = EmoticonManager::instance();

  // Visibility depends on whether or not allowed and removed contacts are shown.
  CurrentAccount *currentAccount = CurrentAccount::instance();

  // Connect account signals
  connect(currentAccount, SIGNAL(changedViewMode()),          this, SLOT(slotUpdateVisiblity()) );
  connect(currentAccount, SIGNAL(changedDisplaySettings()),   this, SLOT(slotUpdateVisiblity()) );

  // Connect contact signals
  connect(contact_, SIGNAL(changedFriendlyName()),            this, SLOT(slotUpdateFriendlyName())            );
  connect(contact_, SIGNAL(changedStatus()),                  this, SLOT(slotUpdateStatus())                  );
  connect(contact_, SIGNAL(changedList(Contact*)),            this, SLOT(slotUpdateStatus())                  );
  connect(contact_, SIGNAL(changedPersonalMessage(Contact*)), this, SLOT(slotUpdatePersonalStatus())          );
  // changedList() is not connected to slotUpdateVisability because the "blocked" icon should also appear.

  // Call the event manually this time, to update the appearance.
  slotUpdateStatus();
  slotUpdateVisiblity();
}



// Return the contact
Contact * ContactListViewItem::getContact() const
{
  return contact_;
}



// Return the tooltip text.
QString ContactListViewItem::getToolTipText() const
{
  QString handle   = QStyleSheet::escape(contact_->getHandle());
  QString realName = QStyleSheet::escape(contact_->getTrueFriendlyName());
  QString iconPath = contact_->getContactPicturePath();

  QString tipText  = "<qt>";

  // Add icon
  if( ! iconPath.isEmpty() )
  {
    tipText += "<img src=\"" + iconPath + "\" align=left>";
  }

  // Add realname
  tipText += "&nbsp;<b>" + realName + "</b>";

  // Add status
  if( ! statusIdentifier_.isEmpty() )
  {
    tipText += " (" + statusIdentifier_ + ")";
  }

  // Add personal status on new line
  if( ! personalStatusTip_.isEmpty() )
  {
    tipText += "<br>" + personalStatusTip_;
  }

  // Add handle on new line
  tipText += "<br>" + handle;

  // Return
  tipText += "</qt>";
  return tipText;
}


// Return the type ID
int ContactListViewItem::getType() const
{
  return LISTTYPE_CONTACT;
}



// Update the friendly name
void ContactListViewItem::slotUpdateFriendlyName()
{
  updateItemText();
}


// Create the HTML code for the personal status message
void ContactListViewItem::slotUpdatePersonalStatus()
{
  QString newText;
  QString newTextTip;  // Same mesage but without emoticons in the personal status (for tooltip).

  // Personal status message
  QString statusMessage      = contact_->getPersonalMessage();
  QString statusMessageTip   = statusMessage;
  const QString &mediaType   = contact_->getCurrentMediaType();
  const QString &mediaString = contact_->getCurrentMediaString();
  QString mediaEmoticon;

  if( ! statusMessage.isEmpty()
  ||  ! mediaString.isEmpty() )
  {
    // Escape HTML add emoticons, and font color
    statusMessage    = QStyleSheet::escape(statusMessage);
    statusMessageTip = statusMessage;
    emoticons_->parseEmoticons(statusMessage, true);
    newText    += "<small><font color=\"#83838F\">" + statusMessage;
    newTextTip += "<small><font color=\"#83838F\">" + statusMessageTip;

    if( ! mediaString.isEmpty() )
    {
      // Spacing for media if needed
      if( ! statusMessage.isEmpty() )
      {
        newText    += " - ";
        newTextTip += "<br>";
      }

      // Determine icon for special media types
      if( mediaType == "Music" )
      {
        mediaEmoticon = "(8)";
      }
      else if( mediaType == "Gaming" )
      {
        mediaEmoticon = "(xx)";
      }

      // Set the icon if it's found in the emoticon theme.
      if( ! mediaEmoticon.isNull() )
      {
        const QString &replacement = emoticons_->getReplacement(mediaEmoticon, true);
        if( ! replacement.isNull() )
        {
          newText    += replacement + "&nbsp;";  // nbsp so it also works in the tooltip text.
          newTextTip += replacement + "&nbsp;";
        }
      }

      // Add final text, HTML escaped.
      newText    += QStyleSheet::escape( mediaString );
      newTextTip += QStyleSheet::escape( mediaString );
    }

    newText    += "</font></small>";
    newTextTip += "</font></small>";
  }

  // Update the text with the new message
  personalStatus_    = newText;
  personalStatusTip_ = newTextTip;
  updateItemText();
}



// Update the appearance of the contact as it's status changes
void ContactListViewItem::slotUpdateStatus()
{
  KIconLoader  *loader  = KGlobal::iconLoader();
  KStandardDirs *dirs   = KGlobal::dirs();

  QString       msnStatus = contact_->getStatus();
  QString       iconName  = "online";
  QString       iconPath;


  // Update the status identifier.
  if(contact_->isBlocked())
  {
    // Show blocked regardless of status
    statusIdentifier_ = i18n( "Blocked" );
    iconName          = "blocked";
    onlineStatus_     = ( msnStatus != "FLN" ) ? 2 : 0;
  }
  else if(msnStatus == "AWY")
  {
    statusIdentifier_ = i18n( "Away" );
    iconName          = "away";
    onlineStatus_     = 1;
  }
  else if(msnStatus == "BRB")
  {
    statusIdentifier_ = i18n( "Be Right Back" );
    iconName          = "berightback";
    onlineStatus_     = 1;
  }
  else if(msnStatus == "BSY")
  {
    statusIdentifier_ = i18n( "Busy" );
    iconName          = "busy";
    onlineStatus_     = 1;
  }
  else if( msnStatus == "HDN" )  // likely never found, just in case
  {
    statusIdentifier_ = i18n( "Invisible" );
    iconName          = "offline";
    onlineStatus_     = 2;
  }
  else if(msnStatus == "FLN")
  {
    statusIdentifier_ = "";
    iconName          = "offline";
    onlineStatus_     = 3;
  }
  else if(msnStatus == "IDL")
  {
    statusIdentifier_ = i18n( "Away - Idle" );
    iconName          = "away";
    onlineStatus_     = 1;
  }
  else if(msnStatus == "LUN")
  {
    statusIdentifier_ = i18n( "Out to Lunch" );
    iconName          = "lunch";
    onlineStatus_     = 1;
  }
  else if(msnStatus == "NLN")
  {
    statusIdentifier_ = "";
    iconName          = "online";
    onlineStatus_     = 0;
  }
  else if(msnStatus == "PHN")
  {
    statusIdentifier_ = i18n( "On the Phone" );
    iconName          = "onthephone";
    onlineStatus_     = 1;
  }
  else
  {
    statusIdentifier_ = "";
    onlineStatus_     = 2;
    kdWarning() << "Contact - '" << msnStatus << "' is not a valid status for contact " << contact_->getHandle() << "." << endl;
  }


  // Find the path to the given icon
  iconPath = dirs->findResource("data", "kmess/pics/" + iconName + ".png");
  if(iconPath.isEmpty())
  {
    // Not found?  Try KDE standard icons
    iconPath = loader->iconPath(iconName, KIcon::Small, false);
  }


  // Update vars
  iconTag_ = "<img align=left src=\"" + iconPath + "\">";


  // Set the sort text
  // FIXME: remove this if the "QListViewItem::compare" method works.
  setKey( QString::number(onlineStatus_) + " " + contact_->getFriendlyName() );

  // Ask parent to re-run the sorting algorithm
  resortParent();

  // Update our appearance.
  updateItemText();

  // Also update the visibility
  slotUpdateVisiblity();
}



// Update the visibility of the contact
void ContactListViewItem::slotUpdateVisiblity()
{
  // Visibility depends on whether or not allowed and removed contacts are shown.
  CurrentAccount *currentAccount = CurrentAccount::instance();

  if(QListViewItem::parent() == 0 && ! currentAccount->getShowContactsByGroup())
  {
    // Hide root items if contacts are shown in online/offline groups.
    setVisible(false);
  }
  else if(contact_->isOffline() && ! currentAccount->getShowOfflineContacts())
  {
    // Hide if online contacts are not shown
    setVisible(false);
  }
  else
  {
    if(contact_->isFriend())
    {
      // Friends should always be visible
      setVisible(true);
    }
    else if(contact_->isAllowed())
    {
      // Whether or not allowed contacts are visible depends on the contact setting
      setVisible( currentAccount->getShowAllowedContacts() );
    }
    else
    {
      // Whether or not removed contacts are visible depends on the contact setting
      setVisible( currentAccount->getShowRemovedContacts() );
    }
  }
}



// Update the item's text
void ContactListViewItem::updateItemText()
{
  QString newIdentifier;
  QString newText;
  QString sortText;

  // Parse the emoticons
  newIdentifier = QStyleSheet::escape( contact_->getFriendlyName() );
  emoticons_->parseEmoticons(newIdentifier, true);

  // Icon
  newText = iconTag_ + " ";

  // Reverse list?
  bool contactRemovedUser = ( ! contact_->isReverse() );

  // Start italics?
  if( contactRemovedUser )
  {
    newText += "<i>";
  }

  // friendly name
  newText += newIdentifier;

  // End italics?
  if( contactRemovedUser )
  {
    newText += "</i>";
  }

  // Add personal status message (already HTML escaped)
  if( ! personalStatus_.isEmpty() )
  {
    // NOTE: MSN Adds a "-" as seperator here, but smaller font + color makes it cleaner.
    newText += " " + personalStatus_;
  }

  // Status identifier
  if( ! statusIdentifier_.isEmpty() )
  {
    newText += "  (" + statusIdentifier_ + ")";
  }


  setText( newText );
}

#include "contactlistviewitem.moc"

Generated by  Doxygen 1.6.0   Back to index