00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include <qtooltip.h>
00026 #include <qframe.h>
00027 #include <qguardedptr.h>
00028 #include <qpixmap.h>
00029 #include <qlayout.h>
00030 #include <qwidgetstack.h>
00031 #include <qdatetime.h>
00032 #include <qwhatsthis.h>
00033
00034 #include <kdebug.h>
00035 #include <klocale.h>
00036 #include <kstandarddirs.h>
00037 #include <kmessagebox.h>
00038 #include <kinputdialog.h>
00039 #include <kio/netaccess.h>
00040 #include <kabc/addressee.h>
00041
00042 #include <libkdepim/designerfields.h>
00043 #include <libkdepim/embeddedurlpage.h>
00044
00045 #include <libkcal/calendarlocal.h>
00046 #include <libkcal/incidence.h>
00047 #include <libkcal/icalformat.h>
00048 #include <libkcal/resourcecalendar.h>
00049
00050 #include "koprefs.h"
00051 #include "koglobals.h"
00052 #include "koeditordetails.h"
00053 #include "koeditoralarms.h"
00054 #include "urihandler.h"
00055 #include "koincidenceeditor.h"
00056 #include "templatemanagementdialog.h"
00057
00058 KOIncidenceEditor::KOIncidenceEditor( const QString &caption,
00059 Calendar *calendar, QWidget *parent )
00060 : KDialogBase( Tabbed, caption, Ok | Apply | Cancel | Default, Ok,
00061 parent, 0, false, false ),
00062 mAttendeeEditor( 0 ), mResource( 0 ), mIsCounter( false ), mIsCreateTask( false )
00063 {
00064
00065
00066 setWFlags( getWFlags() | WGroupLeader );
00067
00068 mCalendar = calendar;
00069
00070 if ( KOPrefs::instance()->mCompactDialogs ) {
00071 showButton( Apply, false );
00072 showButton( Default, false );
00073 } else {
00074 setButtonText( Default, i18n("&Templates...") );
00075 }
00076
00077 connect( this, SIGNAL( defaultClicked() ), SLOT( slotManageTemplates() ) );
00078 connect( this, SIGNAL( finished() ), SLOT( delayedDestruct() ) );
00079 }
00080
00081 KOIncidenceEditor::~KOIncidenceEditor()
00082 {
00083 }
00084
00085 void KOIncidenceEditor::setupAttendeesTab()
00086 {
00087 QFrame *topFrame = addPage( i18n("Atte&ndees") );
00088 QWhatsThis::add( topFrame,
00089 i18n("The Attendees tab allows you to Add or Remove "
00090 "Attendees to/from this event or to-do.") );
00091
00092 QBoxLayout *topLayout = new QVBoxLayout( topFrame );
00093
00094 mAttendeeEditor = mDetails = new KOEditorDetails( spacingHint(), topFrame );
00095 topLayout->addWidget( mDetails );
00096 }
00097
00098 void KOIncidenceEditor::slotApply()
00099 {
00100 processInput();
00101 }
00102
00103 void KOIncidenceEditor::slotOk()
00104 {
00105
00106
00107
00108 QGuardedPtr<QWidget> ptr( this );
00109 if ( processInput() && ptr ) accept();
00110 }
00111
00112 void KOIncidenceEditor::slotCancel()
00113 {
00114 processCancel();
00115 reject();
00116 }
00117
00118 void KOIncidenceEditor::cancelRemovedAttendees( Incidence *incidence )
00119 {
00120 if ( !incidence ) return;
00121
00122
00123
00124 if ( KOPrefs::instance()->thatIsMe( incidence->organizer().email() ) ) {
00125 Incidence *ev = incidence->clone();
00126 ev->registerObserver( 0 );
00127 mAttendeeEditor->cancelAttendeeEvent( ev );
00128 if ( ev->attendeeCount() > 0 ) {
00129 emit deleteAttendee( ev );
00130 }
00131 delete( ev );
00132 }
00133
00134 }
00135
00136 void KOIncidenceEditor::slotManageTemplates()
00137 {
00138 kdDebug(5850) << "KOIncidenceEditor::manageTemplates()" << endl;
00139
00140 TemplateManagementDialog * const d = new TemplateManagementDialog( this, templates() );
00141 connect( d, SIGNAL( loadTemplate( const QString& ) ),
00142 this, SLOT( slotLoadTemplate( const QString& ) ) );
00143 connect( d, SIGNAL( templatesChanged( const QStringList& ) ),
00144 this, SLOT( slotTemplatesChanged( const QStringList& ) ) );
00145 connect( d, SIGNAL( saveTemplate( const QString& ) ),
00146 this, SLOT( slotSaveTemplate( const QString& ) ) );
00147 d->exec();
00148 return;
00149 }
00150
00151 void KOIncidenceEditor::saveAsTemplate( Incidence *incidence,
00152 const QString &templateName )
00153 {
00154 if ( !incidence || templateName.isEmpty() ) return;
00155
00156 QString fileName = "templates/" + incidence->type();
00157 fileName.append( "/" + templateName );
00158 fileName = locateLocal( "data", "korganizer/" + fileName );
00159
00160 CalendarLocal cal( KOPrefs::instance()->mTimeZoneId );
00161 cal.addIncidence( incidence );
00162 ICalFormat format;
00163 format.save( &cal, fileName );
00164 }
00165
00166 void KOIncidenceEditor::slotLoadTemplate( const QString& templateName )
00167 {
00168 CalendarLocal cal( KOPrefs::instance()->mTimeZoneId );
00169 QString fileName = locateLocal( "data", "korganizer/templates/" + type() + "/" +
00170 templateName );
00171
00172 if ( fileName.isEmpty() ) {
00173 KMessageBox::error( this, i18n("Unable to find template '%1'.")
00174 .arg( fileName ) );
00175 } else {
00176 ICalFormat format;
00177 if ( !format.load( &cal, fileName ) ) {
00178 KMessageBox::error( this, i18n("Error loading template file '%1'.")
00179 .arg( fileName ) );
00180 return;
00181 }
00182 }
00183 loadTemplate( cal );
00184 }
00185
00186 void KOIncidenceEditor::slotTemplatesChanged( const QStringList& newTemplates )
00187 {
00188 templates() = newTemplates;
00189 }
00190
00191 void KOIncidenceEditor::setupDesignerTabs( const QString &type )
00192 {
00193 QStringList activePages = KOPrefs::instance()->activeDesignerFields();
00194
00195 QStringList list = KGlobal::dirs()->findAllResources( "data",
00196 "korganizer/designer/" + type + "/*.ui", true, true );
00197 for ( QStringList::iterator it = list.begin(); it != list.end(); ++it ) {
00198 const QString &fn = (*it).mid( (*it).findRev('/') + 1 );
00199 if ( activePages.find( fn ) != activePages.end() ) {
00200 addDesignerTab( *it );
00201 }
00202 }
00203 }
00204
00205 QWidget *KOIncidenceEditor::addDesignerTab( const QString &uifile )
00206 {
00207 kdDebug(5850) << "Designer tab: " << uifile << endl;
00208
00209 KPIM::DesignerFields *wid = new KPIM::DesignerFields( uifile, 0 );
00210 mDesignerFields.append( wid );
00211
00212 QFrame *topFrame = addPage( wid->title() );
00213
00214 QBoxLayout *topLayout = new QVBoxLayout( topFrame );
00215
00216 wid->reparent( topFrame, 0, QPoint() );
00217 topLayout->addWidget( wid );
00218 mDesignerFieldForWidget[ topFrame ] = wid;
00219
00220 return topFrame;
00221 }
00222
00223 class KCalStorage : public KPIM::DesignerFields::Storage
00224 {
00225 public:
00226 KCalStorage( Incidence *incidence )
00227 : mIncidence( incidence )
00228 {
00229 }
00230
00231 QStringList keys()
00232 {
00233 QStringList keys;
00234
00235 QMap<QCString, QString> props = mIncidence->customProperties();
00236 QMap<QCString, QString>::ConstIterator it;
00237 for( it = props.begin(); it != props.end(); ++it ) {
00238 QString customKey = it.key();
00239 QStringList parts = QStringList::split( "-", customKey );
00240 if ( parts.count() != 4 ) continue;
00241 if ( parts[ 2 ] != "KORGANIZER" ) continue;
00242 keys.append( parts[ 3 ] );
00243 }
00244
00245 return keys;
00246 }
00247
00248 QString read( const QString &key )
00249 {
00250 return mIncidence->customProperty( "KORGANIZER", key.utf8() );
00251 }
00252
00253 void write( const QString &key, const QString &value )
00254 {
00255 mIncidence->setCustomProperty( "KORGANIZER", key.utf8(), value );
00256 }
00257
00258 private:
00259 Incidence *mIncidence;
00260 };
00261
00262 void KOIncidenceEditor::readDesignerFields( Incidence *i )
00263 {
00264 KCalStorage storage( i );
00265 KPIM::DesignerFields *fields;
00266 for( fields = mDesignerFields.first(); fields;
00267 fields = mDesignerFields.next() ) {
00268 fields->load( &storage );
00269 }
00270 }
00271
00272 void KOIncidenceEditor::writeDesignerFields( Incidence *i )
00273 {
00274 kdDebug(5850) << "KOIncidenceEditor::writeDesignerFields()" << endl;
00275
00276 KCalStorage storage( i );
00277 KPIM::DesignerFields *fields;
00278 for( fields = mDesignerFields.first(); fields;
00279 fields = mDesignerFields.next() ) {
00280 kdDebug(5850) << "Write Field " << fields->title() << endl;
00281 fields->save( &storage );
00282 }
00283 }
00284
00285
00286 void KOIncidenceEditor::setupEmbeddedURLPage( const QString &label,
00287 const QString &url, const QString &mimetype )
00288 {
00289 kdDebug(5850) << "KOIncidenceEditor::setupEmbeddedURLPage()" << endl;
00290 kdDebug(5850) << "label=" << label << ", url=" << url << ", mimetype=" << mimetype << endl;
00291 QFrame *topFrame = addPage( label );
00292 QBoxLayout *topLayout = new QVBoxLayout( topFrame );
00293
00294 KPIM::EmbeddedURLPage *wid = new KPIM::EmbeddedURLPage( url, mimetype,
00295 topFrame );
00296 topLayout->addWidget( wid );
00297 mEmbeddedURLPages.append( topFrame );
00298 connect( wid, SIGNAL( openURL( const KURL & ) ) ,
00299 this, SLOT( openURL( const KURL & ) ) );
00300
00301 wid->loadContents();
00302 }
00303
00304 void KOIncidenceEditor::createEmbeddedURLPages( Incidence *i )
00305 {
00306 kdDebug(5850) << "KOIncidenceEditor::createEmbeddedURLPages()" << endl;
00307
00308 if ( !i ) return;
00309 if ( !mEmbeddedURLPages.isEmpty() ) {
00310 kdDebug(5850) << "mEmbeddedURLPages are not empty, clearing it!" << endl;
00311 mEmbeddedURLPages.setAutoDelete( true );
00312 mEmbeddedURLPages.clear();
00313 mEmbeddedURLPages.setAutoDelete( false );
00314 }
00315 if ( !mAttachedDesignerFields.isEmpty() ) {
00316 for ( QPtrList<QWidget>::Iterator it = mAttachedDesignerFields.begin();
00317 it != mAttachedDesignerFields.end(); ++it ) {
00318 if ( mDesignerFieldForWidget.contains( *it ) ) {
00319 mDesignerFields.remove( mDesignerFieldForWidget[ *it ] );
00320 }
00321 }
00322 mAttachedDesignerFields.setAutoDelete( true );
00323 mAttachedDesignerFields.clear();
00324 mAttachedDesignerFields.setAutoDelete( false );
00325 }
00326
00327 Attachment::List att = i->attachments();
00328 for ( Attachment::List::Iterator it = att.begin(); it != att.end(); ++it ) {
00329 Attachment *a = (*it);
00330 kdDebug(5850) << "Iterating over the attachments " << endl;
00331 kdDebug(5850) << "label=" << a->label() << ", url=" << a->uri() << ", mimetype=" << a->mimeType() << endl;
00332 if ( a && a->showInline() && a->isUri() ) {
00333
00334
00335
00336
00337
00338
00339
00340
00341
00342 if ( a->mimeType() == "text/html" )
00343 {
00344 setupEmbeddedURLPage( a->label(), a->uri(), a->mimeType() );
00345 }
00346 }
00347 }
00348 }
00349
00350 void KOIncidenceEditor::openURL( const KURL &url )
00351 {
00352 QString uri = url.url();
00353 UriHandler::process( uri );
00354 }
00355
00356 void KOIncidenceEditor::addAttachments( const QStringList &attachments,
00357 const QStringList &mimeTypes,
00358 bool inlineAttachments )
00359 {
00360 emit signalAddAttachments( attachments, mimeTypes, inlineAttachments );
00361 }
00362
00363 void KOIncidenceEditor::addAttendees( const QStringList &attendees )
00364 {
00365 QStringList::ConstIterator it;
00366 for ( it = attendees.begin(); it != attendees.end(); ++it ) {
00367 QString name, email;
00368 KABC::Addressee::parseEmailAddress( *it, name, email );
00369 mAttendeeEditor->insertAttendee( new Attendee( name, email ) );
00370 }
00371 }
00372
00373 void KOIncidenceEditor::setResource( ResourceCalendar *res, const QString &subRes )
00374 {
00375 QString label;
00376 if ( res ) {
00377 if ( !res->subresources().isEmpty() && !subRes.isEmpty() ) {
00378 label = res->labelForSubresource( subRes );
00379 } else {
00380 label = res->resourceName();
00381 }
00382 }
00383
00384 mResource = res;
00385 mSubResource = subRes;
00386 }
00387
00388
00389 void KOIncidenceEditor::selectCreateTask( bool enable )
00390 {
00391 mIsCreateTask = enable;
00392 if ( mIsCreateTask ) {
00393 setCaption( i18n( "Create to-do" ) );
00394 setButtonOK( i18n( "Create to-do" ) );
00395 showButtonApply( false );
00396 }
00397 }
00398
00399 void KOIncidenceEditor::selectInvitationCounterProposal(bool enable)
00400 {
00401 mIsCounter = enable;
00402 if ( mIsCounter ) {
00403 setCaption( i18n( "Counter proposal" ) );
00404 setButtonOK( i18n( "Counter proposal" ) );
00405 showButtonApply( false );
00406 }
00407 }
00408
00409
00410 #include "koincidenceeditor.moc"