• Skip to content
  • Skip to link menu
  • KDE API Reference
  • kdepimlibs-4.8.3 API Reference
  • KDE Home
  • Contact Us
 

KTNEF Library

formatter.cpp
Go to the documentation of this file.
00001 /*
00002     Copyright (c) 2001 Cornelius Schumacher <schumacher@kde.org>
00003     Copyright (c) 2004 Reinhold Kainhofer <reinhold@kainhofer.com>
00004     Copyright (c) 2005 Rafal Rzepecki <divide@users.sourceforge.net>
00005 
00006     This library is free software; you can redistribute it and/or
00007     modify it under the terms of the GNU Library General Public
00008     License as published by the Free Software Foundation; either
00009     version 2 of the License, or (at your option) any later version.
00010 
00011     This library is distributed in the hope that it will be useful,
00012     but WITHOUT ANY WARRANTY; without even the implied warranty of
00013     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014     Library General Public License for more details.
00015 
00016     You should have received a copy of the GNU Library General Public License
00017     along with this library; see the file COPYING.LIB.  If not, write to
00018     the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00019     Boston, MA 02110-1301, USA.
00020 */
00035 #include "formatter.h"
00036 #include "ktnefparser.h"
00037 #include "ktnefmessage.h"
00038 #include "ktnefdefs.h"
00039 
00040 #include <kpimutils/email.h>
00041 #include <kabc/phonenumber.h>
00042 #include <kabc/vcardconverter.h>
00043 
00044 #ifndef KDEPIM_NO_KCAL
00045 #include <kcal/incidenceformatter.h>
00046 #include <kcal/calendar.h>
00047 #endif
00048 
00049 #include <kcalcore/calendar.h>
00050 #include <kcalcore/icalformat.h>
00051 #include <kcalutils/incidenceformatter.h>
00052 
00053 #include <klocale.h>
00054 #include <kdatetime.h>
00055 
00056 #include <QtCore/QBuffer>
00057 
00058 #include <time.h>
00059 
00060 using namespace KCalCore;
00061 using namespace KTnef;
00062 
00063 /*******************************************************************
00064  *  Helper functions for the msTNEF -> VPart converter
00065  *******************************************************************/
00066 
00067 //-----------------------------------------------------------------------------
00068 //@cond IGNORE
00069 static QString stringProp( KTNEFMessage *tnefMsg, const quint32 &key,
00070                            const QString &fallback = QString() )
00071 {
00072   return tnefMsg->findProp( key < 0x10000 ? key & 0xFFFF : key >> 16, fallback );
00073 }
00074 
00075 static QString sNamedProp( KTNEFMessage *tnefMsg, const QString &name,
00076                            const QString &fallback = QString() )
00077 {
00078   return tnefMsg->findNamedProp( name, fallback );
00079 }
00080 
00081 struct save_tz {
00082   char *old_tz;
00083   char *tz_env_str;
00084 };
00085 
00086 /* temporarily go to a different timezone */
00087 static struct save_tz set_tz( const char *_tc )
00088 {
00089   const char *tc = _tc?_tc:"UTC";
00090 
00091   struct save_tz rv;
00092 
00093   rv.old_tz = 0;
00094   rv.tz_env_str = 0;
00095 
00096   //kDebug() << "set_tz(), timezone before =" << timezone;
00097 
00098   char *tz_env = 0;
00099   if ( !qgetenv( "TZ" ).isEmpty() ) {
00100     tz_env = qstrdup( qgetenv( "TZ" ) );
00101     rv.old_tz = tz_env;
00102   }
00103   char *tmp_env = (char*)malloc( strlen( tc ) + 4 );
00104   strcpy( tmp_env, "TZ=" );
00105   strcpy( tmp_env+3, tc );
00106   putenv( tmp_env );
00107 
00108   rv.tz_env_str = tmp_env;
00109 
00110   /* tmp_env is not free'ed -- it is part of the environment */
00111 
00112   tzset();
00113   //kDebug() << "set_tz(), timezone after =" << timezone;
00114 
00115   return rv;
00116 }
00117 
00118 /* restore previous timezone */
00119 static void unset_tz( struct save_tz old_tz )
00120 {
00121   if ( old_tz.old_tz ) {
00122     char *tmp_env = (char*)malloc( strlen( old_tz.old_tz ) + 4 );
00123     strcpy( tmp_env, "TZ=" );
00124     strcpy( tmp_env+3, old_tz.old_tz );
00125     putenv( tmp_env );
00126     /* tmp_env is not free'ed -- it is part of the environment */
00127     free( old_tz.old_tz );
00128   } else {
00129     /* clear TZ from env */
00130     putenv( strdup( "TZ" ) );
00131   }
00132   tzset();
00133 
00134   /* is this OK? */
00135   if ( old_tz.tz_env_str ) {
00136     free( old_tz.tz_env_str );
00137   }
00138 }
00139 
00140 static KDateTime utc2Local( const KDateTime &utcdt )
00141 {
00142   struct tm tmL;
00143 
00144   save_tz tmp_tz = set_tz( "UTC" );
00145   time_t utc = utcdt.toTime_t();
00146   unset_tz( tmp_tz );
00147 
00148   localtime_r( &utc, &tmL );
00149   return KDateTime( QDate( tmL.tm_year + 1900, tmL.tm_mon + 1, tmL.tm_mday ),
00150                     QTime( tmL.tm_hour, tmL.tm_min, tmL.tm_sec ) );
00151 }
00152 
00153 static KDateTime pureISOToLocalQDateTime( const QString &dtStr,
00154                                           bool bDateOnly = false )
00155 {
00156   QDate tmpDate;
00157   QTime tmpTime;
00158   int year, month, day, hour, minute, second;
00159 
00160   if ( bDateOnly ) {
00161     year = dtStr.left( 4 ).toInt();
00162     month = dtStr.mid( 4, 2 ).toInt();
00163     day = dtStr.mid( 6, 2 ).toInt();
00164     hour = 0;
00165     minute = 0;
00166     second = 0;
00167   } else {
00168     year = dtStr.left( 4 ).toInt();
00169     month = dtStr.mid( 4, 2 ).toInt();
00170     day = dtStr.mid( 6, 2 ).toInt();
00171     hour = dtStr.mid( 9, 2 ).toInt();
00172     minute = dtStr.mid( 11, 2 ).toInt();
00173     second = dtStr.mid( 13, 2 ).toInt();
00174   }
00175   tmpDate.setYMD( year, month, day );
00176   tmpTime.setHMS( hour, minute, second );
00177 
00178   if ( tmpDate.isValid() && tmpTime.isValid() ) {
00179     KDateTime dT = KDateTime( tmpDate, tmpTime );
00180 
00181     if ( !bDateOnly ) {
00182       // correct for GMT ( == Zulu time == UTC )
00183       if ( dtStr.at( dtStr.length() - 1 ) == 'Z' ) {
00184         //dT = dT.addSecs( 60 * KRFCDate::localUTCOffset() );
00185         //localUTCOffset( dT ) );
00186         dT = utc2Local( dT );
00187       }
00188     }
00189     return dT;
00190   } else {
00191     return KDateTime();
00192   }
00193 }
00194 //@endcond
00195 
00196 QString KTnef::msTNEFToVPart( const QByteArray &tnef )
00197 {
00198   bool bOk = false;
00199 
00200   KTNEFParser parser;
00201   QByteArray b( tnef );
00202   QBuffer buf( &b );
00203   MemoryCalendar::Ptr cal( new MemoryCalendar( KDateTime::UTC ) );
00204   KABC::Addressee addressee;
00205   ICalFormat calFormat;
00206   Event::Ptr event( new Event() );
00207 
00208   if ( parser.openDevice( &buf ) ) {
00209     KTNEFMessage *tnefMsg = parser.message();
00210     //QMap<int,KTNEFProperty*> props = parser.message()->properties();
00211 
00212     // Everything depends from property PR_MESSAGE_CLASS
00213     // (this is added by KTNEFParser):
00214     QString msgClass = tnefMsg->findProp( 0x001A, QString(), true ).toUpper();
00215     if ( !msgClass.isEmpty() ) {
00216       // Match the old class names that might be used by Outlook for
00217       // compatibility with Microsoft Mail for Windows for Workgroups 3.1.
00218       bool bCompatClassAppointment = false;
00219       bool bCompatMethodRequest = false;
00220       bool bCompatMethodCancled = false;
00221       bool bCompatMethodAccepted = false;
00222       bool bCompatMethodAcceptedCond = false;
00223       bool bCompatMethodDeclined = false;
00224       if ( msgClass.startsWith( QLatin1String( "IPM.MICROSOFT SCHEDULE." ) ) ) {
00225         bCompatClassAppointment = true;
00226         if ( msgClass.endsWith( QLatin1String( ".MTGREQ" ) ) ) {
00227           bCompatMethodRequest = true;
00228         }
00229         if ( msgClass.endsWith( QLatin1String( ".MTGCNCL" ) ) ) {
00230           bCompatMethodCancled = true;
00231         }
00232         if ( msgClass.endsWith( QLatin1String( ".MTGRESPP" ) ) ) {
00233           bCompatMethodAccepted = true;
00234         }
00235         if ( msgClass.endsWith( QLatin1String( ".MTGRESPA" ) ) ) {
00236           bCompatMethodAcceptedCond = true;
00237         }
00238         if ( msgClass.endsWith( QLatin1String( ".MTGRESPN" ) ) ) {
00239           bCompatMethodDeclined = true;
00240         }
00241       }
00242       bool bCompatClassNote = ( msgClass == "IPM.MICROSOFT MAIL.NOTE" );
00243 
00244       if ( bCompatClassAppointment || "IPM.APPOINTMENT" == msgClass ) {
00245         // Compose a vCal
00246         bool bIsReply = false;
00247         QString prodID = "-//Microsoft Corporation//Outlook ";
00248         prodID += tnefMsg->findNamedProp( "0x8554", "9.0" );
00249         prodID += "MIMEDIR/EN\n";
00250         prodID += "VERSION:2.0\n";
00251         calFormat.setApplication( "Outlook", prodID );
00252 
00253         iTIPMethod method;
00254         if ( bCompatMethodRequest ) {
00255           method = iTIPRequest;
00256         } else if ( bCompatMethodCancled ) {
00257           method = iTIPCancel;
00258         } else if ( bCompatMethodAccepted || bCompatMethodAcceptedCond ||
00259                  bCompatMethodDeclined ) {
00260           method = iTIPReply;
00261           bIsReply = true;
00262         } else {
00263           // pending(khz): verify whether "0x0c17" is the right tag ???
00264           //
00265           // at the moment we think there are REQUESTS and UPDATES
00266           //
00267           // but WHAT ABOUT REPLIES ???
00268           //
00269           //
00270 
00271           if ( tnefMsg->findProp(0x0c17) == "1" ) {
00272             bIsReply = true;
00273           }
00274           method = iTIPRequest;
00275         }
00276 
00278         ScheduleMessage schedMsg( event, method, ScheduleMessage::Unknown );
00279 
00280         QString sSenderSearchKeyEmail( tnefMsg->findProp( 0x0C1D ) );
00281 
00282         if ( !sSenderSearchKeyEmail.isEmpty() ) {
00283           int colon = sSenderSearchKeyEmail.indexOf( ':' );
00284           // May be e.g. "SMTP:KHZ@KDE.ORG"
00285           if ( sSenderSearchKeyEmail.indexOf( ':' ) == -1 ) {
00286             sSenderSearchKeyEmail.remove( 0, colon+1 );
00287           }
00288         }
00289 
00290         QString s( tnefMsg->findProp( 0x8189 ) );
00291         const QStringList attendees = s.split( ';' );
00292         if ( attendees.count() ) {
00293           for ( QStringList::const_iterator it = attendees.begin();
00294                it != attendees.end(); ++it ) {
00295             // Skip all entries that have no '@' since these are
00296             // no mail addresses
00297             if ( (*it).indexOf( '@' ) == -1 ) {
00298               s = (*it).trimmed();
00299 
00300               Attendee::Ptr attendee( new Attendee( s, s, true ) );
00301               if ( bIsReply ) {
00302                 if ( bCompatMethodAccepted ) {
00303                   attendee->setStatus( Attendee::Accepted );
00304                 }
00305                 if ( bCompatMethodDeclined ) {
00306                   attendee->setStatus( Attendee::Declined );
00307                 }
00308                 if ( bCompatMethodAcceptedCond ) {
00309                   attendee->setStatus( Attendee::Tentative );
00310                 }
00311               } else {
00312                 attendee->setStatus( Attendee::NeedsAction );
00313                 attendee->setRole( Attendee::ReqParticipant );
00314               }
00315               event->addAttendee( attendee );
00316             }
00317           }
00318         } else {
00319           // Oops, no attendees?
00320           // This must be old style, let us use the PR_SENDER_SEARCH_KEY.
00321           s = sSenderSearchKeyEmail;
00322           if ( !s.isEmpty() ) {
00323             Attendee::Ptr attendee( new Attendee( QString(), QString(), true ) );
00324             if ( bIsReply ) {
00325               if ( bCompatMethodAccepted ) {
00326                 attendee->setStatus( Attendee::Accepted );
00327               }
00328               if ( bCompatMethodAcceptedCond ) {
00329                 attendee->setStatus( Attendee::Declined );
00330               }
00331               if ( bCompatMethodDeclined ) {
00332                 attendee->setStatus( Attendee::Tentative );
00333               }
00334             } else {
00335               attendee->setStatus( Attendee::NeedsAction );
00336               attendee->setRole( Attendee::ReqParticipant );
00337             }
00338             event->addAttendee( attendee );
00339           }
00340         }
00341         s = tnefMsg->findProp( 0x3ff8 ); // look for organizer property
00342         if ( s.isEmpty() && !bIsReply ) {
00343           s = sSenderSearchKeyEmail;
00344         }
00345         // TODO: Use the common name?
00346         if ( !s.isEmpty() ) {
00347           event->setOrganizer( s );
00348         }
00349 
00350         s = tnefMsg->findProp( 0x819b ).remove( QChar( '-' ) ).remove( QChar( ':' ) );
00351         event->setDtStart( KDateTime::fromString( s ) ); // ## Format??
00352 
00353         s = tnefMsg->findProp( 0x819c ).remove( QChar( '-' ) ).remove( QChar( ':' ) );
00354         event->setDtEnd( KDateTime::fromString( s ) );
00355 
00356         s = tnefMsg->findProp( 0x810d );
00357         event->setLocation( s );
00358         // is it OK to set this to OPAQUE always ??
00359         //vPart += "TRANSP:OPAQUE\n"; ###FIXME, portme!
00360         //vPart += "SEQUENCE:0\n";
00361 
00362         // is "0x0023" OK  -  or should we look for "0x0003" ??
00363         s = tnefMsg->findProp( 0x0023 );
00364         event->setUid( s );
00365 
00366         // PENDING(khz): is this value in local timezone? Must it be
00367         // adjusted? Most likely this is a bug in the server or in
00368         // Outlook - we ignore it for now.
00369         s = tnefMsg->findProp( 0x8202 ).remove( QChar( '-' ) ).remove( QChar( ':' ) );
00370         // ### kcal always uses currentDateTime()
00371         // event->setDtStamp( QDateTime::fromString( s ) );
00372 
00373         s = tnefMsg->findNamedProp( "Keywords" );
00374         event->setCategories( s );
00375 
00376         s = tnefMsg->findProp( 0x1000 );
00377         event->setDescription( s );
00378 
00379         s = tnefMsg->findProp( 0x0070 );
00380         event->setSummary( s );
00381 
00382         s = tnefMsg->findProp( 0x0026 );
00383         event->setPriority( s.toInt() );
00384         // is reminder flag set ?
00385         if ( !tnefMsg->findProp( 0x8503 ).isEmpty() ) {
00386           Alarm::Ptr alarm( new Alarm( event.data() ) ); // KDAB_TODO, fix when KCalCore::Alarm is fixed
00387           KDateTime highNoonTime =
00388             pureISOToLocalQDateTime( tnefMsg->findProp( 0x8502 ).
00389                                      remove( QChar( '-' ) ).remove( QChar( ':' ) ) );
00390           KDateTime wakeMeUpTime =
00391             pureISOToLocalQDateTime( tnefMsg->findProp( 0x8560, "" ).
00392                                      remove( QChar( '-' ) ).remove( QChar( ':' ) ) );
00393           alarm->setTime( wakeMeUpTime );
00394 
00395           if ( highNoonTime.isValid() && wakeMeUpTime.isValid() ) {
00396             alarm->setStartOffset( Duration( highNoonTime, wakeMeUpTime ) );
00397           } else {
00398             // default: wake them up 15 minutes before the appointment
00399             alarm->setStartOffset( Duration( 15 * 60 ) );
00400           }
00401           alarm->setDisplayAlarm( i18n( "Reminder" ) );
00402 
00403           // Sorry: the different action types are not known (yet)
00404           //        so we always set 'DISPLAY' (no sounds, no images...)
00405           event->addAlarm( alarm );
00406         }
00407         //ensure we have a uid for this event
00408         if ( event->uid().isEmpty() ) {
00409           event->setUid( CalFormat::createUniqueId() );
00410         }
00411         cal->addEvent( event );
00412         bOk = true;
00413         // we finished composing a vCal
00414       } else if ( bCompatClassNote || "IPM.CONTACT" == msgClass ) {
00415         addressee.setUid( stringProp( tnefMsg, attMSGID ) );
00416         addressee.setFormattedName( stringProp( tnefMsg, MAPI_TAG_PR_DISPLAY_NAME ) );
00417         addressee.insertEmail( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_EMAIL1EMAILADDRESS ), true );
00418         addressee.insertEmail( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_EMAIL2EMAILADDRESS ), false );
00419         addressee.insertEmail( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_EMAIL3EMAILADDRESS ), false );
00420         addressee.insertCustom( "KADDRESSBOOK", "X-IMAddress",
00421                                 sNamedProp( tnefMsg, MAPI_TAG_CONTACT_IMADDRESS ) );
00422         addressee.insertCustom( "KADDRESSBOOK", "X-SpousesName",
00423                                 stringProp( tnefMsg, MAPI_TAG_PR_SPOUSE_NAME ) );
00424         addressee.insertCustom( "KADDRESSBOOK", "X-ManagersName",
00425                                 stringProp( tnefMsg, MAPI_TAG_PR_MANAGER_NAME ) );
00426         addressee.insertCustom( "KADDRESSBOOK", "X-AssistantsName",
00427                                 stringProp( tnefMsg, MAPI_TAG_PR_ASSISTANT ) );
00428         addressee.insertCustom( "KADDRESSBOOK", "X-Department",
00429                                 stringProp( tnefMsg, MAPI_TAG_PR_DEPARTMENT_NAME ) );
00430         addressee.insertCustom( "KADDRESSBOOK", "X-Office",
00431                                 stringProp( tnefMsg, MAPI_TAG_PR_OFFICE_LOCATION ) );
00432         addressee.insertCustom( "KADDRESSBOOK", "X-Profession",
00433                                 stringProp( tnefMsg, MAPI_TAG_PR_PROFESSION ) );
00434 
00435         QString s = tnefMsg->findProp( MAPI_TAG_PR_WEDDING_ANNIVERSARY ).
00436                     remove( QChar( '-' ) ).remove( QChar( ':' ) );
00437         if ( !s.isEmpty() ) {
00438           addressee.insertCustom( "KADDRESSBOOK", "X-Anniversary", s );
00439         }
00440 
00441         addressee.setUrl( KUrl( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_WEBPAGE ) ) );
00442 
00443         // collect parts of Name entry
00444         addressee.setFamilyName( stringProp( tnefMsg, MAPI_TAG_PR_SURNAME ) );
00445         addressee.setGivenName( stringProp( tnefMsg, MAPI_TAG_PR_GIVEN_NAME ) );
00446         addressee.setAdditionalName( stringProp( tnefMsg, MAPI_TAG_PR_MIDDLE_NAME ) );
00447         addressee.setPrefix( stringProp( tnefMsg, MAPI_TAG_PR_DISPLAY_NAME_PREFIX ) );
00448         addressee.setSuffix( stringProp( tnefMsg, MAPI_TAG_PR_GENERATION ) );
00449 
00450         addressee.setNickName( stringProp( tnefMsg, MAPI_TAG_PR_NICKNAME ) );
00451         addressee.setRole( stringProp( tnefMsg, MAPI_TAG_PR_TITLE ) );
00452         addressee.setOrganization( stringProp( tnefMsg, MAPI_TAG_PR_COMPANY_NAME ) );
00453         /*
00454         the MAPI property ID of this (multiline) )field is unknown:
00455         vPart += stringProp(tnefMsg, "\n","NOTE", ... , "" );
00456         */
00457 
00458         KABC::Address adr;
00459         adr.setPostOfficeBox( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_PO_BOX ) );
00460         adr.setStreet( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_STREET ) );
00461         adr.setLocality( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_CITY ) );
00462         adr.setRegion( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_STATE_OR_PROVINCE ) );
00463         adr.setPostalCode( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_POSTAL_CODE ) );
00464         adr.setCountry( stringProp( tnefMsg, MAPI_TAG_PR_HOME_ADDRESS_COUNTRY ) );
00465         adr.setType( KABC::Address::Home );
00466         addressee.insertAddress( adr );
00467 
00468         adr.setPostOfficeBox( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSPOBOX ) );
00469         adr.setStreet( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSSTREET ) );
00470         adr.setLocality( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSCITY ) );
00471         adr.setRegion( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSSTATE ) );
00472         adr.setPostalCode( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSPOSTALCODE ) );
00473         adr.setCountry( sNamedProp( tnefMsg, MAPI_TAG_CONTACT_BUSINESSADDRESSCOUNTRY ) );
00474         adr.setType( KABC::Address::Work );
00475         addressee.insertAddress( adr );
00476 
00477         adr.setPostOfficeBox( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_PO_BOX ) );
00478         adr.setStreet( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_STREET ) );
00479         adr.setLocality( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_CITY ) );
00480         adr.setRegion( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_STATE_OR_PROVINCE ) );
00481         adr.setPostalCode( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_POSTAL_CODE ) );
00482         adr.setCountry( stringProp( tnefMsg, MAPI_TAG_PR_OTHER_ADDRESS_COUNTRY ) );
00483         adr.setType( KABC::Address::Dom );
00484         addressee.insertAddress( adr );
00485 
00486         // problem: the 'other' address was stored by KOrganizer in
00487         //          a line looking like the following one:
00488         // vPart += "\nADR;TYPE=dom;TYPE=intl;TYPE=parcel;TYPE=postal;TYPE=work;"
00489         //          "TYPE=home:other_pobox;;other_str1\nother_str2;other_loc;other_region;"
00490         //          "other_pocode;other_country"
00491 
00492         QString nr;
00493         nr = stringProp( tnefMsg, MAPI_TAG_PR_HOME_TELEPHONE_NUMBER );
00494         addressee.insertPhoneNumber(
00495           KABC::PhoneNumber( nr, KABC::PhoneNumber::Home ) );
00496         nr = stringProp( tnefMsg, MAPI_TAG_PR_BUSINESS_TELEPHONE_NUMBER );
00497         addressee.insertPhoneNumber(
00498           KABC::PhoneNumber( nr, KABC::PhoneNumber::Work ) );
00499         nr = stringProp( tnefMsg, MAPI_TAG_PR_MOBILE_TELEPHONE_NUMBER );
00500         addressee.insertPhoneNumber(
00501           KABC::PhoneNumber( nr, KABC::PhoneNumber::Cell ) );
00502         nr = stringProp( tnefMsg, MAPI_TAG_PR_HOME_FAX_NUMBER );
00503         addressee.insertPhoneNumber(
00504           KABC::PhoneNumber( nr, KABC::PhoneNumber::Fax | KABC::PhoneNumber::Home ) );
00505         nr = stringProp( tnefMsg, MAPI_TAG_PR_BUSINESS_FAX_NUMBER );
00506         addressee.insertPhoneNumber(
00507           KABC::PhoneNumber( nr, KABC::PhoneNumber::Fax | KABC::PhoneNumber::Work ) );
00508 
00509         s = tnefMsg->findProp( MAPI_TAG_PR_BIRTHDAY ).
00510             remove( QChar( '-' ) ).remove( QChar( ':' ) );
00511         if ( !s.isEmpty() ) {
00512           addressee.setBirthday( QDateTime::fromString( s ) );
00513         }
00514 
00515         bOk = ( !addressee.isEmpty() );
00516       } else if ( "IPM.NOTE" == msgClass ) {
00517 
00518       } // else if ... and so on ...
00519     }
00520   }
00521 
00522   // Compose return string
00523   // KDAB_TODO: Interesting, without the explicit QString the toString call is
00524   //            reported to be ambigious with toString( const Incidence::Ptr & ).
00525   const QString iCal = calFormat.toString( cal, QString() );
00526   if ( !iCal.isEmpty() ) {
00527     // This was an iCal
00528     return iCal;
00529   }
00530 
00531   // Not an iCal - try a vCard
00532   KABC::VCardConverter converter;
00533   return QString::fromUtf8( converter.createVCard( addressee ) );
00534 }
00535 
00536 #ifndef KDEPIM_NO_KCAL
00537 QString KTnef::formatTNEFInvitation( const QByteArray &tnef,
00538                                      KCal::Calendar *cal,
00539                                      KCal::InvitationFormatterHelper *h )
00540 {
00541   QString vPart = msTNEFToVPart( tnef );
00542   QString iCal = KCal::IncidenceFormatter::formatICalInvitation( vPart, cal, h );
00543   if ( !iCal.isEmpty() ) {
00544     return iCal;
00545   } else {
00546     return vPart;
00547   }
00548 }
00549 #endif
00550 
00551 QString KTnef::formatTNEFInvitation( const QByteArray &tnef,
00552                                      const MemoryCalendar::Ptr &cal,
00553                                      KCalUtils::InvitationFormatterHelper *h )
00554 {
00555   const QString vPart = msTNEFToVPart( tnef );
00556   QString iCal = KCalUtils::IncidenceFormatter::formatICalInvitation( vPart, cal, h, true );
00557   if ( !iCal.isEmpty() ) {
00558     return iCal;
00559   } else {
00560     return vPart;
00561   }
00562 }
00563 
This file is part of the KDE documentation.
Documentation copyright © 1996-2012 The KDE developers.
Generated on Mon May 14 2012 05:12:27 by doxygen 1.7.5 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.

KTNEF Library

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

kdepimlibs-4.8.3 API Reference

Skip menu "kdepimlibs-4.8.3 API Reference"
  • akonadi
  •   contact
  •   kmime
  • kabc
  • kalarmcal
  • kblog
  • kcal
  • kcalcore
  • kcalutils
  • kholidays
  • kimap
  • kioslave
  •   imap4
  •   mbox
  •   nntp
  • kldap
  • kmbox
  • kmime
  • kontactinterface
  • kpimidentities
  • kpimtextedit
  •   richtextbuilders
  • kpimutils
  • kresources
  • ktnef
  • kxmlrpcclient
  • mailtransport
  • microblog
  • qgpgme
  • syndication
  •   atom
  •   rdf
  •   rss2
Report problems with this website to our bug tracking system.
Contact the specific authors with questions and comments about the page contents.

KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal