kitchensync

groupitem.cpp

00001 /*
00002     This file is part of KitchenSync.
00003 
00004     Copyright (c) 2005 Tobias Koenig <tokoe@kde.org>
00005 
00006     This program is free software; you can redistribute it and/or modify
00007     it under the terms of the GNU General Public License as published by
00008     the Free Software Foundation; either version 2 of the License, or
00009     (at your option) any later version.
00010 
00011     This program is distributed in the hope that it will be useful,
00012     but WITHOUT ANY WARRANTY; without even the implied warranty of
00013     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00014     GNU General Public License for more details.
00015 
00016     You should have received a copy of the GNU General Public License
00017     along with this program; if not, write to the Free Software
00018     Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00019 */
00020 
00021 #include <kapplication.h>
00022 #include <kdialog.h>
00023 #include <kglobal.h>
00024 #include <kglobalsettings.h>
00025 #include <kiconloader.h>
00026 #include <klocale.h>
00027 #include <kpassivepopup.h>
00028 #include <kurllabel.h>
00029 
00030 #include <qlabel.h>
00031 #include <qlayout.h>
00032 #include <qpixmap.h>
00033 #include <qprogressbar.h>
00034 #include <qvbox.h>
00035 
00036 #include "memberinfo.h"
00037 #include "multiconflictdialog.h"
00038 #include "singleconflictdialog.h"
00039 #include "syncprocessmanager.h"
00040 
00041 #include "groupitem.h"
00042 
00043 GroupItem::GroupItem( KWidgetList *parent, SyncProcess *process )
00044   : KWidgetListItem( parent ), mSyncProcess( process ),
00045     mCallbackHandler( new QSync::CallbackHandler ),
00046     mProcessedItems( 0 ), mMaxProcessedItems( 0 ),
00047     mSynchronizing( false )
00048 {
00049   QFont boldFont;
00050   boldFont.setBold( true );
00051   boldFont.setPointSize( boldFont.pointSize() + 2 );
00052 
00053   QGridLayout *layout = new QGridLayout( this, 4, 4, KDialog::marginHint(), KDialog::spacingHint() );
00054 
00055   mBox = new QVBox( this );
00056   mBox->setMargin( 5 );
00057   mProgressBar = new QProgressBar( this );
00058   mProgressBar->setTotalSteps( 100 );
00059 
00060   mTime = new QLabel( this );
00061   mSyncAction = new KURLLabel( "exec:/sync", i18n( "Synchronize Now" ), this );
00062   mConfigureAction = new KURLLabel( "exec:/config", i18n( "Configure" ), this );
00063 
00064   // header
00065   QHBox* hbox = new QHBox( this );
00066   hbox->setMargin( 2 );
00067 
00068   static QPixmap icon;
00069   if ( icon.isNull() )
00070     icon = KGlobal::iconLoader()->loadIcon( "kontact_summary", KIcon::Desktop );
00071 
00072   mIcon = new QLabel( hbox );
00073   mIcon->setPixmap( icon );
00074   mIcon->setFixedSize( mIcon->sizeHint() );
00075   mIcon->setPaletteBackgroundColor( colorGroup().mid() );
00076 
00077   mGroupName = new QLabel( hbox );
00078   mGroupName->setAlignment( AlignLeft | AlignVCenter );
00079   mGroupName->setIndent( KDialog::spacingHint() );
00080   mGroupName->setFont( boldFont );
00081   mGroupName->setPaletteForegroundColor( colorGroup().light() );
00082   mGroupName->setPaletteBackgroundColor( colorGroup().mid() );
00083 
00084   mStatus = new QLabel( hbox );
00085   mStatus->setAlignment( Qt::AlignRight );
00086   mStatus->setAlignment( AlignRight | AlignVCenter );
00087   mStatus->setIndent( KDialog::spacingHint() );
00088   mStatus->setFont( boldFont );
00089   mStatus->setPaletteForegroundColor( colorGroup().light() );
00090   mStatus->setPaletteBackgroundColor( colorGroup().mid() );
00091   mStatus->setText( i18n( "Ready" ) );
00092 
00093   hbox->setPaletteBackgroundColor( colorGroup().mid() );
00094   hbox->setMaximumHeight( hbox->minimumSizeHint().height() );
00095 
00096   layout->addMultiCellWidget( hbox, 0, 0, 0, 3 );
00097   layout->addMultiCellWidget( mBox, 1, 1, 0, 3 );
00098   layout->addWidget( mTime, 2, 0 );
00099   layout->addWidget( mSyncAction, 2, 1 );
00100   layout->addWidget( mConfigureAction, 2, 2 );
00101   layout->addWidget( mProgressBar, 2, 3 );
00102   layout->setColStretch( 0, 1 );
00103   layout->setRowStretch( 3, 1 );
00104 
00105   setPaletteBackgroundColor( kapp->palette().active().base() );
00106 
00107   connect( mCallbackHandler, SIGNAL( conflict( QSync::SyncMapping ) ),
00108            this, SLOT( conflict( QSync::SyncMapping ) ) );
00109   connect( mCallbackHandler, SIGNAL( change( const QSync::SyncChangeUpdate& ) ),
00110            this, SLOT( change( const QSync::SyncChangeUpdate& ) ) );
00111   connect( mCallbackHandler, SIGNAL( mapping( const QSync::SyncMappingUpdate& ) ),
00112            this, SLOT( mapping( const QSync::SyncMappingUpdate& ) ) );
00113   connect( mCallbackHandler, SIGNAL( engine( const QSync::SyncEngineUpdate& ) ),
00114            this, SLOT( engine( const QSync::SyncEngineUpdate& ) ) );
00115   connect( mCallbackHandler, SIGNAL( member( const QSync::SyncMemberUpdate& ) ),
00116            this, SLOT( member( const QSync::SyncMemberUpdate& ) ) );
00117   connect( mSyncAction, SIGNAL( leftClickedURL() ),
00118            this, SLOT( synchronize() ) );
00119   connect( mConfigureAction, SIGNAL( leftClickedURL() ),
00120            this, SLOT( configure() ) );
00121   connect( mSyncProcess, SIGNAL( engineChanged( QSync::Engine* ) ),
00122            this, SLOT( engineChanged( QSync::Engine* ) ) );
00123 
00124   mCallbackHandler->setEngine( mSyncProcess->engine() );
00125 
00126   setSelectionForegroundColor( KGlobalSettings::textColor() );
00127   setSelectionBackgroundColor( KGlobalSettings::alternateBackgroundColor() );
00128 
00129   update();
00130 }
00131 
00132 GroupItem::~GroupItem()
00133 {
00134   delete mCallbackHandler;
00135   mCallbackHandler = 0;
00136 }
00137 
00138 void GroupItem::update()
00139 {
00140   clear();
00141 
00142   mGroupName->setText( i18n( "Group: %1" ).arg( mSyncProcess->group().name() ) );
00143 
00144   QDateTime dateTime = mSyncProcess->group().lastSynchronization();
00145   if ( dateTime.isValid() )
00146     mTime->setText( i18n( "Last synchronized on: %1" ).arg( KGlobal::locale()->formatDateTime( dateTime ) ) );
00147   else
00148     mTime->setText( i18n( "Not synchronized yet" ) );
00149 
00150   mProgressBar->reset();
00151   mProgressBar->hide();
00152 
00153   QSync::Group group = mSyncProcess->group();
00154   QSync::Group::Iterator memberIt( group.begin() );
00155   QSync::Group::Iterator memberEndIt( group.end() );
00156 
00157   for ( ; memberIt != memberEndIt; ++memberIt ) {
00158     MemberItem *item = new MemberItem( mBox, mSyncProcess, *memberIt );
00159     item->show();
00160     item->setStatusMessage( i18n( "Ready" ) );
00161     mMemberItems.append( item );
00162   }
00163 }
00164 
00165 void GroupItem::clear()
00166 {
00167   mGroupName->setText( QString() );
00168 
00169   QValueList<MemberItem*>::Iterator it;
00170   for ( it = mMemberItems.begin(); it != mMemberItems.end(); ++it )
00171     delete *it;
00172 
00173   mMemberItems.clear();
00174 }
00175 
00176 void GroupItem::conflict( QSync::SyncMapping mapping )
00177 {
00178   if ( mapping.changesCount() == 2 ) {
00179     SingleConflictDialog dlg( mapping, this );
00180     dlg.exec();
00181   } else {
00182     MultiConflictDialog dlg( mapping, this );
00183     dlg.exec();
00184   }
00185 }
00186 
00187 void GroupItem::change( const QSync::SyncChangeUpdate &update )
00188 {
00189   switch ( update.type() ) {
00190     case QSync::SyncChangeUpdate::Received:
00191       mProcessedItems++;
00192       mStatus->setText( i18n( "%1 entries read" ).arg( mProcessedItems ) );
00193       break;
00194     case QSync::SyncChangeUpdate::ReceivedInfo:
00195       mStatus->setText( i18n( "Receive information" ) );
00196       break;
00197     case QSync::SyncChangeUpdate::Sent:
00198       mProcessedItems--;
00199       mStatus->setText( i18n( "%1 entries written" ).arg( mMaxProcessedItems - mProcessedItems ) );
00200 
00201       mProgressBar->show();
00202 
00203       {
00204         int progress = 100;
00205         if ( mMaxProcessedItems != 0 )
00206           progress = (mProcessedItems * 100) / mMaxProcessedItems;
00207 
00208         if ( progress < 0 )
00209           progress = 0;
00210 
00211         mProgressBar->setProgress( 100 - progress );
00212       }
00213       break;
00214     case QSync::SyncChangeUpdate::WriteError:
00215       mStatus->setText( i18n( "Error" ) );
00216       KPassivePopup::message( update.result().message(), this );
00217       break;
00218     case QSync::SyncChangeUpdate::ReceiveError:
00219       mStatus->setText( i18n( "Error" ) );
00220       KPassivePopup::message( update.result().message(), this );
00221       break;
00222     default:
00223       mStatus->setText( QString() );
00224       break;
00225   }
00226 }
00227 
00228 void GroupItem::mapping( const QSync::SyncMappingUpdate& )
00229 {
00230 }
00231 
00232 void GroupItem::engine( const QSync::SyncEngineUpdate &update )
00233 {
00234   switch ( update.type() ) {
00235     case QSync::SyncEngineUpdate::EndPhaseConnected:
00236       mStatus->setText( i18n( "Connected" ) );
00237       mProgressBar->setProgress( 0 );
00238       mSynchronizing = true;
00239       mSyncAction->setText( "Abort Synchronization" );
00240       break;
00241     case QSync::SyncEngineUpdate::EndPhaseRead:
00242       mStatus->setText( i18n( "Data read" ) );
00243       break;
00244     case QSync::SyncEngineUpdate::EndPhaseWrite:
00245       mStatus->setText( i18n( "Data written" ) );
00246       mProgressBar->setProgress( 100 );
00247       mProcessedItems = mMaxProcessedItems = 0;
00248       break;
00249     case QSync::SyncEngineUpdate::EndPhaseDisconnected:
00250       mStatus->setText( i18n( "Disconnected" ) );
00251       break;
00252     case QSync::SyncEngineUpdate::Error:
00253       mStatus->setText( i18n( "Synchronization failed" ) );
00254       KPassivePopup::message( update.result().message(), this );
00255       this->update();
00256 
00257       mSynchronizing = false;
00258       mSyncAction->setText( i18n( "Synchronize Now" ) );
00259       break;
00260     case QSync::SyncEngineUpdate::SyncSuccessfull:
00261       mStatus->setText( i18n( "Successfully synchronized" ) );
00262       mSyncProcess->group().setLastSynchronization( QDateTime::currentDateTime() );
00263       mSyncProcess->group().save();
00264       this->update();
00265 
00266       mSynchronizing = false;
00267       mSyncAction->setText( i18n( "Synchronize Now" ) );
00268       break;
00269     case QSync::SyncEngineUpdate::PrevUnclean:
00270       mStatus->setText( i18n( "Previous synchronization failed" ) );
00271       break;
00272     case QSync::SyncEngineUpdate::EndConflicts:
00273       mStatus->setText( i18n( "Conflicts solved" ) );
00274       mMaxProcessedItems = mProcessedItems;
00275       break;
00276     default:
00277       mStatus->setText( QString() );
00278       break;
00279   }
00280 }
00281 
00282 void GroupItem::member( const QSync::SyncMemberUpdate &update )
00283 {
00284   QValueList<MemberItem*>::Iterator it;
00285   for ( it = mMemberItems.begin(); it != mMemberItems.end(); ++it ) {
00286     if ( (*it)->member() == update.member() ) {
00287       switch ( update.type() ) {
00288         case QSync::SyncMemberUpdate::Connected:
00289           (*it)->setStatusMessage( i18n( "Connected" ) );
00290           break;
00291         case QSync::SyncMemberUpdate::SentChanges:
00292           (*it)->setStatusMessage( i18n( "Changes read" ) );
00293           break;
00294         case QSync::SyncMemberUpdate::CommittedAll:
00295           (*it)->setStatusMessage( i18n( "Changes written" ) );
00296           break;
00297         case QSync::SyncMemberUpdate::Disconnected:
00298           (*it)->setStatusMessage( i18n( "Disconnected" ) );
00299           break;
00300         case QSync::SyncMemberUpdate::ConnectError:
00301           (*it)->setStatusMessage( i18n( "Error: %1" ).arg( update.result().message() ) );
00302           break;
00303         case QSync::SyncMemberUpdate::GetChangesError:
00304           (*it)->setStatusMessage( i18n( "Error: %1" ).arg( update.result().message() ) );
00305           break;
00306         case QSync::SyncMemberUpdate::CommittedAllError:
00307           (*it)->setStatusMessage( i18n( "Error: %1" ).arg( update.result().message() ) );
00308           break;
00309         case QSync::SyncMemberUpdate::SyncDoneError:
00310           (*it)->setStatusMessage( i18n( "Error: %1" ).arg( update.result().message() ) );
00311           break;
00312         case QSync::SyncMemberUpdate::DisconnectedError:
00313           (*it)->setStatusMessage( i18n( "Error: %1" ).arg( update.result().message() ) );
00314           break;
00315         default:
00316           break;
00317       }
00318 
00319       return;
00320     }
00321   }
00322 }
00323 
00324 void GroupItem::synchronize()
00325 {
00326   if ( !mSynchronizing )
00327     emit synchronizeGroup( mSyncProcess );
00328   else
00329     emit abortSynchronizeGroup( mSyncProcess );
00330 }
00331 
00332 void GroupItem::configure()
00333 {
00334   emit configureGroup( mSyncProcess );
00335 
00336   this->update();
00337 }
00338 
00339 void GroupItem::engineChanged( QSync::Engine *engine )
00340 {
00341   Q_ASSERT( engine );
00342 
00343   mCallbackHandler->setEngine( engine );
00344 
00345   this->update();
00346 }
00347 
00348 MemberItem::MemberItem( QWidget *parent, SyncProcess *process,
00349                         const QSync::Member &member )
00350   : QWidget( parent ), mSyncProcess( process ), mMember( member )
00351 {
00352   QFont boldFont;
00353   boldFont.setBold( true );
00354 
00355   MemberInfo mi( member );
00356 
00357   QPixmap icon = mi.smallIcon();
00358 
00359   QSync::Plugin plugin = member.plugin();
00360 
00361   QVBoxLayout *layout = new QVBoxLayout( this );
00362 
00363   QHBox* box = new QHBox( this );
00364   box->setMargin( 5 );
00365   box->setSpacing( 6 );
00366   layout->addWidget( box );
00367 
00368   mIcon = new QLabel( box );
00369   mIcon->setPixmap( icon );
00370   mIcon->setAlignment( Qt::AlignTop );
00371   mIcon->setFixedWidth( mIcon->sizeHint().width() );
00372 
00373   QVBox *nameBox = new QVBox( box );
00374   mMemberName = new QLabel( nameBox );
00375   mMemberName->setFont( boldFont );
00376   mDescription = new QLabel( nameBox );
00377 
00378   mStatus = new QLabel( box );
00379 
00380   mMemberName->setText( member.name() );
00381   mDescription->setText( plugin.longName() );
00382 }
00383 
00384 void MemberItem::setStatusMessage( const QString &msg )
00385 {
00386   mStatus->setText( msg );
00387 }
00388 
00389 #include "groupitem.moc"
KDE Home | KDE Accessibility Home | Description of Access Keys