• Skip to content
  • Skip to link menu
KDE 4.1 API Reference
  • KDE API Reference
  • KDE-PIM Libraries
  • Sitemap
  • Contact Us
 

KCal Library

incidencebase.cpp

Go to the documentation of this file.
00001 /*
00002   This file is part of the kcal library.
00003 
00004   Copyright (c) 2001,2004 Cornelius Schumacher <schumacher@kde.org>
00005   Copyright (C) 2003-2004 Reinhold Kainhofer <reinhold@kainhofer.com>
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., 51 Franklin Street, Fifth Floor,
00020   Boston, MA 02110-1301, USA.
00021 */
00035 #include "incidencebase.h"
00036 #include "calformat.h"
00037 
00038 #include <kglobal.h>
00039 #include <klocale.h>
00040 #include <kdebug.h>
00041 #include <kurl.h>
00042 #include <ksystemtimezone.h>
00043 
00044 #include <QtCore/QList>
00045 
00046 using namespace KCal;
00047 
00052 //@cond PRIVATE
00053 class KCal::IncidenceBase::Private
00054 {
00055   public:
00056     Private()
00057       : mUpdateGroupLevel( 0 ),
00058         mUpdatedPending( false ),
00059         mAllDay( true ),
00060         mHasDuration( false )
00061     { mAttendees.setAutoDelete( true ); }
00062 
00063     Private( const Private &other )
00064       : mUpdateGroupLevel( 0 ),
00065         mUpdatedPending( false ),
00066         mAllDay( true ),
00067         mHasDuration( false )
00068     {
00069       mAttendees.setAutoDelete( true );
00070       init( other );
00071     }
00072 
00073     void init( const Private &other );
00074 
00075     KDateTime mLastModified;     // incidence last modified date
00076     KDateTime mDtStart;          // incidence start time
00077     Person mOrganizer;           // incidence person (owner)
00078     QString mUid;                // incidence unique id
00079     Duration mDuration;          // incidence duration
00080     int mUpdateGroupLevel;       // if non-zero, suppresses update() calls
00081     bool mUpdatedPending;        // true if an update has occurred since startUpdates()
00082     bool mAllDay;                // true if the incidence is all-day
00083     bool mHasDuration;           // true if the incidence has a duration
00084 
00085     Attendee::List mAttendees;   // list of incidence attendees
00086     QStringList mComments;       // list of incidence comments
00087     QList<IncidenceObserver*> mObservers; // list of incidence observers
00088 };
00089 
00090 void IncidenceBase::Private::init( const Private &other )
00091 {
00092   mLastModified = other.mLastModified;
00093   mDtStart = other.mDtStart;
00094   mOrganizer = other.mOrganizer;
00095   mUid = other.mUid;
00096   mDuration = other.mDuration;
00097   mAllDay = other.mAllDay;
00098   mHasDuration = other.mHasDuration;
00099   mComments = other.mComments;
00100 
00101   mAttendees.clearAll();
00102   Attendee::List::ConstIterator it;
00103   for ( it = other.mAttendees.begin(); it != other.mAttendees.end(); ++it ) {
00104     mAttendees.append( new Attendee( *(*it) ) );
00105   }
00106 }
00107 //@endcond
00108 
00109 IncidenceBase::IncidenceBase()
00110  : d( new KCal::IncidenceBase::Private )
00111 {
00112   mReadOnly = false;
00113 
00114   setUid( CalFormat::createUniqueId() );
00115 }
00116 
00117 IncidenceBase::IncidenceBase( const IncidenceBase &i )
00118  : CustomProperties( i ),
00119    d( new KCal::IncidenceBase::Private( *i.d ) )
00120 {
00121   mReadOnly = i.mReadOnly;
00122 }
00123 
00124 IncidenceBase::~IncidenceBase()
00125 {
00126   delete d;
00127 }
00128 
00129 IncidenceBase &IncidenceBase::operator=( const IncidenceBase &other )
00130 {
00131   CustomProperties::operator=( other );
00132   d->init( *other.d );
00133   mReadOnly = other.mReadOnly;
00134   return *this;
00135 }
00136 
00137 bool IncidenceBase::operator==( const IncidenceBase &i2 ) const
00138 {
00139   if ( attendees().count() != i2.attendees().count() ) {
00140     return false; // no need to check further
00141   }
00142 
00143   Attendee::List al1 = attendees();
00144   Attendee::List al2 = i2.attendees();
00145   Attendee::List::ConstIterator a1 = al1.begin();
00146   Attendee::List::ConstIterator a2 = al2.begin();
00147   //TODO Does the order of attendees in the list really matter?
00148   //Please delete this comment if you know it's ok, kthx
00149   for ( ; a1 != al1.end() && a2 != al2.end(); ++a1, ++a2 ) {
00150     if ( !( **a1 == **a2 ) ) {
00151       return false;
00152     }
00153   }
00154 
00155   if ( !CustomProperties::operator == (i2) ) {
00156     return false;
00157   }
00158 
00159   return
00160     dtStart() == i2.dtStart() &&
00161     organizer() == i2.organizer() &&
00162     uid() == i2.uid() &&
00163     // Don't compare lastModified, otherwise the operator is not
00164     // of much use. We are not comparing for identity, after all.
00165     allDay() == i2.allDay() &&
00166     duration() == i2.duration() &&
00167     hasDuration() == i2.hasDuration();
00168   // no need to compare mObserver
00169 }
00170 
00171 void IncidenceBase::setUid( const QString &uid )
00172 {
00173   d->mUid = uid;
00174   updated();
00175 }
00176 
00177 QString IncidenceBase::uid() const
00178 {
00179   return d->mUid;
00180 }
00181 
00182 void IncidenceBase::setLastModified( const KDateTime &lm )
00183 {
00184   // DON'T! updated() because we call this from
00185   // Calendar::updateEvent().
00186 
00187   // Convert to UTC and remove milliseconds part.
00188   KDateTime current = lm.toUtc();
00189   QTime t = current.time();
00190   t.setHMS( t.hour(), t.minute(), t.second(), 0 );
00191   current.setTime( t );
00192 
00193   d->mLastModified = current;
00194 }
00195 
00196 KDateTime IncidenceBase::lastModified() const
00197 {
00198   return d->mLastModified;
00199 }
00200 
00201 void IncidenceBase::setOrganizer( const Person &o )
00202 {
00203   // we don't check for readonly here, because it is
00204   // possible that by setting the organizer we are changing
00205   // the event's readonly status...
00206   d->mOrganizer = o;
00207 
00208   updated();
00209 }
00210 
00211 void IncidenceBase::setOrganizer( const QString &o )
00212 {
00213   QString mail( o );
00214   if ( mail.startsWith( "MAILTO:", Qt::CaseInsensitive ) ) {
00215     mail = mail.remove( 0, 7 );
00216   }
00217 
00218   // split the string into full name plus email.
00219   const Person organizer = Person::fromFullName( mail );
00220   setOrganizer( organizer );
00221 }
00222 
00223 Person IncidenceBase::organizer() const
00224 {
00225   return d->mOrganizer;
00226 }
00227 
00228 void IncidenceBase::setReadOnly( bool readOnly )
00229 {
00230   mReadOnly = readOnly;
00231 }
00232 
00233 void IncidenceBase::setDtStart( const KDateTime &dtStart )
00234 {
00235 //  if ( mReadOnly ) return;
00236   d->mDtStart = dtStart;
00237   d->mAllDay = dtStart.isDateOnly();
00238   updated();
00239 }
00240 
00241 KDateTime IncidenceBase::dtStart() const
00242 {
00243   return d->mDtStart;
00244 }
00245 
00246 QString IncidenceBase::dtStartTimeStr( bool shortfmt, const KDateTime::Spec &spec ) const
00247 {
00248   if ( spec.isValid() ) {
00249 
00250     QString timeZone;
00251     if ( spec.timeZone() != KSystemTimeZones::local() ) {
00252       timeZone = ' ' + spec.timeZone().name();
00253     }
00254 
00255     return KGlobal::locale()->formatTime( dtStart().toTimeSpec( spec ).time(), shortfmt )
00256       + timeZone;
00257   } else {
00258     return KGlobal::locale()->formatTime( dtStart().time(), shortfmt );
00259   }
00260 }
00261 
00262 QString IncidenceBase::dtStartDateStr( bool shortfmt, const KDateTime::Spec &spec ) const
00263 {
00264   if ( spec.isValid() ) {
00265 
00266     QString timeZone;
00267     if ( spec.timeZone() != KSystemTimeZones::local() ) {
00268       timeZone = ' ' + spec.timeZone().name();
00269     }
00270 
00271     return KGlobal::locale()->formatDate(
00272       dtStart().toTimeSpec( spec ).date(), ( shortfmt ? KLocale::ShortDate : KLocale::LongDate ) )
00273       + timeZone;
00274   } else {
00275     return KGlobal::locale()->formatDate(
00276       dtStart().date(), ( shortfmt ? KLocale::ShortDate : KLocale::LongDate ) );
00277   }
00278 }
00279 
00280 QString IncidenceBase::dtStartStr( bool shortfmt, const KDateTime::Spec &spec ) const
00281 {
00282   if ( allDay() ) {
00283     return dtStartDateStr( shortfmt, spec );
00284   }
00285 
00286   if ( spec.isValid() ) {
00287 
00288     QString timeZone;
00289     if ( spec.timeZone() != KSystemTimeZones::local() ) {
00290       timeZone = ' ' + spec.timeZone().name();
00291     }
00292 
00293     return KGlobal::locale()->formatDateTime(
00294       dtStart().toTimeSpec( spec ).dateTime(),
00295       ( shortfmt ? KLocale::ShortDate : KLocale::LongDate ) ) + timeZone;
00296   } else {
00297     return KGlobal::locale()->formatDateTime(
00298       dtStart().dateTime(),
00299       ( shortfmt ? KLocale::ShortDate : KLocale::LongDate ) );
00300   }
00301 }
00302 
00303 bool IncidenceBase::allDay() const
00304 {
00305   return d->mAllDay;
00306 }
00307 
00308 void IncidenceBase::setAllDay( bool f )
00309 {
00310   if ( mReadOnly || f == d->mAllDay ) {
00311     return;
00312   }
00313   d->mAllDay = f;
00314   updated();
00315 }
00316 
00317 void IncidenceBase::shiftTimes( const KDateTime::Spec &oldSpec,
00318                                 const KDateTime::Spec &newSpec )
00319 {
00320   d->mDtStart = d->mDtStart.toTimeSpec( oldSpec );
00321   d->mDtStart.setTimeSpec( newSpec );
00322   updated();
00323 }
00324 
00325 void IncidenceBase::addComment( const QString &comment )
00326 {
00327   d->mComments += comment;
00328 }
00329 
00330 bool IncidenceBase::removeComment( const QString &comment )
00331 {
00332   bool found = false;
00333   QStringList::Iterator i;
00334 
00335   for ( i = d->mComments.begin(); !found && i != d->mComments.end(); ++i ) {
00336     if ( (*i) == comment ) {
00337       found = true;
00338       d->mComments.erase( i );
00339     }
00340   }
00341 
00342   return found;
00343 }
00344 
00345 void IncidenceBase::clearComments()
00346 {
00347   d->mComments.clear();
00348 }
00349 
00350 QStringList IncidenceBase::comments() const
00351 {
00352   return d->mComments;
00353 }
00354 
00355 void IncidenceBase::addAttendee( Attendee *a, bool doupdate )
00356 {
00357   if ( mReadOnly ) {
00358     return;
00359   }
00360 
00361   if ( a->name().left(7).toUpper() == "MAILTO:" ) {
00362     a->setName( a->name().remove( 0, 7 ) );
00363   }
00364 
00365   d->mAttendees.append( a );
00366   if ( doupdate ) {
00367     updated();
00368   }
00369 }
00370 
00371 const Attendee::List &IncidenceBase::attendees() const
00372 {
00373   return d->mAttendees;
00374 }
00375 
00376 int IncidenceBase::attendeeCount() const
00377 {
00378   return d->mAttendees.count();
00379 }
00380 
00381 void IncidenceBase::clearAttendees()
00382 {
00383   if ( mReadOnly ) {
00384     return;
00385   }
00386   qDeleteAll( d->mAttendees );
00387   d->mAttendees.clear();
00388 }
00389 
00390 Attendee *IncidenceBase::attendeeByMail( const QString &email ) const
00391 {
00392   Attendee::List::ConstIterator it;
00393   for ( it = d->mAttendees.begin(); it != d->mAttendees.end(); ++it ) {
00394     if ( (*it)->email() == email ) {
00395       return *it;
00396     }
00397   }
00398 
00399   return 0;
00400 }
00401 
00402 Attendee *IncidenceBase::attendeeByMails( const QStringList &emails,
00403                                           const QString &email ) const
00404 {
00405   QStringList mails = emails;
00406   if ( !email.isEmpty() ) {
00407     mails.append( email );
00408   }
00409 
00410   Attendee::List::ConstIterator itA;
00411   for ( itA = d->mAttendees.begin(); itA != d->mAttendees.end(); ++itA ) {
00412     for ( QStringList::Iterator it = mails.begin(); it != mails.end(); ++it ) {
00413       if ( (*itA)->email() == (*it) ) {
00414         return *itA;
00415       }
00416     }
00417   }
00418 
00419   return 0;
00420 }
00421 
00422 Attendee *IncidenceBase::attendeeByUid( const QString &uid ) const
00423 {
00424   Attendee::List::ConstIterator it;
00425   for ( it = d->mAttendees.begin(); it != d->mAttendees.end(); ++it ) {
00426     if ( (*it)->uid() == uid ) {
00427       return *it;
00428     }
00429   }
00430 
00431   return 0;
00432 }
00433 
00434 void IncidenceBase::setDuration( const Duration &duration )
00435 {
00436   d->mDuration = duration;
00437   setHasDuration( true );
00438   updated();
00439 }
00440 
00441 Duration IncidenceBase::duration() const
00442 {
00443   return d->mDuration;
00444 }
00445 
00446 void IncidenceBase::setHasDuration( bool hasDuration )
00447 {
00448   d->mHasDuration = hasDuration;
00449 }
00450 
00451 bool IncidenceBase::hasDuration() const
00452 {
00453   return d->mHasDuration;
00454 }
00455 
00456 void IncidenceBase::registerObserver( IncidenceBase::IncidenceObserver *observer )
00457 {
00458   if ( !d->mObservers.contains( observer ) ) {
00459     d->mObservers.append( observer );
00460   }
00461 }
00462 
00463 void IncidenceBase::unRegisterObserver( IncidenceBase::IncidenceObserver *observer )
00464 {
00465   d->mObservers.removeAll( observer );
00466 }
00467 
00468 void IncidenceBase::updated()
00469 {
00470   if ( d->mUpdateGroupLevel ) {
00471     d->mUpdatedPending = true;
00472   } else {
00473     foreach ( IncidenceObserver *o, d->mObservers ) {
00474       o->incidenceUpdated( this );
00475     }
00476   }
00477 }
00478 
00479 void IncidenceBase::startUpdates()
00480 {
00481   ++d->mUpdateGroupLevel;
00482 }
00483 
00484 void IncidenceBase::endUpdates()
00485 {
00486   if ( d->mUpdateGroupLevel > 0 ) {
00487     if ( --d->mUpdateGroupLevel == 0 && d->mUpdatedPending ) {
00488       d->mUpdatedPending = false;
00489       updated();
00490     }
00491   }
00492 }
00493 
00494 void IncidenceBase::customPropertyUpdated()
00495 {
00496   updated();
00497 }
00498 
00499 KUrl IncidenceBase::uri() const
00500 {
00501   return KUrl( QString( "urn:x-ical:" ) + uid() );
00502 }
00503 
00504 bool IncidenceBase::Visitor::visit( Event *event )
00505 {
00506   Q_UNUSED( event );
00507   return false;
00508 }
00509 
00510 bool IncidenceBase::Visitor::visit( Todo *todo )
00511 {
00512   Q_UNUSED( todo );
00513   return false;
00514 }
00515 
00516 bool IncidenceBase::Visitor::visit( Journal *journal )
00517 {
00518   Q_UNUSED( journal );
00519   return false;
00520 }
00521 
00522 bool IncidenceBase::Visitor::visit( FreeBusy *freebusy )
00523 {
00524   Q_UNUSED( freebusy );
00525   return false;
00526 }

KCal Library

Skip menu "KCal Library"
  • Main Page
  • Namespace List
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Namespace Members
  • Class Members
  • Related Pages

KDE-PIM Libraries

Skip menu "KDE-PIM Libraries"
  • akonadi
  • kabc
  • kblog
  • kcal
  • kimap
  • kioslave
  •   imap4
  •   mbox
  • kldap
  • kmime
  • kpimidentities
  • kpimutils
  • kresources
  • ktnef
  • kxmlrpcclient
  • mailtransport
  • qgpgme
  • syndication
  •   atom
  •   rdf
  •   rss2
Generated for KDE-PIM Libraries by doxygen 1.5.6
This website is maintained by Adriaan de Groot and Allen Winter.
KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal