00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "identitystatuswidget.h"
00021 #include "ui_identitystatusbase.h"
00022 #include "addaccountwizard.h"
00023
00024 #include <KIcon>
00025 #include <KMenu>
00026 #include <KActionMenu>
00027 #include <QTimeLine>
00028 #include <QToolTip>
00029 #include <QCursor>
00030 #include <QUrl>
00031 #include <QHelpEvent>
00032 #include <KColorScheme>
00033 #include <kopeteidentity.h>
00034 #include <kopeteidentitymanager.h>
00035 #include <kopeteaccount.h>
00036 #include <kopeteaccountmanager.h>
00037 #include <kopetecontact.h>
00038 #include <kopeteprotocol.h>
00039 #include <kopetestdaction.h>
00040 #include <avatardialog.h>
00041 #include <KDebug>
00042 #include <kopeteuiglobal.h>
00043 #include <KCMultiDialog>
00044
00045 #include "kopetestatusrootaction.h"
00046
00047 class IdentityStatusWidget::Private
00048 {
00049 public:
00050 Kopete::Identity *identity;
00051 Ui::IdentityStatusBase ui;
00052 QTimeLine *timeline;
00053 QString photoPath;
00054 QHash<QListWidgetItem *,Kopete::Account *> accountHash;
00055 bool dirty;
00056 };
00057
00058 IdentityStatusWidget::IdentityStatusWidget(Kopete::Identity *identity, QWidget *parent)
00059 : QWidget(parent)
00060 {
00061 d = new Private();
00062 d->identity = 0;
00063
00064
00065 d->timeline = new QTimeLine( 150, this );
00066 d->timeline->setCurveShape( QTimeLine::EaseInOutCurve );
00067 connect( d->timeline, SIGNAL(valueChanged(qreal)),
00068 this, SLOT(slotAnimate(qreal)) );
00069
00070 d->ui.setupUi(this);
00071 d->ui.accounts->setContextMenuPolicy( Qt::CustomContextMenu );
00072 QWidget::setVisible( false );
00073
00074 setIdentity(identity);
00075
00076
00077 connect( d->ui.accounts, SIGNAL(customContextMenuRequested(const QPoint &)),
00078 this, SLOT(showAccountContextMenu(const QPoint &)) );
00079 connect( d->ui.accounts, SIGNAL(itemClicked(QListWidgetItem *)),
00080 this, SLOT(slotAccountClicked( QListWidgetItem *)) );
00081 connect( d->ui.photo, SIGNAL(clicked()),
00082 this, SLOT(slotPhotoClicked()));
00083
00084 connect( Kopete::AccountManager::self(), SIGNAL(accountRegistered(Kopete::Account*)),
00085 this, SLOT(slotAccountRegistered(Kopete::Account*)));
00086 connect( Kopete::AccountManager::self(), SIGNAL(accountUnregistered(const Kopete::Account*)),
00087 this, SLOT(slotAccountUnregistered(const Kopete::Account*)));
00088
00089 connect( Kopete::IdentityManager::self(), SIGNAL(identityUnregistered(const Kopete::Identity*)),
00090 this, SLOT(slotIdentityUnregistered(const Kopete::Identity*)));
00091
00092 d->ui.accounts->viewport()->installEventFilter( this );
00093 }
00094
00095 IdentityStatusWidget::~IdentityStatusWidget()
00096 {
00097 delete d;
00098 }
00099
00100 void IdentityStatusWidget::setIdentity(Kopete::Identity *identity)
00101 {
00102 d->identity = identity;
00103 load();
00104
00105 if (d->identity)
00106 {
00107
00108
00109 ;
00110 }
00111 }
00112
00113 Kopete::Identity *IdentityStatusWidget::identity() const
00114 {
00115 return d->identity;
00116 }
00117
00118 void IdentityStatusWidget::setVisible( bool visible )
00119 {
00120 if ( visible == isVisible() )
00121 return;
00122
00123
00124 d->timeline->setDirection( visible ? QTimeLine::Forward
00125 : QTimeLine::Backward );
00126 d->timeline->start();
00127 }
00128
00129 bool IdentityStatusWidget::eventFilter( QObject *watched, QEvent *event )
00130 {
00131 if( event->type() == QEvent::ToolTip && watched == d->ui.accounts->viewport() )
00132 {
00133 QHelpEvent *helpEvent = static_cast<QHelpEvent *>(event);
00134 QListWidgetItem* item = d->ui.accounts->itemAt( helpEvent->pos() );
00135 if ( item )
00136 {
00137 const Kopete::Account * account = d->accountHash.value( item, 0 );
00138 if ( account )
00139 item->setToolTip( account->myself()->toolTip() );
00140 }
00141 }
00142 return QWidget::eventFilter( watched, event );
00143 }
00144
00145 void IdentityStatusWidget::slotAnimate(qreal amount)
00146 {
00147 if (amount == 0)
00148 {
00149 QWidget::setVisible( false );
00150 return;
00151 }
00152
00153 if (amount == 1.0)
00154 {
00155 layout()->setSizeConstraint( QLayout::SetDefaultConstraint );
00156 setFixedHeight( sizeHint().height() );
00157 return;
00158 }
00159
00160 setFixedHeight( sizeHint().height() * amount );
00161
00162 if (!isVisible())
00163 QWidget::setVisible( true );
00164 }
00165
00166 void IdentityStatusWidget::load()
00167 {
00168
00169 d->ui.accounts->clear();
00170 d->accountHash.clear();
00171
00172 if (!d->identity)
00173 return;
00174
00175 Kopete::Global::Properties *props = Kopete::Global::Properties::self();
00176
00177
00178 if (d->identity->hasProperty(props->photo().key()))
00179 {
00180 d->photoPath = d->identity->property(props->photo()).value().toString();
00181 d->ui.photo->setIcon( QIcon( d->photoPath ) );
00182 } else {
00183 d->ui.photo->setIcon( KIcon( "user-identity" ) );
00184 }
00185
00186 d->ui.identityName->setText(d->identity->label());
00187
00188 foreach(Kopete::Account *a, d->identity->accounts()) {
00189 addAccountItem( a );
00190 }
00191 if ( d->identity->accounts().isEmpty() ) {
00192 new QListWidgetItem( KIcon("configure" ), i18nc("Button to open account configuration widget", "Click to add an account" ), d->ui.accounts );
00193 }
00194 resizeAccountListWidget();
00195 }
00196
00197 void IdentityStatusWidget::slotAccountRegistered( Kopete::Account *account )
00198 {
00199 if (account && account->identity() == d->identity && d->accountHash.isEmpty())
00200 {
00201
00202 d->ui.accounts->clear();
00203 }
00204
00205 addAccountItem( account );
00206 resizeAccountListWidget();
00207 }
00208
00209 void IdentityStatusWidget::slotAccountUnregistered( const Kopete::Account *account )
00210 {
00211 QListWidgetItem * item = 0;
00212
00213 QHashIterator<QListWidgetItem*, Kopete::Account *> i( d->accountHash );
00214 while ( i.hasNext() ) {
00215 i.next();
00216 Kopete::Account * candidate = i.value();
00217 if ( candidate == account ) {
00218 item = i.key();
00219 }
00220 }
00221 if( !item )
00222 return;
00223 d->ui.accounts->takeItem( d->ui.accounts->row( item ) );
00224 d->accountHash.remove( item );
00225 delete item;
00226
00227 if ( d->identity && d->identity->accounts().isEmpty() ) {
00228 new QListWidgetItem( KIcon("configure" ), i18nc("Button to open account configuration widget", "Click to add an account" ), d->ui.accounts );
00229 }
00230 resizeAccountListWidget();
00231 }
00232
00233 void IdentityStatusWidget::addAccountItem( Kopete::Account *account )
00234 {
00235
00236
00237
00238 if ( !account || ( account->identity() != d->identity ) ) {
00239 return;
00240 }
00241
00242 connect( account->myself(),
00243 SIGNAL(onlineStatusChanged(Kopete::Contact *, const Kopete::OnlineStatus &, const Kopete::OnlineStatus &)),
00244 this, SLOT(slotAccountStatusIconChanged(Kopete::Contact *)) );
00245
00246 QListWidgetItem * item = new QListWidgetItem( account->accountIcon(), account->accountLabel(), d->ui.accounts );
00247 d->accountHash.insert( item, account );
00248
00249 slotAccountStatusIconChanged( account->myself() );
00250 }
00251
00252 void IdentityStatusWidget::slotAccountStatusIconChanged( Kopete::Contact *contact )
00253 {
00255 Kopete::OnlineStatus status = contact->onlineStatus();
00256 QListWidgetItem * item = 0;
00257 QHashIterator<QListWidgetItem*, Kopete::Account *> i( d->accountHash );
00258 while ( i.hasNext() ) {
00259 i.next();
00260 Kopete::Account * candidate = i.value();
00261 if ( candidate == contact->account() ) {
00262 item = i.key();
00263 }
00264 }
00265 if( !item )
00266 return;
00267
00268 item->setIcon ( status.iconFor( contact->account() ) );
00269 }
00270
00271 void IdentityStatusWidget::showAccountContextMenu( const QPoint & point )
00272 {
00273 QListWidgetItem * item = d->ui.accounts->itemAt( point );
00274 if ( item && !d->accountHash.isEmpty() ) {
00275 Kopete::Account * account = d->accountHash[ item ];
00276 if ( account ) {
00277 KActionMenu *actionMenu = new KActionMenu( account->accountId(), account );
00278
00279 if ( !account->hasCustomStatusMenu() )
00280 Kopete::StatusRootAction::createAccountStatusActions( account, actionMenu );
00281
00282 account->fillActionMenu( actionMenu );
00283
00284 actionMenu->menu()->exec( d->ui.accounts->mapToGlobal( point ) );
00285 delete actionMenu;
00286 }
00287 }
00288 }
00289
00290 void IdentityStatusWidget::slotAccountClicked( QListWidgetItem * item )
00291 {
00292 Q_UNUSED( item );
00293
00294 if ( d->identity->accounts().isEmpty() )
00295 {
00296 Q_ASSERT(d->accountHash.isEmpty());
00297
00298 AddAccountWizard *addwizard = new AddAccountWizard( this, true );
00299 addwizard->setIdentity(identity());
00300 addwizard->show();
00301 }
00302 }
00303
00304 void IdentityStatusWidget::slotPhotoClicked()
00305 {
00306 bool ok, changed = false;
00307 const QString photoPath = Kopete::UI::AvatarDialog::getAvatar( this, d->photoPath, &ok);
00308 if ( ok ) {
00309 Kopete::Global::Properties *props = Kopete::Global::Properties::self();
00310 if ( photoPath.isEmpty() ) {
00311 d->identity->removeProperty( props->photo() );
00312 d->photoPath.clear();
00313 changed = true;
00314 }
00315 else if ( photoPath != d->photoPath ) {
00316 d->identity->setProperty(props->photo(), photoPath);
00317 d->photoPath = photoPath;
00318 changed = true;
00319 }
00320
00321 if ( changed ) {
00322 load();
00323 }
00324 }
00325 }
00326
00327 void IdentityStatusWidget::resizeAccountListWidget()
00328 {
00329 int frameWidth = d->ui.accounts->frameWidth();
00330 int itemHeight = d->ui.accounts->itemDelegate()->sizeHint(
00331 QStyleOptionViewItem(), d->ui.accounts->model()->index( 0, 0 ) ).height();
00332 int itemCount = d->ui.accounts->count();
00333 d->ui.accounts->setFixedHeight( 2 * frameWidth
00334 + itemHeight * ( itemCount ? itemCount : 1 ) );
00335 layout()->invalidate();
00336 setFixedHeight( sizeHint().height() );
00337
00338 }
00339
00340 void IdentityStatusWidget::slotIdentityUnregistered( const Kopete::Identity* identity )
00341 {
00342 if ( identity == d->identity )
00343 {
00344 disconnect( identity );
00345 hide();
00346 setIdentity( Kopete::IdentityManager::self()->defaultIdentity() );
00347 }
00348 }
00349
00350 #include "identitystatuswidget.moc"
00351
00352