kmail

kmlineeditspell.cpp
1 // -*- mode: C++; c-file-style: "gnu" -*-
2 // kmcomposewin.cpp
3 // Author: Markus Wuebben <markus.wuebben@kde.org>
4 // This code is published under the GPL.
5 
6 #include "kmlineeditspell.h"
7 
8 #include "recentaddresses.h"
9 #include "kmkernel.h"
10 #include "globalsettings.h"
11 #include "stringutil.h"
12 
13 #include <libtdepim/kvcarddrag.h>
14 #include <libemailfunctions/email.h>
15 
16 #include <tdeabc/vcardconverter.h>
17 #include <tdeio/netaccess.h>
18 
19 #include <tdepopupmenu.h>
20 #include <kurl.h>
21 #include <kurldrag.h>
22 #include <tdemessagebox.h>
23 #include <tdecompletionbox.h>
24 #include <tdelocale.h>
25 
26 #include <tqevent.h>
27 #include <tqfile.h>
28 #include <tqcstring.h>
29 #include <tqcursor.h>
30 
31 
32 KMLineEdit::KMLineEdit(bool useCompletion,
33  TQWidget *parent, const char *name)
34  : KPIM::AddresseeLineEdit(parent,useCompletion,name)
35 {
36  allowSemiColonAsSeparator( GlobalSettings::allowSemicolonAsAddressSeparator() );
37 }
38 
39 
40 //-----------------------------------------------------------------------------
41 void KMLineEdit::keyPressEvent(TQKeyEvent *e)
42 {
43  if ((e->key() == Key_Enter || e->key() == Key_Return) &&
44  !completionBox()->isVisible())
45  {
46  emit focusDown();
47  AddresseeLineEdit::keyPressEvent(e);
48  return;
49  }
50  if (e->key() == Key_Up)
51  {
52  emit focusUp();
53  return;
54  }
55  if (e->key() == Key_Down)
56  {
57  emit focusDown();
58  return;
59  }
60  AddresseeLineEdit::keyPressEvent(e);
61 }
62 
63 
64 void KMLineEdit::insertEmails( const TQStringList & emails )
65 {
66  if ( emails.empty() )
67  return;
68 
69  TQString contents = text();
70  if ( !contents.isEmpty() )
71  contents += ',';
72  // only one address, don't need tdepopup to choose
73  if ( emails.size() == 1 ) {
74  setText( contents + emails.front() );
75  return;
76  }
77  //multiple emails, let the user choose one
78  TDEPopupMenu menu( this, "Addresschooser" );
79  for ( TQStringList::const_iterator it = emails.begin(), end = emails.end() ; it != end; ++it )
80  menu.insertItem( *it );
81  const int result = menu.exec( TQCursor::pos() );
82  if ( result == -1 )
83  return;
84  setText( contents + menu.text( result ) );
85 }
86 
87 void KMLineEdit::dropEvent( TQDropEvent *event )
88 {
89  KURL::List urls;
90 
91  // Case one: The user dropped a text/directory (i.e. vcard), so decode its
92  // contents
93  if ( KVCardDrag::canDecode( event ) ) {
94  TDEABC::Addressee::List list;
95  KVCardDrag::decode( event, list );
96 
97  TDEABC::Addressee::List::Iterator ait;
98  for ( ait = list.begin(); ait != list.end(); ++ait ){
99  insertEmails( (*ait).emails() );
100  }
101  }
102 
103  // Case two: The user dropped a list or Urls.
104  // Iterate over that list. For mailto: Urls, just add the addressee to the list,
105  // and for other Urls, download the Url and assume it points to a vCard
106  else if ( KURLDrag::decode( event, urls ) ) {
107  KURL::List::Iterator it = urls.begin();
108  TDEABC::Addressee::List list;
109  for ( it = urls.begin(); it != urls.end(); ++it ) {
110 
111  // First, let's deal with mailto Urls. The path() part contains the
112  // email-address.
113  if ( (*it).protocol() == "mailto" ) {
114  TDEABC::Addressee addressee;
115  addressee.insertEmail( KMail::StringUtil::decodeMailtoUrl( (*it).path() ), true /* preferred */ );
116  list += addressee;
117  }
118  // Otherwise, download the vCard to which the Url points
119  else {
120  TDEABC::VCardConverter converter;
121  TQString fileName;
122  if ( TDEIO::NetAccess::download( (*it), fileName, parentWidget() ) ) {
123  TQFile file( fileName );
124  file.open( IO_ReadOnly );
125  const TQByteArray data = file.readAll();
126  file.close();
127 #if defined(KABC_VCARD_ENCODING_FIX)
128  list += converter.parseVCardsRaw( data.data() );
129 #else
130  list += converter.parseVCards( data );
131 #endif
132  TDEIO::NetAccess::removeTempFile( fileName );
133  } else {
134  TQString caption( i18n( "vCard Import Failed" ) );
135  TQString text = i18n( "<qt>Unable to access <b>%1</b>.</qt>" ).arg( (*it).url() );
136  KMessageBox::error( parentWidget(), text, caption );
137  }
138  }
139  // Now, let the user choose which addressee to add.
140  TDEABC::Addressee::List::Iterator ait;
141  for ( ait = list.begin(); ait != list.end(); ++ait )
142  insertEmails( (*ait).emails() );
143  }
144  }
145 
146  // Case three: Let AddresseeLineEdit deal with the rest
147  else {
148  KPIM::AddresseeLineEdit::dropEvent( event );
149  }
150 }
151 
152 TQPopupMenu *KMLineEdit::createPopupMenu()
153 {
154  TQPopupMenu *menu = KPIM::AddresseeLineEdit::createPopupMenu();
155  if ( !menu )
156  return 0;
157 
158  menu->insertSeparator();
159  menu->insertItem( i18n( "Edit Recent Addresses..." ),
160  this, TQT_SLOT( editRecentAddresses() ) );
161 
162  return menu;
163 }
164 
165 void KMLineEdit::editRecentAddresses()
166 {
167  TDERecentAddress::RecentAddressDialog dlg( this );
168  dlg.setAddresses( TDERecentAddress::RecentAddresses::self( KMKernel::config() )->addresses() );
169  if ( !dlg.exec() )
170  return;
171  TDERecentAddress::RecentAddresses::self( KMKernel::config() )->clear();
172  const TQStringList addrList = dlg.addresses();
173  for ( TQStringList::const_iterator it = addrList.begin(), end = addrList.end() ; it != end ; ++it )
174  TDERecentAddress::RecentAddresses::self( KMKernel::config() )->add( *it );
175  loadContacts();
176 }
177 
178 
179 //-----------------------------------------------------------------------------
180 void KMLineEdit::loadContacts()
181 {
182  AddresseeLineEdit::loadContacts();
183 
184  if ( GlobalSettings::self()->showRecentAddressesInComposer() ){
185  if ( KMKernel::self() ) {
186  TQStringList recent =
187  TDERecentAddress::RecentAddresses::self( KMKernel::config() )->addresses();
188  TQStringList::Iterator it = recent.begin();
189  TQString name, email;
190 
191  TDEConfig config( "kpimcompletionorder" );
192  config.setGroup( "CompletionWeights" );
193  int weight = config.readEntry( "Recent Addresses", "10" ).toInt();
194  int idx = addCompletionSource( i18n( "Recent Addresses" ), weight );
195  for ( ; it != recent.end(); ++it ) {
196  TDEABC::Addressee addr;
197  KPIM::getNameAndMail(*it, name, email);
198  name = KPIM::quoteNameIfNecessary( name );
199  if ( ( name[0] == '"' ) && ( name[name.length() - 1] == '"' ) ) {
200  name.remove( 0, 1 );
201  name.truncate( name.length() - 1 );
202  }
203  addr.setNameFromString( name );
204  addr.insertEmail( email, true );
205  addContact( addr, weight, idx );
206  }
207  }
208  }
209 }
210 
211 
212 KMLineEditSpell::KMLineEditSpell(bool useCompletion,
213  TQWidget *parent, const char *name)
214  : KMLineEdit(useCompletion,parent,name)
215 {
216 }
217 
218 
219 void KMLineEditSpell::highLightWord( unsigned int length, unsigned int pos )
220 {
221  setSelection ( pos, length );
222 }
223 
224 void KMLineEditSpell::spellCheckDone( const TQString &s )
225 {
226  if( s != text() )
227  setText( s );
228 }
229 
230 void KMLineEditSpell::spellCheckerMisspelling( const TQString &_text, const TQStringList&, unsigned int pos)
231 {
232  highLightWord( _text.length(),pos );
233 }
234 
235 void KMLineEditSpell::spellCheckerCorrected( const TQString &old, const TQString &corr, unsigned int pos)
236 {
237  if( old!= corr )
238  {
239  setSelection ( pos, old.length() );
240  insert( corr );
241  setSelection ( pos, corr.length() );
242  emit subjectTextSpellChecked();
243  }
244 }
245 
246 
247 #include "kmlineeditspell.moc"