/***************************************************************************
                          initialview.cpp  -  description
                             -------------------
    begin                : Sun Jan 12 2003
    copyright            : (C) 2003 by Mike K. Bennett
    email                : mkb137b@hotmail.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 "initialview.h"

#include "network/msnconnection.h" // Required for the offline socket #define
#include "utils/kmessconfig.h"
#include "utils/kmessshared.h"
#include "accountsmanager.h"
#include "account.h"
#include "kmessdebug.h"

#include <QTimer>
#include <QWheelEvent>

#include <kdeversion.h>
#include <KIconEffect>
#include <KIconLoader>
#include <KLocale>
#include <KStandardDirs>

/**
 * Reconnection timeout
 *
 * This number is the time, expressed in seconds, after which a connection is attempted again
 */
#ifndef RECONNECTION_TIME
  #define RECONNECTION_TIME        30
#endif



// The constructor
InitialView::InitialView( QWidget *parent )
 : QWidget( parent )
 , Ui::InitialView()
 , isConnectingUI_( false )
 , networkStatus_( Solid::Networking::Connected )
 , reconnectionRemainingSeconds_( 30 )
 , triedConnecting_( false )
{
  // Set up the UI first
  setupUi( this );

  // Set the username box with the last used email address
  config_ = KMessConfig::instance()->getGlobalConfig( "InitialView" );
  lastUsedHandle_ = config_.readEntry( "defaultHandle", "me@hotmail.com" );

  // Enable auto completion
  handleCombobox_->setCompletionMode( KGlobalSettings::CompletionPopup );

  // Select an image to load into the main screen.. mmmm, eggs!
  QString imageName;
  QDate currentDate = QDate::currentDate();
  if( currentDate.month() == 12 && currentDate.day() > 15 )
  {
    imageName = "kmessstrip2";
  }
  else
  {
    imageName = "kmessstrip1";
  }
  // Load the chosen icon
  loader_ = KIconLoader::global();
  QPixmap icon = loader_->loadIcon( imageName, KIconLoader::User );
  kmessLogo_->setPixmap( icon );
  kmessLogo_->setMinimumSize( icon.width(), icon.height() );

  // Add the items to the initial status combo box
  QStringList states;
  states << i18n("Online")
         << i18n("Away")
         << i18n("Be Right Back")
         << i18n("Busy")
         << i18n("Out to Lunch")
         << i18n("On the Phone")
         << i18n("Invisible");
  initialStatus_->insertItems( 0, states );

  // Load the accounts list into our combo box
  const QList<Account*> accountsList = AccountsManager::instance()->getAccounts();
  foreach( Account *account, accountsList  )
  {
    addAccount( account );
  }

  // Connect the remaining signals
  connect( handleCombobox_,             SIGNAL(             editTextChanged(const QString&) ),
           this,                        SLOT  (                  updateView()               ) );
  connect( connectButton_,              SIGNAL(                     clicked()               ),
           this,                        SLOT  (          slotConnectClicked()               ) );
  connect( rememberAccountCheckBox_,    SIGNAL(                stateChanged(int)            ),
           this,                        SLOT  ( rememberAccountStateChanged(int)            ) );
  connect( forgottenPasswordLabel_,     SIGNAL(              leftClickedUrl(const QString&) ),
           this,                        SLOT  (              slotClickedUrl(const QString&) ) );
  connect( newAccountLabel_,            SIGNAL(              leftClickedUrl(const QString&) ),
           this,                        SLOT  (              slotClickedUrl(const QString&) ) );
  connect( statusLabel_,                SIGNAL(               linkActivated(const QString&) ),
           this,                        SLOT  (              slotClickedUrl(const QString&) ) );
  connect( rememberPasswordCheckBox_,   SIGNAL(                stateChanged(int)            ),
           this,                        SLOT  (rememberPasswordStateChanged(int)            ) );
  connect( rememberAutoLoginCheckBox_,  SIGNAL(                stateChanged(int)            ),
           this,                        SLOT  (       autoLoginStateChanged(int)            ) );

  // Enable tooltips for the two URL labels (they're disabled by default)
  newAccountLabel_->setUseTips( true );
  forgottenPasswordLabel_->setUseTips( true );

  // When an account is edited, reflect the changes in the accounts list
  connect( AccountsManager::instance(), SIGNAL( accountChanged(Account*,QString,QString) ),
           this,                        SLOT  ( updateView()                             ) );

  // When (if!) the passwords have been read from the user's password wallet, show them
  connect( AccountsManager::instance(), SIGNAL( passwordsReady() ),
           this,                        SLOT  (     updateView() ) );

  // Use Solid to find out whether we're connected or not, and apply the status immediately
  connect( Solid::Networking::notifier(), SIGNAL(               statusChanged(Solid::Networking::Status) ),
           this,                          SLOT  ( slotConnectionStatusChanged(Solid::Networking::Status) ) );

  // Set the initial status of the widgets
  reset();

  // Add an event filter to create a quick account chooser
  pictureLabel_->installEventFilter( this );
  installEventFilter( this );

  // Set up the timers
  reconnectionTimer_.setInterval( 1000 ); // Fire every second
  connect( &reconnectionTimer_,  SIGNAL(                 timeout() ),
            this,                SLOT  ( slotReconnectTimerEvent() ) );
  statusMessageTimer_.setSingleShot( true );
  connect( &statusMessageTimer_, SIGNAL(                 timeout() ),
            this,                SLOT  (           statusMessage() ) );
}



// The destructor
InitialView::~InitialView()
{
#ifdef KMESSDEBUG_INITIALVIEW
  kDebug() << "DESTROYED.";
#endif
}



// Add an account to the list of displayed accounts from which the user can choose
void InitialView::addAccount(Account *account)
{
  const QString &handle = account->getHandle();

  // Add account to internal list
  accounts_.insert( handle, account );

  // Add an entry for the account to the dropdown list
  handleCombobox_->addItem( handle );
  handleCombobox_->completionObject()->addItem( handle );

  // Select the account in the combobox if it's the default account.
  // Don't update the view if we're currently connecting; when connecting
  // to an account for the first time and it is not set as a guest account,
  // the account is added bringing code flow here, and updateView() will
  // clear the password field because no password is saved yet. We don't
  // want that.
  if( !isConnectingUI_ && handle == lastUsedHandle_ )
  {
    handleCombobox_->setCurrentItem( lastUsedHandle_ );
    updateView();
  }
}



//The "auto connect" checkbox changed its state
void InitialView::autoLoginStateChanged( int state )
{
  if( state == Qt::Checked )
  {
    rememberPasswordCheckBox_->setCheckState( Qt::Checked );
  }
}



// Modify an account in the list of displayed accounts from which the user can choose
void InitialView::changedAccount( QString oldName, QString newName )
{
  if( accounts_[ oldName ] == 0 )
  {
    return;
  }

  Account *account = accounts_[ oldName ];
  accounts_.remove( oldName );
  accounts_.insert( newName, account );

  // Change completion box entry
  handleCombobox_->completionObject()->removeItem( oldName );
  handleCombobox_->completionObject()->addItem( newName );

  // Remove account from qcombobox
  bool foundItem = false;
  for( int i = 0; i < handleCombobox_->count(); i++ )
  {
    if( handleCombobox_->itemText(i).toLower() == oldName.toLower() )
    {
      handleCombobox_->removeItem(i);
      foundItem = true;
      break;
    }
  }
  handleCombobox_->addItem( newName );

  if( ! foundItem )
  {
    kWarning() << "Account not found in pulldown list!";
  }
}



/**
 * @brief Automatically reconnect with a specified account [slot].
 *
 * This method starts reconnecting to an account
 *
 * @param handle  The email address of the account to reconnect
 * @param connectImmediately  Whether to wait for a little time or not before (re)connecting.
 *                            Useful when reconnecting.
 */
void InitialView::reconnect( QString handle, bool connectImmediately )
{
#ifdef KMESSDEBUG_INITIALVIEW
  kDebug() << "Reconnecting account" << handle;
#endif

  Account *account = accounts_[ handle ];
  if( account == 0 )
  {
#ifdef KMESSDEBUG_INITIALVIEW
    kDebug() << "Account not found, aborting.";
#endif

    statusMessage( i18nc( "Status message on login screen",
                          "Cannot reconnect: account not found" ),
                   10000 );
    return;
  }

  // If the account has not a saved password, we can't reconnect
  if( account->getPassword().isEmpty() || ! account->getSavePassword() )
  {
#ifdef KMESSDEBUG_INITIALVIEW
    kDebug() << "Account has no password, aborting.";
#endif

    statusMessage( i18nc( "Status message on login screen",
                          "Cannot reconnect: this account has no saved password" ),
                   10000 );
    return;
  }

  // Save the account which we will connect to, later on
  reconnectionHandle_ = handle;
  triedConnecting_ = true;

  switch( networkStatus_ )
  {
    // We're connected to the network, try connecting now
    case Solid::Networking::Connected:
#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "Network status: Connected. Scheduling reconnection.";
#endif
      if( connectImmediately )
      {
        reconnectionRemainingSeconds_ = 0;
      }
      else
      {
        reconnectionRemainingSeconds_ = 5;
      }
      break;


    // The network connection is down, wait for it to come up again
    case Solid::Networking::Unconnected:
    case Solid::Networking::Connecting:
#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "Network status: Unconnected/connecting. Waiting for a connection.";
#endif
      setEnabled( false );
      statusMessage( i18nc( "Status message on login screen",
                            "Waiting for an Internet connection to reconnect...<br /><a href='%1'>Reconnect now!</a>",
                            "kmess://reconnect/" ) );
      return;


    // The connection is being brought down, wait for it
    case Solid::Networking::Disconnecting:
#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "Network status: disconnecting. Waiting a moment for reconnection.";
#endif
      reconnectionRemainingSeconds_ = 30;
      return;


    // The network connection status is not known, wait a while before reconnecting
    case Solid::Networking::Unknown:

#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "Network status: Unknown. Scheduling reconnection.";
#endif
      // When the user starts kmess and the connection status is unknown, connect immediately.
      if( connectImmediately )
      {
        reconnectionRemainingSeconds_ = 0;
      }
      else
      {
        reconnectionRemainingSeconds_ = 30;
      }

      break;
  }

  // Start the reconnection delay timer
  setEnabled( false );
  reconnectionTimer_.start();
  slotReconnectTimerEvent();
}



/**
 * @brief Update the view when the network connection status changes
 *
 * This method receives KDE's Solid network connection status changes, and updates the view's widgets
 * to reflect it.
 *
 * @param newStatus  The new status of the network connection
 */
void InitialView::slotConnectionStatusChanged( Solid::Networking::Status newStatus )
{
  networkStatus_ = newStatus;

#ifdef KMESSDEBUG_INITIALVIEW
  QString status;
  switch( networkStatus_ )
  {
    case Solid::Networking::Unknown:       status = "Unknown";           break;
    case Solid::Networking::Unconnected:   status = "Unconnected";       break;
    case Solid::Networking::Disconnecting: status = "Disconnecting";     break;
    case Solid::Networking::Connecting:    status = "Connecting";        break;
    case Solid::Networking::Connected:     status = "Connected";         break;
    default:                               status = "Other (not known)"; break;
  }
  kDebug() << "The network connection status has changed to:" << status << ".";
#endif

  // If Solid is unable to retrieve the status, assume we're connected
  if( networkStatus_ == Solid::Networking::Connected
  ||  networkStatus_ == Solid::Networking::Unknown )
  {
    if( ! triedConnecting_ )
    {
#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "no connection attempt active, do nothing.";
#endif
      statusMessage();
      setEnabled( true );
    }
    else
    {
#ifdef KMESSDEBUG_INITIALVIEW
      kDebug() << "A connection attempt was in progress, continuing...";
#endif

      if( ! reconnectionHandle_.isEmpty() )
      {
#ifdef KMESSDEBUG_INITIALVIEW
        kDebug() << "Reconnection asked, scheduling.";
#endif
        reconnect( reconnectionHandle_ );
      }
      else
      {
        statusMessage();
        setEnabled( true );
      }
    }
  }
  else
  {
    // Solid connection is not up.
    // Reset the dialog, keep the "isConnecting" status
    setEnabled( ! triedConnecting_ );
    if( triedConnecting_ )
    {
      // Still show the same message.
      statusMessage( i18nc( "Status message on login screen",
                            "Waiting for an Internet connection to reconnect...<br /><a href='%1'>Reconnect now!</a>",
                            "kmess://reconnect/" ) );
    }
    else
    {
      statusMessage( i18nc( "Status message on login screen", "Internet connection not available" ) );
    }
  }
}



// Update the reconnection timer data
void InitialView::slotReconnectTimerEvent()
{
  if( reconnectionRemainingSeconds_ == 0 )
  {
    // Halt the timer
    reconnectionTimer_.stop();

    // Try reconnecting now
    startConnecting( reconnectionHandle_ );
    return;
  }

  statusMessage( i18ncp( "Status message on login screen",
                        "Waiting %1 second before reconnection...<br /><a href='%2'>Reconnect now!</a>",
                        "Waiting %1 seconds before reconnection...<br /><a href='%2'>Reconnect now!</a>",
                        reconnectionRemainingSeconds_,
                        "kmess://reconnect/" ),
                 5000 );

  // Reduce time for reconnect
  --reconnectionRemainingSeconds_;
}



// The account was deleted
void InitialView::deleteAccount(Account *account)
{
  // Remove account from hashmap.
  QString handle( account->getHandle() );
  accounts_.remove(handle);

  // Remove account from completionbox (extended qlistbox)
  handleCombobox_->completionObject()->removeItem( handle );

  // Remove account from qcombobox
  bool foundItem = false;
  for( int i = 0; i < handleCombobox_->count(); i++ )
  {
    if( handleCombobox_->itemText(i).toLower() == handle.toLower() )
    {
      handleCombobox_->removeItem(i);
      foundItem = true;
      break;
    }
  }

  if( ! foundItem )
  {
    kWarning() << "Account not found in pulldown list!";
  }
}



// Get the currently selected handle
QString InitialView::getSelectedHandle() const
{
  // Get handle, remove appended friendlyname if present
  QString handle( handleCombobox_->currentText() );
  if( handle.contains(' ') )
  {
    handle = handle.section(' ', 0, 0);
  }
  return handle.toLower();
}



// A profile was selected from the drop-down list, or written manually.
void InitialView::updateView()
{
  Account *account = accounts_[ getSelectedHandle() ];
  if( account != 0 )
  {
    rememberAutoLoginCheckBox_->setChecked( false );
    // User typed the full account name without using autocompletion.
    if( ! account->getSavePassword() )
    {
      rememberPasswordCheckBox_->setChecked( false );
      passwordEdit_->setText( QString() );
    }
    else
    {
      rememberPasswordCheckBox_->setChecked( true );
      passwordEdit_->setText( account->getPassword() );

      // Check the auto login checkbox
      if( account->getUseAutologin() )
      {
        rememberAutoLoginCheckBox_->setChecked( true );
      }
    }

    // Set the current account picture
    QString picturePath;

    // Check if the user wants one picture
    if( account->getShowPicture() )
    {
      picturePath = account->getPicturePath();
      pictureLabel_->setEnabled( true );
    }
    else
    {
      picturePath = KGlobal::dirs()->findResource( "data", "kmess/pics/kmesspic.png" );
      pictureLabel_->setEnabled( false );
    }

    // Check if the picture is valid
    const QPixmap picture( picturePath );
    if( ! picture.isNull() )
    {
      pictureLabel_->setPixmap( picture );
    }
    else
    {
      pictureLabel_->setPixmap( QPixmap() );
    }

    rememberAccountCheckBox_->setChecked( ! account->isGuestAccount() );
    rememberAccountCheckBox_->setDisabled( ! account->isGuestAccount() );

    // Make sure the drop down list matches the user's initial status
    int index;
    switch( account->getInitialStatus() )
    {
      case STATUS_AWAY:          index = 1; break;
      case STATUS_BE_RIGHT_BACK: index = 2; break;
      case STATUS_BUSY:          index = 3; break;
      case STATUS_INVISIBLE:     index = 6; break;
      case STATUS_ON_THE_PHONE:  index = 5; break;
      case STATUS_OUT_TO_LUNCH:  index = 4; break;
      case STATUS_ONLINE:
      default:                   index = 0; break;
    }
    initialStatus_->setCurrentIndex( index );
  }
  else
  {
    // User typed a new account name

    // Set the default picture
    KStandardDirs *dirs = KGlobal::dirs();
    QPixmap picture( dirs->findResource( "data", "kmess/pics/kmesspic.png"  ) );
    if( ! picture.isNull() )
    {
      pictureLabel_->setPixmap( picture );
    }

    // Set the default options
    rememberAccountCheckBox_  ->setDisabled( false );
    rememberPasswordCheckBox_ ->setDisabled( false );
    rememberAutoLoginCheckBox_->setDisabled( false );
    rememberAccountCheckBox_  ->setChecked ( true  );
    rememberPasswordCheckBox_ ->setChecked ( false );
    rememberAutoLoginCheckBox_->setChecked ( false );

    // Clear password again
    passwordEdit_->setText( QString::null );
    initialStatus_->setCurrentIndex( 0 );
  }

  // Put the attention back to the email field
  handleCombobox_->setFocus();
}



// The "remember account" checkbox changed its state
void InitialView::rememberAccountStateChanged( int state )
{
  if( state == Qt::Unchecked )
  {
    rememberPasswordCheckBox_ ->setCheckState( Qt::Unchecked );
    rememberAutoLoginCheckBox_->setCheckState( Qt::Unchecked );
    rememberPasswordCheckBox_ ->setEnabled( false );
    rememberAutoLoginCheckBox_->setEnabled( false );
  }
  else
  {
    rememberPasswordCheckBox_ ->setEnabled( true );
    rememberAutoLoginCheckBox_->setEnabled( true );
  }
}



// The "remember password" checkbox changed its state
void InitialView::rememberPasswordStateChanged( int state )
{
  if( state == Qt::Unchecked )
  {
    rememberAutoLoginCheckBox_->setCheckState( Qt::Unchecked );
  }
}



// Reset the view to its initial state
void InitialView::reset()
{
  // Reset internal data
  setEnabled( true );
  reconnectionHandle_ = QString();
  reconnectionTimer_.stop();
  triedConnecting_ = false;

  // Update the view again with regard to the current network status
  updateView();
  statusMessage();
  slotConnectionStatusChanged( Solid::Networking::status() );
}



// Enable or disable the widgets when we're waiting or connecting
void InitialView::setEnabled( bool isEnabled )
{
  isConnectingUI_ = ( ! isEnabled );

  initialStatusLabel_       ->setEnabled( isEnabled );
  initialStatus_            ->setEnabled( isEnabled );
  handleCombobox_           ->setEnabled( isEnabled );
  passwordEdit_             ->setEnabled( isEnabled );
  rememberAccountCheckBox_  ->setEnabled( isEnabled );
  rememberPasswordCheckBox_ ->setEnabled( isEnabled );
  rememberAutoLoginCheckBox_->setEnabled( isEnabled );

  // Switch the button's look
  if( isEnabled )
  {
    connectButton_->setText( i18nc( "Button label", "&Connect" ) );
    connectButton_->setIcon( loader_->loadIcon( "network-connect", KIconLoader::Small, KIconLoader::SizeMedium ) );
  }
  else
  {
    connectButton_->setText( i18nc( "Button label", "&Cancel" ) );
    connectButton_->setIcon( loader_->loadIcon( "network-disconnect", KIconLoader::Small, KIconLoader::SizeMedium ) );
  }
}



// The connect/disconnect button has been clicked
void InitialView::slotConnectClicked()
{
#ifdef KMESSDEBUG_INITIALVIEW
  kDebug() << "Connect button clicked," << ( isConnectingUI_ ? "disconnecting" : "connecting" );
#endif

  // The button was acting as Disconnect button when it was clicked
  if( isConnectingUI_ )
  {
    emit disconnectClicked();

    // Enable back the widgets to allow connecting again
    reset();

    return;
  }

  // The button was acting as Connect button when it was clicked

  startConnecting( getSelectedHandle() );
}



/** Start connecting with a specified account.
 *
 * It can also simply update the UI, without actually requesting a connection.
 * KMess' autologin functions connect by themselves, so this is required.
 *
 * @param handle                 Handle of the account to connect with
 * @param emitConnectionSignal   Whether to emit the connection request signal
 *                               to the KMess class or not
 */
bool InitialView::startConnecting( const QString handle, bool emitConnectionSignal )
{
  // If the reconnection timer is active, stop it.
  if( reconnectionTimer_.isActive() )
  {
    reconnectionTimer_.stop();
  }

  // Fill the UI fields with the selected handle's details, if any
  // Selecting the account this way also makes a saved account's
  // password to appear
  handleCombobox_->setEditText( handle );

  const QString password( passwordEdit_->text() );
  
  // Avoid connecting with empty fields
  if( handle.isEmpty() || password.isEmpty() )
  {
    statusMessage( i18nc( "Status message on login screen",
                          "Please enter both your email address and password" ),
                   10000 );

    // Select the box with the error
    if( handle.isEmpty() )
    {
      handleCombobox_->setFocus();
    }
    else
    {
      passwordEdit_->setFocus();
    }
    return false;
  }

  // Also don't connect if the handle is invalid
  if( ! Account::isValidEmail( handle ) )
  {
    statusMessage( i18nc( "Status message on login screen",
                          "Please enter a valid email address" ),
                   10000 );

    handleCombobox_->setFocus();
    return false;
  }

#ifdef KMESSDEBUG_INITIALVIEW
  kDebug() << "Connecting with handle:" << handle;
#endif

  // Disable the widgets to start connecting
  setEnabled( false );

  // Save the currently selected account for the next logins
  lastUsedHandle_ = handle;
  config_.writeEntry( "defaultHandle", handle );

  // Find out what status has been chosen
  Status initialStatus;
  switch( initialStatus_->currentIndex() )
  {
    case 1:  initialStatus = STATUS_AWAY;          break;
    case 2:  initialStatus = STATUS_BE_RIGHT_BACK; break;
    case 3:  initialStatus = STATUS_BUSY;          break;
    case 4:  initialStatus = STATUS_OUT_TO_LUNCH;  break;
    case 5:  initialStatus = STATUS_ON_THE_PHONE;  break;
    case 6:  initialStatus = STATUS_INVISIBLE;     break;
    case 0:
    default: initialStatus = STATUS_ONLINE;        break;
  }

  // Set the state.
  // This toggles reconnection, and "continue connecting" stuff.
  triedConnecting_ = true;

  // When we connect to an account from outside InitialView, the actual connection
  // process may be handled externally, so emitting the signal below would cause
  // problems, and even infinite loops.
  if( ! emitConnectionSignal )
  {
    return true;
  }

  // Inform parent with the account information
  emit connectWithAccount( handle,
                           password,
                           rememberAccountCheckBox_  ->isChecked(),
                           rememberPasswordCheckBox_ ->isChecked(),
                           rememberAutoLoginCheckBox_->isChecked(),
                           initialStatus );

  return true;
}



// Change the connection status text
void InitialView::statusMessage( const QString text, int timeout )
{
  statusLabel_->setText( text );

  if( timeout > 0 )
  {
    statusMessageTimer_.start( timeout );
  }
  else
  {
    statusMessageTimer_.stop();
  }
}



// Execute the browser for a clicked UI link
void InitialView::slotClickedUrl( const QString &url )
{
  // Handle special links
  if( url.startsWith( "kmess://" ) )
  {
    if( url == "kmess://reconnect/" )
    {
      startConnecting( reconnectionHandle_ );
    }

    return;
  }

  KMessShared::openBrowser( KUrl( url ) );
}



bool InitialView::eventFilter(QObject *obj, QEvent *event)
{
  // Handle keyboard events for all widgets
  const QEvent::Type& eventType( event->type() );

  if( eventType == QEvent::KeyPress )
  {
    const QKeyEvent *keyEvent = static_cast<QKeyEvent*>( event );
    int key = keyEvent->key();

    // Enable pressing Enter from any widget to start connecting
    if( ( key == Qt::Key_Return || key == Qt::Key_Enter )
    ||  ( key == Qt::Key_Escape && isConnectingUI_ ) )    // Enable pressing Esc to cancel a connection attempt
    {
      slotConnectClicked();
      return true;
    }
  }

  // The following code is only for the picture label. If any code has to be added for
  // another widget, this code may need to be changed..

  if( obj != pictureLabel_ )
  {
    return false;  // don't stop processing.
  }

  // Don't handle events when connecting
  if( isConnectingUI_ )
  {
    return false;
  }

  Account *account = accounts_[ getSelectedHandle() ];

  if( eventType == QEvent::Enter ) // Glow effect when mouse enters display picture
  {
    QImage glowingImage;

    if( account != 0 && account->getShowPicture() )
    {
      glowingImage = QImage( account->getPicturePath() );
    }
    else
    {
      glowingImage = QImage( KGlobal::dirs()->findResource( "data", "kmess/pics/kmesspic.png" ) );
    }

    KIconEffect::toGamma( glowingImage, 0.8f );
    pictureLabel_->setPixmap( QPixmap::fromImage( glowingImage ) );
  }
  else if( eventType == QEvent::Leave ) // Restore default when mouse leaves display picture
  {
    QPixmap picture;

    if( account != 0 && account->getShowPicture() )
    {
        picture = QPixmap( account->getPicturePath() );
    }
    else
    {
      picture = QPixmap( KGlobal::dirs()->findResource( "data", "kmess/pics/kmesspic.png" ) );
    }

    pictureLabel_->setPixmap( picture );
  }
  else if( eventType == QEvent::Wheel && handleCombobox_->isEnabled() == true ) // Switch accounts using mousewheel
  {
    const QWheelEvent *wheelEvent = static_cast<QWheelEvent*>( event );

    int newIndex = handleCombobox_->currentIndex();

    if( wheelEvent->delta() > 0 )
    {
      newIndex--;

      if( newIndex < 0 )
      {
        newIndex = handleCombobox_->count() - 1;
      }
    }
    else
    {
      newIndex++;

      if( newIndex >= handleCombobox_->count() )
      {
        newIndex = 0;
      }
    }

    handleCombobox_->setCurrentIndex( newIndex );
  }
  else if( eventType == QEvent::MouseButtonRelease ) // Show settings when display picture is clicked
  {
    emit showSettings( account );
  }

  return false;  // don't stop processing.
}



#include "initialview.moc"
