libkdepim Library API Documentation

addressesdialog.cpp

00001 /*  -*- mode: C++; c-file-style: "gnu" -*-
00002  *
00003  *  This file is part of libkdepim.
00004  *  Copyright (c) 2003 Zack Rusin <zack@kde.org>
00005  *  Copyright (c) 2003 Aaron J. Seigo <aseigo@kde.org>
00006  *
00007  *  This library is free software; you can redistribute it and/or
00008  *  modify it under the terms of the GNU Library General Public
00009  *  License as published by the Free Software Foundation; either
00010  *  version 2 of the License, or (at your option) any later version.
00011  *
00012  *  This library is distributed in the hope that it will be useful,
00013  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015  *  Library General Public License for more details.
00016  *
00017  *  You should have received a copy of the GNU Library General Public License
00018  *  along with this library; see the file COPYING.LIB.  If not, write to
00019  *  the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00020  *  Boston, MA 02111-1307, USA.
00021  *
00022  */
00023 
00024 #include "addressesdialog.h"
00025 #include "ldapsearchdialog.h"
00026 
00027 #include <kabc/stdaddressbook.h>
00028 #include <kabc/distributionlist.h>
00029 #include <kresources/selectdialog.h>
00030 #include <kabc/resource.h>
00031 #include <kapplication.h>
00032 #include <kdebug.h>
00033 #include <kglobal.h>
00034 #include <kiconloader.h>
00035 #include <kinputdialog.h>
00036 #include <klineedit.h>
00037 #include <klocale.h>
00038 #include <kmessagebox.h>
00039 #include <kprocess.h>
00040 #include <kpushbutton.h>
00041 #include <krun.h>
00042 #include <kstandarddirs.h>
00043 
00044 #include <qdict.h>
00045 #include <qlayout.h>
00046 #include <qvbox.h>
00047 #include <qwidget.h>
00048 
00049 #include "addresspicker.h"
00050 #include "distributionlist.h"
00051 #include "email.h"
00052 
00053 namespace KPIM {
00054 
00055 // private start :
00056 struct AddresseeViewItem::AddresseeViewItemPrivate {
00057   KABC::Addressee               address;
00058   AddresseeViewItem::Category   category;
00059   KABC::Addressee::List         addresses;
00060 };
00061 
00062 struct AddressesDialog::AddressesDialogPrivate {
00063   AddressesDialogPrivate() : 
00064     ui(0), personal(0), recent(0),
00065     toItem(0), ccItem(0), bccItem(0),
00066     ldapSearchDialog(0)
00067   {}
00068 
00069   AddressPickerUI             *ui;
00070 
00071   AddresseeViewItem           *personal;
00072   AddresseeViewItem           *recent;
00073 
00074   AddresseeViewItem           *toItem;
00075   AddresseeViewItem           *ccItem;
00076   AddresseeViewItem           *bccItem;
00077 
00078   QDict<AddresseeViewItem>     groupDict;
00079 
00080   KABC::Addressee::List       recentAddresses;
00081   LDAPSearchDialog            *ldapSearchDialog;
00082 };
00083 // privates end
00084 
00085 AddresseeViewItem::AddresseeViewItem( AddresseeViewItem *parent, const KABC::Addressee& addr,
00086                                       int emailIndex )
00087   : QObject( 0 ), KListViewItem( parent, addr.realName(),
00088                                ( emailIndex == 0 ? addr.preferredEmail() : addr.emails()[ emailIndex ] ) )
00089 {
00090   d = new AddresseeViewItemPrivate;
00091   d->address = addr;
00092   d->category = Entry;
00093 
00094   if ( text( 0 ).stripWhiteSpace().isEmpty() )
00095     setText( 0, addr.preferredEmail() );
00096 
00097   if ( addr.photo().url().isEmpty() ) {
00098     if ( addr.photo().data().isNull() )
00099       setPixmap( 0, KGlobal::iconLoader()->loadIcon( "personal", KIcon::Small ) );
00100     else
00101       setPixmap( 0, addr.photo().data().smoothScale( 16, 16 ) );
00102   } else {
00103     setPixmap( 0, KGlobal::iconLoader()->loadIcon( addr.photo().url(), KIcon::Small ) );
00104   }
00105 }
00106 
00107 AddresseeViewItem::AddresseeViewItem( KListView *lv, const QString& name, Category cat )
00108   : QObject(0), KListViewItem( lv, name )
00109 {
00110   d = new AddresseeViewItemPrivate;
00111   d->category = cat;
00112 }
00113 
00114 AddresseeViewItem::AddresseeViewItem(  AddresseeViewItem *parent, const QString& name,
00115                                        const KABC::Addressee::List &lst )
00116   : QObject(0), KListViewItem( parent, name, i18n("<group>") )
00117 {
00118   d = new AddresseeViewItemPrivate;
00119   d->category = FilledGroup;
00120   d->addresses = lst;
00121 }
00122 
00123 AddresseeViewItem::AddresseeViewItem(  AddresseeViewItem *parent, const QString& name )
00124   : QObject(0), KListViewItem( parent, name, i18n("<group>") )
00125 {
00126   d = new AddresseeViewItemPrivate;
00127   d->category = DistList;
00128 
00129   setPixmap( 0, KGlobal::iconLoader()->loadIcon( "kdmconfig", KIcon::Small ) );
00130 }
00131 
00132 AddresseeViewItem::~AddresseeViewItem()
00133 {
00134   delete d;
00135   d = 0;
00136 }
00137 
00138 KABC::Addressee
00139 AddresseeViewItem::addressee() const
00140 {
00141   return d->address;
00142 }
00143 
00144 KABC::Addressee::List
00145 AddresseeViewItem::addresses() const
00146 {
00147   return d->addresses;
00148 }
00149 
00150 AddresseeViewItem::Category
00151 AddresseeViewItem::category() const
00152 {
00153   return d->category;
00154 }
00155 
00156 QString
00157 AddresseeViewItem::name() const
00158 {
00159   return text(0);
00160 }
00161 
00162 QString
00163 AddresseeViewItem::email() const
00164 {
00165   return text(1);
00166 }
00167 
00168 bool AddresseeViewItem::matches(const QString& txt) const
00169 {
00170     return d->address.realName().contains(txt, false) || d->address.preferredEmail().contains(txt, false);
00171 }
00172 
00173 void AddresseeViewItem::setSelected(bool selected)
00174 {
00175     if (selected == isSelected())
00176     {
00177         return;
00178     }
00179 
00180     emit addressSelected( this, selected );
00181     QListViewItem::setSelected(selected);
00182 }
00183 
00184 int
00185 AddresseeViewItem::compare( QListViewItem * i, int col, bool ascending ) const
00186 {
00187   if ( category() == Group || category() == Entry )
00188     return KListViewItem::compare( i , col, ascending );
00189 
00190   AddresseeViewItem *item = static_cast<AddresseeViewItem*>( i );
00191   int a = static_cast<int>( category() );
00192   int b = static_cast<int>( item->category() );
00193 
00194   if ( ascending )
00195     if ( a < b )
00196       return -1;
00197     else
00198       return 1;
00199   else
00200     if ( a < b )
00201       return 1;
00202     else
00203       return -1;
00204 }
00205 
00206 AddressesDialog::AddressesDialog( QWidget *widget, const char *name )
00207   : KDialogBase( widget, name, true, i18n("Address Selection"),
00208                  Ok|Cancel, Ok, true )
00209 {
00210   QVBox *page = makeVBoxMainWidget();
00211   d = new AddressesDialogPrivate;
00212   d->ui = new AddressPickerUI( page );
00213 
00214   KABC::StdAddressBook::self( true );
00215   updateAvailableAddressees();
00216   initConnections();
00217 
00218   d->ui->mAvailableView->setFocus();
00219 }
00220 
00221 AddressesDialog::~AddressesDialog()
00222 {
00223   delete d;
00224   d = 0;
00225 }
00226 
00227 AddresseeViewItem* AddressesDialog::selectedToItem()
00228 {
00229   if ( !d->toItem )
00230   {
00231     d->toItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("To"), AddresseeViewItem::To );
00232     connect(d->toItem, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00233             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00234   }
00235   return d->toItem;
00236 }
00237 
00238 AddresseeViewItem* AddressesDialog::selectedCcItem()
00239 {
00240   if ( !d->ccItem )
00241   {
00242     d->ccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("CC"), AddresseeViewItem::CC );
00243     connect(d->ccItem, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00244             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00245   }
00246   return d->ccItem;
00247 }
00248 
00249 AddresseeViewItem* AddressesDialog::selectedBccItem()
00250 {
00251   if ( !d->bccItem )
00252   {
00253     d->bccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("BCC"), AddresseeViewItem::BCC );
00254     connect(d->bccItem, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00255             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00256   }
00257   return d->bccItem;
00258 }
00259 
00260 void
00261 AddressesDialog::setSelectedTo( const QStringList& l )
00262 {
00263   QString name, email;
00264   for ( QStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
00265     KABC::Addressee addr;
00266     KABC::Addressee::parseEmailAddress( *it, name, email );
00267     addr.setNameFromString( name );
00268     addr.insertEmail( email );
00269     addAddresseeToSelected( addr, selectedToItem() );
00270   }
00271 }
00272 
00273 void
00274 AddressesDialog::setSelectedCC( const QStringList& l )
00275 {
00276   QString name, email;
00277   for ( QStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
00278     KABC::Addressee addr;
00279     KABC::Addressee::parseEmailAddress( *it, name, email );
00280     addr.setNameFromString( name );
00281     addr.insertEmail( email );
00282     addAddresseeToSelected( addr, selectedCcItem() );
00283   }
00284 }
00285 
00286 void
00287 AddressesDialog::setSelectedBCC( const QStringList& l )
00288 {
00289   QString name, email;
00290   for ( QStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
00291     KABC::Addressee addr;
00292     KABC::Addressee::parseEmailAddress( *it, name, email );
00293     addr.setNameFromString( name );
00294     addr.insertEmail( email );
00295     addAddresseeToSelected( addr, selectedBccItem() );
00296   }
00297 }
00298 
00299 void
00300 AddressesDialog::setRecentAddresses( const KABC::Addressee::List& list )
00301 {
00302   d->recentAddresses = list;
00303 
00304   updateRecentAddresses();
00305 
00306   checkForSingleAvailableGroup();
00307 }
00308 
00309 void
00310 AddressesDialog::updateRecentAddresses()
00311 {
00312   static const QString &recentGroup = KGlobal::staticQString( i18n( "Recent Addresses" ) );
00313 
00314   if ( !d->recent ) {
00315     d->recent = new AddresseeViewItem( d->ui->mAvailableView, recentGroup );
00316     connect(d->recent, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00317             this, SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
00318     d->recent->setVisible( false );
00319     d->groupDict.insert( recentGroup, d->recent );
00320   }
00321 
00322   KABC::Addressee::List::ConstIterator it;
00323   for ( it = d->recentAddresses.begin(); it != d->recentAddresses.end(); ++it )
00324     addAddresseeToAvailable( *it, d->recent );
00325 
00326   if ( d->recent->childCount() > 0 ) {
00327     d->recent->setVisible( true );
00328   }
00329 }
00330 
00331 void
00332 AddressesDialog::setShowCC( bool b )
00333 {
00334   d->ui->mCCButton->setShown( b );
00335 }
00336 
00337 void
00338 AddressesDialog::setShowBCC( bool b )
00339 {
00340   d->ui->mBCCButton->setShown( b );
00341 }
00342 
00343 QStringList
00344 AddressesDialog::to() const
00345 {
00346   QStringList emails = allDistributionLists( d->toItem );
00347   KABC::Addressee::List l = toAddresses();
00348   emails += entryToString( l );
00349 
00350   return emails;
00351 }
00352 
00353 QStringList
00354 AddressesDialog::cc() const
00355 {
00356   QStringList emails = allDistributionLists( d->ccItem );
00357   KABC::Addressee::List l = ccAddresses();
00358   emails += entryToString( l );
00359 
00360   return emails;
00361 }
00362 
00363 QStringList
00364 AddressesDialog::bcc() const
00365 {
00366   QStringList emails = allDistributionLists( d->bccItem );
00367 
00368   KABC::Addressee::List l = bccAddresses();
00369   emails += entryToString( l );
00370 
00371   return emails;
00372 }
00373 
00374 KABC::Addressee::List
00375 AddressesDialog::toAddresses()  const
00376 {
00377   return allAddressee( d->toItem );
00378 }
00379 
00380 KABC::Addressee::List
00381 AddressesDialog::allToAddressesNoDuplicates()  const
00382 {
00383   KABC::Addressee::List aList = allAddressee( d->toItem );
00384   const QStringList dList = toDistributionLists();
00385   KABC::AddressBook* abook = KABC::StdAddressBook::self( true );
00386   for ( QStringList::ConstIterator it = dList.begin(); it != dList.end(); ++it ) {
00387     QValueList<KPIM::DistributionList::Entry> eList
00388       = KPIM::DistributionList::findByName(abook, *it).entries(abook);
00389     QValueList<KPIM::DistributionList::Entry>::Iterator eit;
00390     if ( eList.count() > 0 )
00391       for( eit = eList.begin(); eit != eList.end(); ++eit ) {
00392         KABC::Addressee a = (*eit).addressee;
00393         bool found = false;
00394          for ( KABC::Addressee::List::iterator itr = aList.begin();
00395               itr != aList.end(); ++itr ) {
00396             KABC::Addressee ad = (*itr);
00397             if ( ad == a ) {
00398               found = true;
00399               break;
00400             }
00401         }
00402          if ( !found ) {
00403            if ( ! a.preferredEmail().isEmpty () )
00404              aList.append( a ) ;
00405          }
00406       }
00407   }
00408   return aList;
00409 }
00410 
00411 KABC::Addressee::List
00412 AddressesDialog::ccAddresses()  const
00413 {
00414   return allAddressee( d->ccItem );
00415 }
00416 
00417 KABC::Addressee::List
00418 AddressesDialog::bccAddresses()  const
00419 {
00420   return allAddressee( d->bccItem );
00421 }
00422 
00423 
00424 QStringList
00425 AddressesDialog::toDistributionLists() const
00426 {
00427   return allDistributionLists( d->toItem );
00428 }
00429 
00430 QStringList
00431 AddressesDialog::ccDistributionLists() const
00432 {
00433   return allDistributionLists( d->ccItem );
00434 }
00435 
00436 QStringList
00437 AddressesDialog::bccDistributionLists() const
00438 {
00439   return allDistributionLists( d->bccItem );
00440 }
00441 
00442 void
00443 AddressesDialog::updateAvailableAddressees()
00444 {
00445   d->ui->mAvailableView->clear();
00446   d->groupDict.clear();
00447 
00448   static const QString &personalGroup = KGlobal::staticQString( i18n( "Other Addresses" ) );
00449   d->ui->mAvailableView->setRootIsDecorated( true );
00450   d->personal = new AddresseeViewItem( d->ui->mAvailableView, personalGroup );
00451   //connect(d->personal, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00452   //        this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00453   d->personal->setVisible( false );
00454   d->groupDict.insert( personalGroup, d->personal );
00455 
00456   KABC::AddressBook *addressBook = KABC::StdAddressBook::self( true );
00457   for( KABC::AddressBook::Iterator it = addressBook->begin();
00458        it != addressBook->end(); ++it ) {
00459     addAddresseeToAvailable( *it, d->personal );
00460   }
00461 
00462   d->recent = 0;
00463   updateRecentAddresses();
00464 
00465   addDistributionLists();
00466   if ( d->personal->childCount() > 0 ) {
00467     d->personal->setVisible( true );
00468   }
00469 
00470   checkForSingleAvailableGroup();
00471 }
00472 
00473 void AddressesDialog::checkForSingleAvailableGroup()
00474 {
00475   QListViewItem* item = d->ui->mAvailableView->firstChild();
00476   QListViewItem* firstGroup = 0;
00477   int found = 0;
00478   while (item)
00479   {
00480     if (item->isVisible())
00481     {
00482       if (!firstGroup && static_cast<AddresseeViewItem*>(item)->category() != AddresseeViewItem::Entry)
00483       {
00484         firstGroup = item;
00485       }
00486       ++found;
00487     }
00488     item = item->nextSibling();
00489   }
00490 
00491   if (found == 1 && firstGroup)
00492   {
00493     firstGroup->setOpen(true);
00494   }
00495 }
00496 
00497 void
00498 AddressesDialog::availableSelectionChanged()
00499 {
00500   bool selection = !selectedAvailableAddresses.isEmpty();
00501   d->ui->mToButton->setEnabled(selection);
00502   d->ui->mCCButton->setEnabled(selection);
00503   d->ui->mBCCButton->setEnabled(selection);
00504 }
00505 
00506 void
00507 AddressesDialog::selectedSelectionChanged()
00508 {
00509   bool selection = !selectedSelectedAddresses.isEmpty();
00510   d->ui->mRemoveButton->setEnabled(selection);
00511 }
00512 
00513 void
00514 AddressesDialog::availableAddressSelected( AddresseeViewItem* item, bool selected )
00515 {
00516   if (selected)
00517   {
00518     selectedAvailableAddresses.append(item);
00519   }
00520   else
00521   {
00522     selectedAvailableAddresses.remove(item);
00523   }
00524 }
00525 
00526 void
00527 AddressesDialog::selectedAddressSelected( AddresseeViewItem* item, bool selected )
00528 {
00529   // we have to avoid that a parent and a child is selected together
00530   // because in this case we get a double object deletion ( program crashes )
00531   // when removing the selected items from list
00532   AddresseeViewItem* parent = static_cast<AddresseeViewItem*>(((QListViewItem*)item)->parent());
00533   if ( parent  && selected )
00534     parent->setSelected( false );
00535   if (selected)
00536   {
00537     selectedSelectedAddresses.append(item);
00538   }
00539   else
00540   {
00541     selectedSelectedAddresses.remove(item);
00542   }
00543   if ( selected ) {
00544     AddresseeViewItem* child = static_cast<AddresseeViewItem*>(item->firstChild());
00545     while (child) {
00546       child->setSelected( false );
00547       child = static_cast<AddresseeViewItem*>(child->nextSibling());
00548     }
00549   }
00550 }
00551 
00552 void
00553 AddressesDialog::initConnections()
00554 {
00555   connect( d->ui->mFilterEdit, SIGNAL(textChanged(const QString &)),
00556            SLOT(filterChanged(const QString &)) );
00557   connect( d->ui->mToButton, SIGNAL(clicked()),
00558            SLOT(addSelectedTo()) );
00559   connect( d->ui->mCCButton, SIGNAL(clicked()),
00560            SLOT(addSelectedCC()) );
00561   connect( d->ui->mBCCButton, SIGNAL(clicked()),
00562            SLOT(addSelectedBCC())  );
00563   connect( d->ui->mSaveAs, SIGNAL(clicked()),
00564            SLOT(saveAs())  );
00565   connect( d->ui->mLdapSearch, SIGNAL(clicked()),
00566            SLOT(searchLdap())  );
00567   connect( d->ui->mRemoveButton, SIGNAL(clicked()),
00568            SLOT(removeEntry()) );
00569   connect( d->ui->mAvailableView, SIGNAL(selectionChanged()),
00570            SLOT(availableSelectionChanged())  );
00571   connect( d->ui->mAvailableView, SIGNAL(doubleClicked(QListViewItem*)),
00572            SLOT(addSelectedTo()) );
00573   connect( d->ui->mSelectedView, SIGNAL(selectionChanged()),
00574            SLOT(selectedSelectionChanged()) );
00575   connect( d->ui->mSelectedView, SIGNAL(doubleClicked(QListViewItem*)),
00576            SLOT(removeEntry()) );
00577 
00578   //connect( KABC::DistributionListWatcher::self(), SIGNAL( changed() ),
00579   //         this, SLOT( updateAvailableAddressees() ) );
00580 
00581   connect( KABC::StdAddressBook::self(), SIGNAL( addressBookChanged(AddressBook*) ),
00582            this, SLOT( updateAvailableAddressees() ) );
00583 }
00584 
00585 void
00586 AddressesDialog::addAddresseeToAvailable( const KABC::Addressee& addr, AddresseeViewItem* defaultParent, bool useCategory )
00587 {
00588   if ( addr.preferredEmail().isEmpty() )
00589     return;
00590 
00591   if ( useCategory ) {
00592     QStringList categories = addr.categories();
00593 
00594     for ( QStringList::Iterator it = categories.begin(); it != categories.end(); ++it ) {
00595       if ( !d->groupDict[ *it ] ) {  //we don't have the category yet
00596         AddresseeViewItem* category = new AddresseeViewItem( d->ui->mAvailableView, *it );
00597         d->groupDict.insert( *it,  category );
00598       }
00599 
00600       for ( uint i = 0; i < addr.emails().count(); ++i ) {
00601         AddresseeViewItem* addressee = new AddresseeViewItem( d->groupDict[ *it ], addr, i );
00602         connect(addressee, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00603                 this, SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
00604       }
00605     }
00606   }
00607 
00608   bool noCategory = false;
00609   if ( useCategory ) {
00610     if ( addr.categories().isEmpty() )
00611       noCategory = true;
00612   } else
00613     noCategory = true;
00614 
00615   if ( defaultParent && noCategory ) { // only non-categorized items here
00616     AddresseeViewItem* addressee = new AddresseeViewItem( defaultParent, addr );
00617     connect(addressee, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00618             this, SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
00619   }
00620 }
00621 
00622 void
00623 AddressesDialog::addAddresseeToSelected( const KABC::Addressee& addr, AddresseeViewItem* defaultParent )
00624 {
00625   if ( addr.preferredEmail().isEmpty() )
00626     return;
00627 
00628   if ( defaultParent ) {
00629     AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( defaultParent->firstChild() );
00630     while( myChild ) {
00631       if ( myChild->addressee().preferredEmail() == addr.preferredEmail() )
00632         return;//already got it
00633       myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
00634     }
00635     AddresseeViewItem* addressee = new AddresseeViewItem( defaultParent, addr );
00636     connect(addressee, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00637             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00638     defaultParent->setOpen( true );
00639   }
00640 
00641   d->ui->mSaveAs->setEnabled(true);
00642 }
00643 
00644 void
00645 AddressesDialog::addAddresseesToSelected( AddresseeViewItem *parent,
00646                                           const QPtrList<AddresseeViewItem>& addresses )
00647 {
00648   Q_ASSERT( parent );
00649 
00650   QPtrListIterator<AddresseeViewItem> itr( addresses );
00651 
00652   if (itr.current())
00653   {
00654     d->ui->mSaveAs->setEnabled(true);
00655   }
00656 
00657   while ( itr.current() ) {
00658     AddresseeViewItem* address = itr.current();
00659     ++itr;
00660 
00661     if (selectedToAvailableMapping.find(address) != 0)
00662     {
00663       continue;
00664     }
00665 
00666     AddresseeViewItem* newItem = 0;
00667     if (address->category() == AddresseeViewItem::Entry)
00668     {
00669       newItem = new AddresseeViewItem( parent, address->addressee() );
00670     }
00671     else if (address->category() == AddresseeViewItem::DistList)
00672     {
00673       newItem = new AddresseeViewItem( parent, address->name() );
00674     }
00675     else
00676     {
00677       newItem = new AddresseeViewItem( parent, address->name(), allAddressee( address ) );
00678     }
00679 
00680     address->setSelected( false );
00681     address->setVisible( false );
00682     selectedToAvailableMapping.insert(address, newItem);
00683     selectedToAvailableMapping.insert(newItem, address);
00684     connect(newItem, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00685             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00686   }
00687 
00688   parent->setOpen( true );
00689 }
00690 
00691 QStringList
00692 AddressesDialog::entryToString( const KABC::Addressee::List& l ) const
00693 {
00694   QStringList entries;
00695 
00696   for( KABC::Addressee::List::ConstIterator it = l.begin(); it != l.end(); ++it ) {
00697     entries += (*it).fullEmail();
00698   }
00699   return entries;
00700 }
00701 
00702 void
00703 AddressesDialog::addSelectedTo()
00704 {
00705   if ( !d->toItem )
00706   {
00707     d->toItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("To"), AddresseeViewItem::To );
00708     connect(d->toItem, SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00709             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00710   }
00711 
00712   addAddresseesToSelected( d->toItem, selectedAvailableAddresses );
00713   selectedAvailableAddresses.clear();
00714 
00715   if ( d->toItem->childCount() > 0 )
00716     d->toItem->setVisible( true );
00717   else
00718   {
00719     delete d->toItem;
00720     d->toItem = 0;
00721   }
00722 }
00723 
00724 void
00725 AddressesDialog::addSelectedCC()
00726 {
00727   if ( !d->ccItem )
00728   {
00729     d->ccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("CC"), AddresseeViewItem::CC );
00730     connect(d->ccItem , SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00731             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00732   }
00733 
00734   addAddresseesToSelected( d->ccItem, selectedAvailableAddresses );
00735   selectedAvailableAddresses.clear();
00736 
00737   if ( d->ccItem->childCount() > 0 )
00738     d->ccItem->setVisible( true );
00739   else
00740   {
00741     delete d->ccItem;
00742     d->ccItem = 0;
00743   }
00744 }
00745 
00746 void
00747 AddressesDialog::addSelectedBCC()
00748 {
00749   if ( !d->bccItem )
00750   {
00751     d->bccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("BCC"), AddresseeViewItem::BCC );
00752     connect(d->bccItem , SIGNAL(addressSelected(AddresseeViewItem*, bool)),
00753             this, SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
00754   }
00755 
00756   addAddresseesToSelected( d->bccItem, selectedAvailableAddresses );
00757   selectedAvailableAddresses.clear();
00758 
00759   if ( d->bccItem->childCount() > 0 )
00760     d->bccItem->setVisible( true );
00761   else
00762   {
00763     delete d->bccItem;
00764     d->bccItem = 0;
00765   }
00766 }
00767 
00768 void AddressesDialog::unmapSelectedAddress(AddresseeViewItem* item)
00769 {
00770   AddresseeViewItem* correspondingItem = selectedToAvailableMapping[item];
00771   if (correspondingItem)
00772   {
00773     correspondingItem->setVisible( true );
00774     selectedToAvailableMapping.remove( item );
00775     selectedToAvailableMapping.remove( correspondingItem );
00776   }
00777 
00778   AddresseeViewItem* child = static_cast<AddresseeViewItem*>(item->firstChild());
00779   while (child)
00780   {
00781     unmapSelectedAddress(child);
00782     child = static_cast<AddresseeViewItem*>(child->nextSibling());
00783   }
00784 }
00785 
00786 void
00787 AddressesDialog::removeEntry()
00788 {
00789   QPtrList<AddresseeViewItem> lst;
00790   bool resetTo  = false;
00791   bool resetCC  = false;
00792   bool resetBCC = false;
00793 
00794   lst.setAutoDelete( false );
00795   QPtrListIterator<AddresseeViewItem> it( selectedSelectedAddresses );
00796   while ( it.current() ) {
00797     AddresseeViewItem* item = it.current();
00798     ++it;
00799     if ( d->toItem == item )
00800       resetTo = true;
00801     else if ( d->ccItem == item )
00802       resetCC = true;
00803     else if( d->bccItem == item )
00804       resetBCC = true;
00805     // we may only append parent items
00806     unmapSelectedAddress(item);
00807     lst.append( item );
00808   }
00809   selectedSelectedAddresses.clear();
00810   lst.setAutoDelete( true );
00811   lst.clear();
00812   if ( resetTo )
00813     d->toItem  = 0;
00814   else if ( d->toItem && d->toItem->childCount() == 0 )
00815   {
00816     delete d->toItem;
00817     d->toItem = 0;
00818   }
00819   if ( resetCC )
00820     d->ccItem = 0;
00821   else if ( d->ccItem && d->ccItem->childCount() == 0 )
00822   {
00823     delete d->ccItem;
00824     d->ccItem = 0;
00825   }
00826   if ( resetBCC )
00827     d->bccItem  = 0;
00828   else if ( d->bccItem && d->bccItem->childCount() == 0 )
00829   {
00830     delete d->bccItem;
00831     d->bccItem = 0;
00832   }
00833   d->ui->mSaveAs->setEnabled(d->ui->mSelectedView->firstChild() != 0);
00834 }
00835 
00836 // copied from kabcore.cpp :(
00837 static KABC::Resource *requestResource( KABC::AddressBook* abook, QWidget *parent )
00838 {
00839   QPtrList<KABC::Resource> kabcResources = abook->resources();
00840 
00841   QPtrList<KRES::Resource> kresResources;
00842   QPtrListIterator<KABC::Resource> resIt( kabcResources );
00843   KABC::Resource *resource;
00844   while ( ( resource = resIt.current() ) != 0 ) {
00845     ++resIt;
00846     if ( !resource->readOnly() ) {
00847       KRES::Resource *res = static_cast<KRES::Resource*>( resource );
00848       if ( res )
00849         kresResources.append( res );
00850     }
00851   }
00852 
00853   KRES::Resource *res = KRES::SelectDialog::getResource( kresResources, parent );
00854   return static_cast<KABC::Resource*>( res );
00855 }
00856 
00857 void
00858 AddressesDialog::saveAs()
00859 {
00860   if ( !d->ui->mSelectedView->firstChild() ) {
00861     KMessageBox::information( 0,
00862                               i18n("There are no addresses in your list. "
00863                                    "First add some addresses from your address book, "
00864                                    "then try again.") );
00865     return;
00866   }
00867 
00868   bool ok = false;
00869   QString name = KInputDialog::getText( i18n("New Distribution List"),
00870                                         i18n("Please enter name:"),
00871                                         QString::null, &ok,
00872                                         this );
00873   if ( !ok || name.isEmpty() )
00874     return;
00875 
00876   KABC::AddressBook* abook = KABC::StdAddressBook::self( true );
00877   KPIM::DistributionList dlist = KPIM::DistributionList::findByName( abook, name );
00878 
00879   if ( !dlist.isEmpty() ) {
00880     KMessageBox::information( 0,
00881                               i18n( "<qt>Distribution list with the given name <b>%1</b> "
00882                                     "already exists. Please select a different name.</qt>" )
00883                               .arg( name ) );
00884     return;
00885   }
00886 
00887   KABC::Resource* resource = requestResource( abook, this );
00888   if ( !resource )
00889     return;
00890 
00891   dlist.setResource( resource );
00892   dlist.setName( name );
00893   KABC::Addressee::List addrl = allAddressee( d->ui->mSelectedView, false );
00894   for ( KABC::Addressee::List::iterator itr = addrl.begin();
00895         itr != addrl.end(); ++itr ) {
00896     dlist.insertEntry( *itr );
00897   }
00898 
00899   abook->insertAddressee( dlist );
00900 }
00901 
00902 void
00903 AddressesDialog::searchLdap()
00904 {
00905     if ( !d->ldapSearchDialog ) {
00906       d->ldapSearchDialog = new LDAPSearchDialog( this );
00907       connect( d->ldapSearchDialog, SIGNAL( addresseesAdded() ),
00908                SLOT(ldapSearchResult() ) );
00909     }
00910     d->ldapSearchDialog->show();
00911 }
00912 
00913 void
00914 AddressesDialog::ldapSearchResult()
00915 {
00916   QStringList emails = QStringList::split(',', d->ldapSearchDialog->selectedEMails() );
00917   QStringList::iterator it( emails.begin() );
00918   QStringList::iterator end( emails.end() );
00919   for ( ; it != end; ++it ){
00920       QString name;
00921       QString email;
00922       KPIM::getNameAndMail( (*it), name, email );
00923       KABC::Addressee ad;
00924       ad.setNameFromString( name );
00925       ad.insertEmail( email );
00926       addAddresseeToSelected( ad, selectedToItem() );
00927   }
00928 }
00929 
00930 void
00931 AddressesDialog::launchAddressBook()
00932 {
00933   kapp->startServiceByDesktopName( "kaddressbook", QString() );
00934 }
00935 
00936 void
00937 AddressesDialog::filterChanged( const QString& txt )
00938 {
00939   QListViewItemIterator it( d->ui->mAvailableView );
00940   bool showAll = false;
00941 
00942   if ( txt.isEmpty() )
00943     showAll = true;
00944 
00945   while ( it.current() ) {
00946     AddresseeViewItem* item = static_cast<AddresseeViewItem*>( it.current() );
00947     ++it;
00948     if ( showAll ) {
00949       item->setVisible( true );
00950       if ( item->category() == AddresseeViewItem::Group )
00951         item->setOpen( false );//close to not have too many entries
00952       continue;
00953     }
00954     if ( item->category() == AddresseeViewItem::Entry ) {
00955       bool matches = item->matches( txt ) ;
00956       item->setVisible( matches );
00957       if ( matches && static_cast<QListViewItem*>(item)->parent() ) {
00958           static_cast<QListViewItem*>(item)->parent()->setOpen( true );//open the parents with found entries
00959       }
00960     }
00961   }
00962 }
00963 
00964 KABC::Addressee::List
00965 AddressesDialog::allAddressee( KListView* view, bool onlySelected ) const
00966 {
00967   KABC::Addressee::List lst;
00968   QListViewItemIterator it( view );
00969   while ( it.current() ) {
00970     AddresseeViewItem* item = static_cast<AddresseeViewItem*>( it.current() );
00971     if ( !onlySelected || item->isSelected() ) {
00972       if ( item->category() != AddresseeViewItem::Entry  ) {
00973         AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( item->firstChild() );
00974         while( myChild ) {
00975           lst.append( myChild->addressee() );
00976           myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
00977         }
00978       } else {
00979         lst.append( item->addressee() );
00980       }
00981     }
00982     ++it;
00983   }
00984 
00985   return lst;
00986 }
00987 
00988 KABC::Addressee::List
00989 AddressesDialog::allAddressee( AddresseeViewItem* parent ) const
00990 {
00991   KABC::Addressee::List lst;
00992 
00993   if ( !parent ) return lst;
00994 
00995   if ( parent->category() == AddresseeViewItem::Entry )
00996   {
00997     lst.append( parent->addressee() );
00998     return lst;
00999   }
01000 
01001   AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( parent->firstChild() );
01002   while( myChild ) {
01003     if ( myChild->category() == AddresseeViewItem::FilledGroup )
01004       lst += myChild->addresses();
01005     else if ( !myChild->addressee().isEmpty() )
01006       lst.append( myChild->addressee() );
01007     myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
01008   }
01009 
01010   return lst;
01011 }
01012 
01013 QStringList
01014 AddressesDialog::allDistributionLists( AddresseeViewItem* parent ) const
01015 {
01016   QStringList lists;
01017 
01018   if ( !parent )
01019     return QStringList();
01020 
01021   AddresseeViewItem *item = static_cast<AddresseeViewItem*>( parent->firstChild() );
01022   while ( item ) {
01023     if ( item->category() == AddresseeViewItem::DistList && !item->name().isEmpty() )
01024       lists.append( item->name() );
01025 
01026     item = static_cast<AddresseeViewItem*>( item->nextSibling() );
01027   }
01028 
01029   return lists;
01030 }
01031 
01032 void
01033 AddressesDialog::addDistributionLists()
01034 {
01035   KABC::AddressBook* abook = KABC::StdAddressBook::self( true );
01036   const QValueList<KPIM::DistributionList> distLists =
01037     KPIM::DistributionList::allDistributionLists( abook );
01038 
01039   if ( distLists.isEmpty() )
01040     return;
01041 
01042   AddresseeViewItem *topItem = new AddresseeViewItem( d->ui->mAvailableView,
01043                                                       i18n( "Distribution Lists" ) );
01044 
01045   QValueList<KPIM::DistributionList>::ConstIterator listIt;
01046   for ( listIt = distLists.begin(); listIt != distLists.end(); ++listIt ) {
01047     KPIM::DistributionList dlist = *listIt;
01048     KPIM::DistributionList::Entry::List entries = dlist.entries(abook);
01049 
01050     AddresseeViewItem *item = new AddresseeViewItem( topItem, dlist.name() );
01051     connect( item, SIGNAL( addressSelected( AddresseeViewItem*, bool ) ),
01052              this, SLOT( availableAddressSelected( AddresseeViewItem*, bool ) ) );
01053 
01054     KPIM::DistributionList::Entry::List::Iterator itemIt;
01055     for ( itemIt = entries.begin(); itemIt != entries.end(); ++itemIt )
01056       addAddresseeToAvailable( (*itemIt).addressee, item, false );
01057   }
01058 }
01059 
01060 }
01061 
01062 #include "addressesdialog.moc"
KDE Logo
This file is part of the documentation for libkdepim Library Version 3.3.2.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Wed Jan 31 15:53:22 2007 by doxygen 1.4.2 written by Dimitri van Heesch, © 1997-2003