libtdepim

addressesdialog.cpp
1/*
2 *
3 * This file is part of libtdepim.
4 *
5 * Copyright (c) 2003 Zack Rusin <zack@kde.org>
6 * Copyright (c) 2003 Aaron J. Seigo <aseigo@kde.org>
7 *
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Library General Public
10 * License as published by the Free Software Foundation; either
11 * version 2 of the License, or (at your option) any later version.
12 *
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Library General Public License for more details.
17 *
18 * You should have received a copy of the GNU Library General Public License
19 * along with this library; see the file COPYING.LIB. If not, write to
20 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 * Boston, MA 02110-1301, USA.
22 *
23 */
24
25#include "addressesdialog.h"
26#include "addresspicker.h"
27#include "ldapsearchdialog.h"
28
29#include <config.h>
30
31#include <libemailfunctions/email.h>
32
33#ifdef TDEPIM_NEW_DISTRLISTS
34#include "distributionlist.h"
35#include <tderesources/selectdialog.h>
36#include <tdeabc/resource.h>
37#else
38#include <tdeabc/distributionlist.h>
39#endif
40
41#include <tdeabc/stdaddressbook.h>
42#include <tdeapplication.h>
43#include <kdebug.h>
44#include <tdeglobal.h>
45#include <kiconloader.h>
46#include <kinputdialog.h>
47#include <klineedit.h>
48#include <tdelocale.h>
49#include <tdemessagebox.h>
50#include <tdeprocess.h>
51#include <kpushbutton.h>
52#include <krun.h>
53#include <tdestandarddirs.h>
54
55#include <tqdict.h>
56#include <tqlayout.h>
57#include <tqvbox.h>
58#include <tqwidget.h>
59
60namespace KPIM {
61
62// private start :
63struct AddresseeViewItem::AddresseeViewItemPrivate {
64 TDEABC::Addressee address;
65 AddresseeViewItem::Category category;
66 TDEABC::Addressee::List addresses;
67};
68
69struct AddressesDialog::AddressesDialogPrivate {
70 AddressesDialogPrivate() :
71 ui(0), personal(0), recent(0),
72 toItem(0), ccItem(0), bccItem(0),
73 ldapSearchDialog(0)
74 {}
75
76 AddressPickerUI *ui;
77
78 AddresseeViewItem *personal;
79 AddresseeViewItem *recent;
80 AddresseeViewItem *topdist;
81 TQPtrList<AddresseeViewItem> dists;
82
83 AddresseeViewItem *toItem;
84 AddresseeViewItem *ccItem;
85 AddresseeViewItem *bccItem;
86
87 TQDict<AddresseeViewItem> groupDict;
88
89 TDEABC::Addressee::List recentAddresses;
90 LDAPSearchDialog *ldapSearchDialog;
91};
92// privates end
93
94AddresseeViewItem::AddresseeViewItem( AddresseeViewItem *parent, const TDEABC::Addressee& addr,
95 int emailIndex )
96 : TQObject( 0 ), TDEListViewItem( parent, addr.realName(),
97 ( emailIndex == 0 ? addr.preferredEmail() : addr.emails()[ emailIndex ] ) )
98{
99 d = new AddresseeViewItemPrivate;
100 d->address = addr;
101 d->category = Entry;
102
103 if ( text( 0 ).stripWhiteSpace().isEmpty() )
104 setText( 0, addr.preferredEmail() );
105
106 if ( addr.photo().url().isEmpty() ) {
107 if ( addr.photo().data().isNull() )
108 setPixmap( 0, TDEGlobal::iconLoader()->loadIcon( "preferences-desktop-personal", TDEIcon::Small ) );
109 else
110 setPixmap( 0, addr.photo().data().smoothScale( 16, 16 ) );
111 } else {
112 setPixmap( 0, TDEGlobal::iconLoader()->loadIcon( addr.photo().url(), TDEIcon::Small ) );
113 }
114}
115
116AddresseeViewItem::AddresseeViewItem( TDEListView *lv, const TQString& name, Category cat )
117 : TQObject(0), TDEListViewItem( lv, name )
118{
119 d = new AddresseeViewItemPrivate;
120 d->category = cat;
121}
122
123AddresseeViewItem::AddresseeViewItem( AddresseeViewItem *parent, const TQString& name,
124 const TDEABC::Addressee::List &lst )
125 : TQObject(0), TDEListViewItem( parent, name, i18n("<group>") )
126{
127 d = new AddresseeViewItemPrivate;
128 d->category = FilledGroup;
129 d->addresses = lst;
130}
131
132AddresseeViewItem::AddresseeViewItem( AddresseeViewItem *parent, const TQString& name )
133 : TQObject(0), TDEListViewItem( parent, name, i18n("<group>") )
134{
135 d = new AddresseeViewItemPrivate;
136 d->category = DistList;
137
138 setPixmap( 0, TDEGlobal::iconLoader()->loadIcon( "tdmconfig", TDEIcon::Small ) );
139}
140
141AddresseeViewItem::~AddresseeViewItem()
142{
143 delete d;
144 d = 0;
145}
146
147TDEABC::Addressee
148AddresseeViewItem::addressee() const
149{
150 return d->address;
151}
152
153TDEABC::Addressee::List
154AddresseeViewItem::addresses() const
155{
156 return d->addresses;
157}
158
159AddresseeViewItem::Category
160AddresseeViewItem::category() const
161{
162 return d->category;
163}
164
165TQString
166AddresseeViewItem::name() const
167{
168 return text(0);
169}
170
171TQString
172AddresseeViewItem::email() const
173{
174 return text(1);
175}
176
177bool AddresseeViewItem::matches(const TQString& txt) const
178{
179 return d->address.realName().contains(txt, false) || d->address.preferredEmail().contains(txt, false);
180}
181
182void AddresseeViewItem::setSelected(bool selected)
183{
184 if (selected == isSelected())
185 {
186 return;
187 }
188
189 emit addressSelected( this, selected );
190 TQListViewItem::setSelected(selected);
191}
192
193int
194AddresseeViewItem::compare( TQListViewItem * i, int col, bool ascending ) const
195{
196 if ( category() == Group || category() == Entry )
197 return TDEListViewItem::compare( i , col, ascending );
198
199 AddresseeViewItem *item = static_cast<AddresseeViewItem*>( i );
200 int a = static_cast<int>( category() );
201 int b = static_cast<int>( item->category() );
202
203 if ( ascending )
204 if ( a < b )
205 return -1;
206 else
207 return 1;
208 else
209 if ( a < b )
210 return 1;
211 else
212 return -1;
213}
214
215AddressesDialog::AddressesDialog( TQWidget *widget, const char *name )
216 : KDialogBase( widget, name, true, i18n("Address Selection"),
217 Ok|Cancel, Ok, true )
218{
219 TQVBox *page = makeVBoxMainWidget();
220 d = new AddressesDialogPrivate;
221 d->ui = new AddressPickerUI( page );
222
223 TDEABC::StdAddressBook::self( true );
224 updateAvailableAddressees();
225 initConnections();
226
227 d->ui->mAvailableView->setFocus();
228
229 setMainWidget( page );
230 page->setMinimumSize( 750, 400 );
231}
232
233AddressesDialog::~AddressesDialog()
234{
235 delete d;
236 d = 0;
237}
238
239AddresseeViewItem* AddressesDialog::selectedToItem()
240{
241 if ( !d->toItem )
242 {
243 d->toItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("To"), AddresseeViewItem::To );
244 connect(d->toItem, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
245 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
246 }
247 return d->toItem;
248}
249
250AddresseeViewItem* AddressesDialog::selectedCcItem()
251{
252 if ( !d->ccItem )
253 {
254 d->ccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("CC"), AddresseeViewItem::CC );
255 connect(d->ccItem, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
256 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
257 }
258 return d->ccItem;
259}
260
261AddresseeViewItem* AddressesDialog::selectedBccItem()
262{
263 if ( !d->bccItem )
264 {
265 d->bccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("BCC"), AddresseeViewItem::BCC );
266 connect(d->bccItem, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
267 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
268 }
269 return d->bccItem;
270}
271
272void
273AddressesDialog::setSelectedTo( const TQStringList& l )
274{
275 TQString name, email;
276 for ( TQStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
277 TDEABC::Addressee addr;
278 TDEABC::Addressee::parseEmailAddress( *it, name, email );
279 addr.setNameFromString( name );
280 addr.insertEmail( email );
281 addAddresseeToSelected( addr, selectedToItem() );
282 }
283}
284
285void
286AddressesDialog::setSelectedCC( const TQStringList& l )
287{
288 TQString name, email;
289 for ( TQStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
290 TDEABC::Addressee addr;
291 TDEABC::Addressee::parseEmailAddress( *it, name, email );
292 addr.setNameFromString( name );
293 addr.insertEmail( email );
294 addAddresseeToSelected( addr, selectedCcItem() );
295 }
296}
297
298void
299AddressesDialog::setSelectedBCC( const TQStringList& l )
300{
301 TQString name, email;
302 for ( TQStringList::ConstIterator it = l.begin(); it != l.end(); ++it ) {
303 TDEABC::Addressee addr;
304 TDEABC::Addressee::parseEmailAddress( *it, name, email );
305 addr.setNameFromString( name );
306 addr.insertEmail( email );
307 addAddresseeToSelected( addr, selectedBccItem() );
308 }
309}
310
311void
312AddressesDialog::setRecentAddresses( const TDEABC::Addressee::List& list )
313{
314 d->recentAddresses = list;
315
316 updateRecentAddresses();
317
318 checkForSingleAvailableGroup();
319}
320
321void
322AddressesDialog::updateRecentAddresses()
323{
324 static const TQString &recentGroup = TDEGlobal::staticQString( i18n( "Recent Addresses" ) );
325
326 if ( !d->recent ) {
327 d->recent = new AddresseeViewItem( d->ui->mAvailableView, recentGroup );
328 connect(d->recent, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
329 this, TQ_SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
330 d->recent->setVisible( false );
331 d->groupDict.insert( recentGroup, d->recent );
332 }
333
334 TDEABC::Addressee::List::ConstIterator it;
335 for ( it = d->recentAddresses.begin(); it != d->recentAddresses.end(); ++it )
336 addAddresseeToAvailable( *it, d->recent );
337
338 if ( d->recent->childCount() > 0 ) {
339 d->recent->setOpen( true );
340 d->recent->setVisible( true );
341 }
342}
343
344void
345AddressesDialog::setShowCC( bool b )
346{
347 d->ui->mCCButton->setShown( b );
348}
349
350void
351AddressesDialog::setShowBCC( bool b )
352{
353 d->ui->mBCCButton->setShown( b );
354}
355
356TQStringList
357AddressesDialog::to() const
358{
359 TQStringList emails = allDistributionLists( d->toItem );
360 TDEABC::Addressee::List l = toAddresses();
361 emails += entryToString( l );
362
363 return emails;
364}
365
366TQStringList
367AddressesDialog::cc() const
368{
369 TQStringList emails = allDistributionLists( d->ccItem );
370 TDEABC::Addressee::List l = ccAddresses();
371 emails += entryToString( l );
372
373 return emails;
374}
375
376TQStringList
377AddressesDialog::bcc() const
378{
379 TQStringList emails = allDistributionLists( d->bccItem );
380
381 TDEABC::Addressee::List l = bccAddresses();
382 emails += entryToString( l );
383
384 return emails;
385}
386
387TDEABC::Addressee::List
388AddressesDialog::toAddresses() const
389{
390 return allAddressee( d->toItem );
391}
392TDEABC::Addressee::List
393AddressesDialog::allToAddressesNoDuplicates() const
394{
395 TDEABC::Addressee::List aList = allAddressee( d->toItem );
396 const TQStringList dList = toDistributionLists();
397 TDEABC::AddressBook* abook = TDEABC::StdAddressBook::self( true );
398#ifdef TDEPIM_NEW_DISTRLISTS
399 for ( TQStringList::ConstIterator it = dList.begin(); it != dList.end(); ++it ) {
400 const TQValueList<KPIM::DistributionList::Entry> eList
401 = KPIM::DistributionList::findByName(abook, *it).entries(abook);
402 TQValueList<KPIM::DistributionList::Entry>::ConstIterator eit;
403 for( eit = eList.begin(); eit != eList.end(); ++eit ) {
404 TDEABC::Addressee a = (*eit).addressee;
405 if ( !a.preferredEmail().isEmpty() && aList.find( a ) == aList.end() ) {
406 aList.append( a ) ;
407 }
408 }
409 }
410#else
411 TDEABC::DistributionListManager manager( abook );
412 manager.load();
413 for ( TQStringList::ConstIterator it = dList.begin(); it != dList.end(); ++it ) {
414 const TQValueList<TDEABC::DistributionList::Entry> eList = manager.list( *it )->entries();
415 TQValueList<TDEABC::DistributionList::Entry>::ConstIterator eit;
416 for( eit = eList.begin(); eit != eList.end(); ++eit ) {
417 TDEABC::Addressee a = (*eit).addressee;
418 if ( !a.preferredEmail().isEmpty() && aList.find( a ) == aList.end() ) {
419 aList.append( a ) ;
420 }
421 }
422 }
423#endif
424 return aList;
425}
426
427TDEABC::Addressee::List
428AddressesDialog::ccAddresses() const
429{
430 return allAddressee( d->ccItem );
431}
432
433TDEABC::Addressee::List
434AddressesDialog::bccAddresses() const
435{
436 return allAddressee( d->bccItem );
437}
438
439
440TQStringList
441AddressesDialog::toDistributionLists() const
442{
443 return allDistributionLists( d->toItem );
444}
445
446TQStringList
447AddressesDialog::ccDistributionLists() const
448{
449 return allDistributionLists( d->ccItem );
450}
451
452TQStringList
453AddressesDialog::bccDistributionLists() const
454{
455 return allDistributionLists( d->bccItem );
456}
457
458void
459AddressesDialog::updateAvailableAddressees()
460{
461 d->ui->mAvailableView->clear();
462 d->groupDict.clear();
463
464 static const TQString &personalGroup = TDEGlobal::staticQString( i18n( "Other Addresses" ) );
465 d->ui->mAvailableView->setRootIsDecorated( true );
466 d->personal = new AddresseeViewItem( d->ui->mAvailableView, personalGroup );
467 //connect(d->personal, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
468 // this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
469 d->personal->setVisible( false );
470 d->groupDict.insert( personalGroup, d->personal );
471
472 TDEABC::AddressBook *addressBook = TDEABC::StdAddressBook::self( true );
473 for( TDEABC::AddressBook::Iterator it = addressBook->begin();
474 it != addressBook->end(); ++it ) {
475 addAddresseeToAvailable( *it, d->personal );
476 }
477
478 d->recent = 0;
479 updateRecentAddresses();
480
481 d->topdist = 0;
482 addDistributionLists();
483 if ( d->personal->childCount() > 0 ) {
484 d->personal->setOpen( true );
485 d->personal->setVisible( true );
486 }
487
488 checkForSingleAvailableGroup();
489}
490
491void AddressesDialog::checkForSingleAvailableGroup()
492{
493 TQListViewItem* item = d->ui->mAvailableView->firstChild();
494 TQListViewItem* firstGroup = 0;
495 int found = 0;
496 while (item)
497 {
498 if (item->isVisible())
499 {
500 if (!firstGroup && static_cast<AddresseeViewItem*>(item)->category() != AddresseeViewItem::Entry)
501 {
502 firstGroup = item;
503 }
504 ++found;
505 }
506 item = item->nextSibling();
507 }
508
509 if (found == 1 && firstGroup)
510 {
511 firstGroup->setOpen(true);
512 }
513}
514
515void
516AddressesDialog::availableSelectionChanged()
517{
518 bool selection = !selectedAvailableAddresses.isEmpty();
519 d->ui->mToButton->setEnabled(selection);
520 d->ui->mCCButton->setEnabled(selection);
521 d->ui->mBCCButton->setEnabled(selection);
522}
523
524void
525AddressesDialog::selectedSelectionChanged()
526{
527 bool selection = !selectedSelectedAddresses.isEmpty();
528 d->ui->mRemoveButton->setEnabled(selection);
529}
530
531void
532AddressesDialog::availableAddressSelected( AddresseeViewItem* item, bool selected )
533{
534 if (selected)
535 {
536 selectedAvailableAddresses.append(item);
537 }
538 else
539 {
540 selectedAvailableAddresses.remove(item);
541 }
542}
543
544void
545AddressesDialog::selectedAddressSelected( AddresseeViewItem* item, bool selected )
546{
547 // we have to avoid that a parent and a child is selected together
548 // because in this case we get a double object deletion ( program crashes )
549 // when removing the selected items from list
550 AddresseeViewItem* parent = static_cast<AddresseeViewItem*>(((TQListViewItem*)item)->parent());
551 if ( parent && selected )
552 parent->setSelected( false );
553 if (selected)
554 {
555 selectedSelectedAddresses.append(item);
556 }
557 else
558 {
559 selectedSelectedAddresses.remove(item);
560 }
561 if ( selected ) {
562 AddresseeViewItem* child = static_cast<AddresseeViewItem*>(item->firstChild());
563 while (child) {
564 child->setSelected( false );
565 child = static_cast<AddresseeViewItem*>(child->nextSibling());
566 }
567 }
568}
569
570void
571AddressesDialog::initConnections()
572{
573 connect( d->ui->mFilterEdit, TQ_SIGNAL(textChanged(const TQString &)),
574 TQ_SLOT(filterChanged(const TQString &)) );
575 connect( d->ui->mToButton, TQ_SIGNAL(clicked()),
576 TQ_SLOT(addSelectedTo()) );
577 connect( d->ui->mCCButton, TQ_SIGNAL(clicked()),
578 TQ_SLOT(addSelectedCC()) );
579 connect( d->ui->mBCCButton, TQ_SIGNAL(clicked()),
580 TQ_SLOT(addSelectedBCC()) );
581 connect( d->ui->mSaveAs, TQ_SIGNAL(clicked()),
582 TQ_SLOT(saveAs()) );
583 connect( d->ui->mLdapSearch, TQ_SIGNAL(clicked()),
584 TQ_SLOT(searchLdap()) );
585 connect( d->ui->mRemoveButton, TQ_SIGNAL(clicked()),
586 TQ_SLOT(removeEntry()) );
587 connect( d->ui->mAvailableView, TQ_SIGNAL(selectionChanged()),
588 TQ_SLOT(availableSelectionChanged()) );
589 connect( d->ui->mAvailableView, TQ_SIGNAL(doubleClicked(TQListViewItem*)),
590 TQ_SLOT(addSelectedTo()) );
591 connect( d->ui->mSelectedView, TQ_SIGNAL(selectionChanged()),
592 TQ_SLOT(selectedSelectionChanged()) );
593 connect( d->ui->mSelectedView, TQ_SIGNAL(doubleClicked(TQListViewItem*)),
594 TQ_SLOT(removeEntry()) );
595
596#ifndef TDEPIM_NEW_DISTRLISTS
597 connect( TDEABC::DistributionListWatcher::self(), TQ_SIGNAL( changed() ),
598 this, TQ_SLOT( updateAvailableAddressees() ) );
599#endif
600
601 connect( TDEABC::StdAddressBook::self( true ), TQ_SIGNAL( addressBookChanged(AddressBook*) ),
602 this, TQ_SLOT( updateAvailableAddressees() ) );
603}
604
605void
606AddressesDialog::addAddresseeToAvailable( const TDEABC::Addressee& addr, AddresseeViewItem* defaultParent, bool useCategory )
607{
608 if ( addr.preferredEmail().isEmpty() )
609 return;
610
611 if ( useCategory ) {
612 TQStringList categories = addr.categories();
613
614 for ( TQStringList::Iterator it = categories.begin(); it != categories.end(); ++it ) {
615 if ( !d->groupDict[ *it ] ) { //we don't have the category yet
616 AddresseeViewItem* category = new AddresseeViewItem( d->ui->mAvailableView, *it );
617 d->groupDict.insert( *it, category );
618 }
619
620 for ( uint i = 0; i < addr.emails().count(); ++i ) {
621 AddresseeViewItem* addressee = new AddresseeViewItem( d->groupDict[ *it ], addr, i );
622 connect(addressee, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
623 this, TQ_SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
624 }
625 }
626 }
627
628 bool noCategory = false;
629 if ( useCategory ) {
630 if ( addr.categories().isEmpty() )
631 noCategory = true;
632 } else
633 noCategory = true;
634
635 if ( defaultParent && noCategory ) { // only non-categorized items here
636 AddresseeViewItem* addressee = new AddresseeViewItem( defaultParent, addr );
637 connect(addressee, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
638 this, TQ_SLOT(availableAddressSelected(AddresseeViewItem*, bool)));
639 }
640}
641
642void
643AddressesDialog::addAddresseeToSelected( const TDEABC::Addressee& addr, AddresseeViewItem* defaultParent )
644{
645 if ( addr.preferredEmail().isEmpty() )
646 return;
647
648 if ( defaultParent ) {
649 AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( defaultParent->firstChild() );
650 while( myChild ) {
651 if ( myChild->addressee().preferredEmail() == addr.preferredEmail() )
652 return;//already got it
653 myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
654 }
655 AddresseeViewItem* addressee = new AddresseeViewItem( defaultParent, addr );
656 connect(addressee, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
657 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
658 defaultParent->setOpen( true );
659 }
660
661 d->ui->mSaveAs->setEnabled(true);
662}
663
664void
665AddressesDialog::addAddresseesToSelected( AddresseeViewItem *parent,
666 const TQPtrList<AddresseeViewItem>& addresses )
667{
668 Q_ASSERT( parent );
669
670 TQPtrListIterator<AddresseeViewItem> itr( addresses );
671
672 if (itr.current())
673 {
674 d->ui->mSaveAs->setEnabled(true);
675 }
676
677 while ( itr.current() ) {
678 AddresseeViewItem* address = itr.current();
679 ++itr;
680
681 if (selectedToAvailableMapping.find(address) != 0)
682 {
683 continue;
684 }
685
686 AddresseeViewItem* newItem = 0;
687 if (address->category() == AddresseeViewItem::Entry)
688 {
689 newItem = new AddresseeViewItem( parent, address->addressee() );
690 }
691 else if (address->category() == AddresseeViewItem::DistList)
692 {
693 newItem = new AddresseeViewItem( parent, address->name() );
694 }
695 else
696 {
697 newItem = new AddresseeViewItem( parent, address->name(), allAddressee( address ) );
698 }
699
700 address->setSelected( false );
701 address->setVisible( false );
702 selectedToAvailableMapping.insert(address, newItem);
703 selectedToAvailableMapping.insert(newItem, address);
704 connect(newItem, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
705 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
706 }
707
708 parent->setOpen( true );
709}
710
711TQStringList
712AddressesDialog::entryToString( const TDEABC::Addressee::List& l ) const
713{
714 TQStringList entries;
715
716 for( TDEABC::Addressee::List::ConstIterator it = l.begin(); it != l.end(); ++it ) {
717 entries += (*it).fullEmail();
718 }
719 return entries;
720}
721
722void
723AddressesDialog::addSelectedTo()
724{
725 if ( !d->toItem )
726 {
727 d->toItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("To"), AddresseeViewItem::To );
728 connect(d->toItem, TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
729 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
730 }
731
732 addAddresseesToSelected( d->toItem, selectedAvailableAddresses );
733 selectedAvailableAddresses.clear();
734
735 if ( d->toItem->childCount() > 0 ) {
736 d->toItem->setVisible( true );
737 } else {
738 delete d->toItem;
739 d->toItem = 0;
740 }
741}
742
743void
744AddressesDialog::addSelectedCC()
745{
746 if ( !d->ccItem )
747 {
748 d->ccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("CC"), AddresseeViewItem::CC );
749 connect(d->ccItem , TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
750 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
751 }
752
753 addAddresseesToSelected( d->ccItem, selectedAvailableAddresses );
754 selectedAvailableAddresses.clear();
755
756 if ( d->ccItem->childCount() > 0 ) {
757 d->ccItem->setVisible( true );
758 } else {
759 delete d->ccItem;
760 d->ccItem = 0;
761 }
762}
763
764void
765AddressesDialog::addSelectedBCC()
766{
767 if ( !d->bccItem )
768 {
769 d->bccItem = new AddresseeViewItem( d->ui->mSelectedView, i18n("BCC"), AddresseeViewItem::BCC );
770 connect(d->bccItem , TQ_SIGNAL(addressSelected(AddresseeViewItem*, bool)),
771 this, TQ_SLOT(selectedAddressSelected(AddresseeViewItem*, bool)));
772 }
773
774 addAddresseesToSelected( d->bccItem, selectedAvailableAddresses );
775 selectedAvailableAddresses.clear();
776
777 if ( d->bccItem->childCount() > 0 ) {
778 d->bccItem->setVisible( true );
779 } else {
780 delete d->bccItem;
781 d->bccItem = 0;
782 }
783}
784
785void AddressesDialog::unmapSelectedAddress(AddresseeViewItem* item)
786{
787 AddresseeViewItem* correspondingItem = selectedToAvailableMapping[item];
788 if (correspondingItem)
789 {
790 correspondingItem->setVisible( true );
791 selectedToAvailableMapping.remove( item );
792 selectedToAvailableMapping.remove( correspondingItem );
793 }
794
795 AddresseeViewItem* child = static_cast<AddresseeViewItem*>(item->firstChild());
796 while (child)
797 {
798 unmapSelectedAddress(child);
799 child = static_cast<AddresseeViewItem*>(child->nextSibling());
800 }
801}
802
803void
804AddressesDialog::removeEntry()
805{
806 TQPtrList<AddresseeViewItem> lst;
807 bool resetTo = false;
808 bool resetCC = false;
809 bool resetBCC = false;
810
811 lst.setAutoDelete( false );
812 TQPtrListIterator<AddresseeViewItem> it( selectedSelectedAddresses );
813 while ( it.current() ) {
814 AddresseeViewItem* item = it.current();
815 ++it;
816 if ( d->toItem == item )
817 resetTo = true;
818 else if ( d->ccItem == item )
819 resetCC = true;
820 else if( d->bccItem == item )
821 resetBCC = true;
822 // we may only append parent items
823 unmapSelectedAddress(item);
824 lst.append( item );
825 }
826 selectedSelectedAddresses.clear();
827 lst.setAutoDelete( true );
828 lst.clear();
829 if ( resetTo )
830 d->toItem = 0;
831 else if ( d->toItem && d->toItem->childCount() == 0 )
832 {
833 delete d->toItem;
834 d->toItem = 0;
835 }
836 if ( resetCC )
837 d->ccItem = 0;
838 else if ( d->ccItem && d->ccItem->childCount() == 0 )
839 {
840 delete d->ccItem;
841 d->ccItem = 0;
842 }
843 if ( resetBCC )
844 d->bccItem = 0;
845 else if ( d->bccItem && d->bccItem->childCount() == 0 )
846 {
847 delete d->bccItem;
848 d->bccItem = 0;
849 }
850 d->ui->mSaveAs->setEnabled(d->ui->mSelectedView->firstChild() != 0);
851}
852
853#ifdef TDEPIM_NEW_DISTRLISTS
854
855// copied from tdeabcore.cpp :(
856// KDE4: should be in libtdeabc I think
857static TDEABC::Resource *requestResource( TDEABC::AddressBook* abook, TQWidget *parent )
858{
859 TQPtrList<TDEABC::Resource> tdeabcResources = abook->resources();
860
861 TQPtrList<KRES::Resource> kresResources;
862 TQPtrListIterator<TDEABC::Resource> resIt( tdeabcResources );
863 TDEABC::Resource *resource;
864 while ( ( resource = resIt.current() ) != 0 ) {
865 ++resIt;
866 if ( !resource->readOnly() ) {
867 KRES::Resource *res = static_cast<KRES::Resource*>( resource );
868 if ( res )
869 kresResources.append( res );
870 }
871 }
872
873 KRES::Resource *res = KRES::SelectDialog::getResource( kresResources, parent );
874 return static_cast<TDEABC::Resource*>( res );
875}
876#endif
877
878void
879AddressesDialog::saveAs()
880{
881#ifndef TDEPIM_NEW_DISTRLISTS
882 TDEABC::DistributionListManager manager( TDEABC::StdAddressBook::self( true ) );
883 manager.load();
884#endif
885
886 if ( !d->ui->mSelectedView->firstChild() ) {
887 KMessageBox::information( 0,
888 i18n("There are no addresses in your list. "
889 "First add some addresses from your address book, "
890 "then try again.") );
891 return;
892 }
893
894 bool ok = false;
895 TQString name = KInputDialog::getText( i18n("New Distribution List"),
896 i18n("Please enter name:"),
897 TQString(), &ok,
898 this );
899 if ( !ok || name.isEmpty() )
900 return;
901
902 bool alreadyExists = false;
903#ifdef TDEPIM_NEW_DISTRLISTS
904 TDEABC::AddressBook* abook = TDEABC::StdAddressBook::self( true );
905 KPIM::DistributionList dlist = KPIM::DistributionList::findByName( abook, name );
906 alreadyExists = !dlist.isEmpty();
907#else
908 alreadyExists = manager.list( name );
909#endif
910
911 if ( alreadyExists ) {
912 KMessageBox::information( 0,
913 i18n( "<qt>Distribution list with the given name <b>%1</b> "
914 "already exists. Please select a different name.</qt>" )
915 .arg( name ) );
916 return;
917 }
918
919#ifdef TDEPIM_NEW_DISTRLISTS
920 TDEABC::Resource* resource = requestResource( abook, this );
921 if ( !resource )
922 return;
923
924 dlist.setResource( resource );
925 dlist.setName( name );
926 TDEABC::Addressee::List addrl = allAddressee( d->ui->mSelectedView, false );
927 for ( TDEABC::Addressee::List::iterator itr = addrl.begin();
928 itr != addrl.end(); ++itr ) {
929 dlist.insertEntry( *itr );
930 }
931 abook->insertAddressee( dlist );
932#else
933 TDEABC::DistributionList *dlist = new TDEABC::DistributionList( &manager, name );
934 TDEABC::Addressee::List addrl = allAddressee( d->ui->mSelectedView, false );
935 for ( TDEABC::Addressee::List::iterator itr = addrl.begin();
936 itr != addrl.end(); ++itr ) {
937 dlist->insertEntry( *itr );
938 }
939
940 manager.save();
941#endif
942}
943
944void
945AddressesDialog::searchLdap()
946{
947 if ( !d->ldapSearchDialog ) {
948 d->ldapSearchDialog = new LDAPSearchDialog( this );
949 connect( d->ldapSearchDialog, TQ_SIGNAL( addresseesAdded() ),
950 TQ_SLOT(ldapSearchResult() ) );
951 }
952 d->ldapSearchDialog->show();
953}
954
955void
956AddressesDialog::ldapSearchResult()
957{
958 TQStringList emails = KPIM::splitEmailAddrList( d->ldapSearchDialog->selectedEMails() );
959 TQStringList::iterator it( emails.begin() );
960 TQStringList::iterator end( emails.end() );
961 for ( ; it != end; ++it ){
962 TQString name;
963 TQString email;
964 KPIM::getNameAndMail( (*it), name, email );
965 TDEABC::Addressee ad;
966 ad.setNameFromString( name );
967 ad.insertEmail( email );
968 addAddresseeToSelected( ad, selectedToItem() );
969 }
970}
971
972void
973AddressesDialog::launchAddressBook()
974{
975 tdeApp->startServiceByDesktopName( "kaddressbook", TQString() );
976}
977
978void
979AddressesDialog::filterChanged( const TQString& txt )
980{
981 TQListViewItemIterator it( d->ui->mAvailableView );
982 bool showAll = false;
983
984 if ( txt.isEmpty() )
985 showAll = true;
986
987 int personalVisible = 0;
988 int recentVisible = 0;
989 while ( it.current() ) {
990 AddresseeViewItem* item = static_cast<AddresseeViewItem*>( it.current() );
991 ++it;
992
993 if ( showAll ) {
994 item->setOpen( true );
995 item->setVisible( true );
996 // allen: I do not like the following behavior. comment out and see if anyone screams
997 //if ( item->category() == AddresseeViewItem::Group )
998 // item->setOpen( false );//close to not have too many entries
999 continue;
1000 }
1001
1002 if ( item->category() == AddresseeViewItem::Entry ) {
1003 bool matches = item->matches( txt );
1004 item->setVisible( matches );
1005 TQListViewItem *parent = static_cast<TQListViewItem*>( item )->parent();
1006 if ( matches && parent ) {
1007 if ( parent == d->personal ) {
1008 personalVisible++;
1009 } else if ( parent == d->recent ) {
1010 recentVisible++;
1011 }
1012 }
1013 }
1014 if ( item->category() == AddresseeViewItem::Group ) {
1015 item->setOpen( true );
1016 item->setVisible( true );
1017 }
1018 }
1019
1020 if ( !showAll && personalVisible == 0 ) {
1021 d->personal->setOpen( false );
1022 d->personal->setVisible( false );
1023 }
1024 if ( !showAll && recentVisible == 0 ) {
1025 d->recent->setOpen( false );
1026 d->recent->setVisible( false );
1027 }
1028
1029 int distlistgroupVisible = 0;
1030 if ( !showAll ) {
1031 TQPtrListIterator<AddresseeViewItem> it( d->dists );
1032 for ( ; it.current(); ++it ) {
1033 TQListViewItem *p = *it;
1034 p->setVisible( true );
1035 AddresseeViewItem *p2 = static_cast<AddresseeViewItem*>( p->firstChild() );
1036 int pcount = 0;
1037 while ( p2 ) {
1038 if ( p2->matches( txt ) ) {
1039 p2->setVisible( true );
1040 pcount++;
1041 } else {
1042 p2->setVisible( false );
1043 }
1044 p2 = static_cast<AddresseeViewItem*>( p2->nextSibling() );
1045 }
1046 if ( !pcount && !p->text( 0 ).contains( txt, false ) ) {
1047 p->setVisible( false );
1048 }
1049 distlistgroupVisible += pcount;
1050 if ( p->text( 0 ).contains( txt, false ) ) {
1051 distlistgroupVisible++;
1052 }
1053 }
1054 }
1055 if ( d->topdist ) {
1056 if ( showAll || distlistgroupVisible > 0 ) {
1057 d->topdist->setOpen( true );
1058 } else {
1059 d->topdist->setOpen( false );
1060 d->topdist->setVisible( false );
1061 }
1062 }
1063}
1064
1065TDEABC::Addressee::List
1066AddressesDialog::allAddressee( TDEListView* view, bool onlySelected ) const
1067{
1068 TDEABC::Addressee::List lst;
1069 TQListViewItemIterator it( view );
1070 while ( it.current() ) {
1071 AddresseeViewItem* item = static_cast<AddresseeViewItem*>( it.current() );
1072 if ( !onlySelected || item->isSelected() ) {
1073 if ( item->category() != AddresseeViewItem::Entry ) {
1074 AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( item->firstChild() );
1075 while( myChild ) {
1076 lst.append( myChild->addressee() );
1077 myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
1078 }
1079 } else {
1080 lst.append( item->addressee() );
1081 }
1082 }
1083 ++it;
1084 }
1085
1086 return lst;
1087}
1088
1089TDEABC::Addressee::List
1090AddressesDialog::allAddressee( AddresseeViewItem* parent ) const
1091{
1092 TDEABC::Addressee::List lst;
1093
1094 if ( !parent ) return lst;
1095
1096 if ( parent->category() == AddresseeViewItem::Entry )
1097 {
1098 lst.append( parent->addressee() );
1099 return lst;
1100 }
1101
1102 AddresseeViewItem *myChild = static_cast<AddresseeViewItem*>( parent->firstChild() );
1103 while( myChild ) {
1104 if ( myChild->category() == AddresseeViewItem::FilledGroup )
1105 lst += myChild->addresses();
1106 else if ( !myChild->addressee().isEmpty() )
1107 lst.append( myChild->addressee() );
1108 myChild = static_cast<AddresseeViewItem*>( myChild->nextSibling() );
1109 }
1110
1111 return lst;
1112}
1113
1114TQStringList
1115AddressesDialog::allDistributionLists( AddresseeViewItem* parent ) const
1116{
1117 TQStringList lists;
1118
1119 if ( !parent )
1120 return TQStringList();
1121
1122 AddresseeViewItem *item = static_cast<AddresseeViewItem*>( parent->firstChild() );
1123 while ( item ) {
1124 if ( item->category() == AddresseeViewItem::DistList && !item->name().isEmpty() )
1125 lists.append( item->name() );
1126
1127 item = static_cast<AddresseeViewItem*>( item->nextSibling() );
1128 }
1129
1130 return lists;
1131}
1132
1133void
1134AddressesDialog::addDistributionLists()
1135{
1136 TDEABC::AddressBook* abook = TDEABC::StdAddressBook::self( true );
1137
1138#ifdef TDEPIM_NEW_DISTRLISTS
1139 const TQValueList<KPIM::DistributionList> distLists =
1140 KPIM::DistributionList::allDistributionLists( abook );
1141#else
1142 TDEABC::DistributionListManager manager( abook );
1143 manager.load();
1144
1145 TQStringList distLists = manager.listNames();
1146#endif
1147
1148 if ( distLists.isEmpty() )
1149 return;
1150
1151 if ( !d->topdist ) {
1152 d->topdist = new AddresseeViewItem( d->ui->mAvailableView, i18n( "Distribution Lists" ) );
1153 }
1154
1155#ifdef TDEPIM_NEW_DISTRLISTS
1156 TQValueList<KPIM::DistributionList>::ConstIterator listIt;
1157#else
1158 TQStringList::Iterator listIt;
1159#endif
1160 int total = 0;
1161 for ( listIt = distLists.begin(); listIt != distLists.end(); ++listIt ) {
1162#ifdef TDEPIM_NEW_DISTRLISTS
1163 KPIM::DistributionList dlist = *listIt;
1164 KPIM::DistributionList::Entry::List entries = dlist.entries(abook);
1165#else
1166 TDEABC::DistributionList& dlist = *manager.list( *listIt );
1167 TDEABC::DistributionList::Entry::List entries = dlist.entries();
1168#endif
1169
1170 AddresseeViewItem *item = new AddresseeViewItem( d->topdist, dlist.name() );
1171 d->dists.append( item );
1172 connect( item, TQ_SIGNAL( addressSelected( AddresseeViewItem*, bool ) ),
1173 this, TQ_SLOT( availableAddressSelected( AddresseeViewItem*, bool ) ) );
1174
1175#ifdef TDEPIM_NEW_DISTRLISTS
1176 KPIM::DistributionList::Entry::List::Iterator itemIt;
1177#else
1178 TDEABC::DistributionList::Entry::List::Iterator itemIt;
1179#endif
1180 for ( itemIt = entries.begin(); itemIt != entries.end(); ++itemIt ) {
1181 addAddresseeToAvailable( (*itemIt).addressee, item, false );
1182 }
1183 if ( item->childCount() > 0 ) {
1184 item->setOpen( true );
1185 item->setVisible( true );
1186 }
1187 total += item->childCount();
1188 }
1189 if ( total > 0 ) {
1190 d->topdist->setOpen( true );
1191 d->topdist->setVisible( true );
1192 }
1193}
1194
1195} // namespace
1196
1197#include "addressesdialog.moc"
Distribution list of email addresses.
void insertEntry(const Addressee &, const TQString &email=TQString())
Insert an entry into this distribution list.
void setName(const TQString &name)
HACK: reimplemented from Addressee, but it's NOT virtual there.
Entry::List entries(TDEABC::AddressBook *book) const
Return list of entries belonging to this distribution list.
TDEPIM classes for drag and drop of mails.