--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/email/mail/PluginSrc/icalviewer/uisrc/CICalViewer.cpp Thu Dec 17 08:44:11 2009 +0200
@@ -0,0 +1,649 @@
+/*
+* Copyright (c) 2002-2006 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: ICalendar viewer ECOM plugin
+*
+*/
+
+
+// INCLUDE FILES
+
+#include "CICalViewer.h"
+#include "CICalViewerView.h"
+#include "MailLog.h"
+#include "ICalViewer.hrh"
+#include "icalvieweruid.h"
+#include <avkon.hrh>
+#include "cicalattaloader.h"
+#include <MRCommands.hrh>
+
+// SYSTEM INCLUDES
+#include <stringloader.h>
+#include <MsgEditorView.h> // CMsgEditorView
+#include <FeatMgr.h>
+#include <icalvieweruires.rsg>
+#include <MsgMailViewer.rsg>
+#include <MMSVATTACHMENTMANAGER.H>
+#include <msgmailviewer.hrh>
+#include <CMSVATTACHMENT.H>
+#include <APGCLI.H>
+#include <calsession.h>
+#include <CALENTRY.H> //calendar api V2
+#include <MAgnEntryUi.h> //entry ui params
+#include <MsgMailUIDs.h> //mail viewer application uid
+#include <CMailMessage.h> //mail
+#include <e32des16.h> //HBufC
+#include <caluser.h> //CCalAttendee
+#include <calalarm.h> //CCalAlarm
+#include <calrrule.h> //TCalRRule
+#include <e32std.h>
+#include <e32base.h>
+#include <CalenImporter.h> // import/export for ical files
+#include <SendUiConsts.h> //MTM uid constants for resolver params
+
+
+// CONSTANTS
+/// Unnamed namespace for local definitions
+namespace {
+
+_LIT(KICalUiResourceFile, "icalvieweruires.rsc");
+_LIT8(KDataTypeVCalendar2, "text/x-vCalendar"); // vCalendar v1.0 MIME type
+_LIT8(KDataTypeVCalendar3, "text/calendar"); // vCalendar v2.0 MIME type
+
+enum TStatusFlags
+ {
+ EFlagRecognized = KBit0,
+ EFlagIsUnread = KBit1, // MsgEditor sets unread flag to EFalse too early!
+ EFlagIsNavigableForward = KBit2,
+ EFlagIsNavigableBackward = KBit3,
+ };
+
+} // namespace
+
+
+// ============================ MEMBER FUNCTIONS ===============================
+
+// -----------------------------------------------------------------------------
+// CICalViewer::CICalViewer
+// C++ default constructor can NOT contain any code, that
+// might leave.
+// -----------------------------------------------------------------------------
+//
+CICalViewer::CICalViewer(): iFlags(0)
+ {
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ConstructL
+// Symbian 2nd phase constructor can leave.
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::ConstructL()
+ {
+ LOG("CICalViewer::ConstructL");
+ FeatureManager::InitializeLibL();
+
+ TFileName driveName;
+ DoGetCorrectDllDriveL( driveName );
+ TInt nameLength = driveName.Length() + KICalUiResourceFile().Length();
+ LOG1("CICalViewer::ConstructL: namelength: %d", nameLength);
+ iResourceFile = HBufC::NewL( KMaxFileName );
+ *iResourceFile = driveName;
+ iResourceFile->Des().Append( KICalUiResourceFile );
+
+ LOG("CICalViewer::ConstructL -> End");
+ }
+// -----------------------------------------------------------------------------
+// CICalViewer::NewL
+// Two-phased constructor.
+// -----------------------------------------------------------------------------
+//
+CICalViewer* CICalViewer::NewL()
+ {
+ CICalViewer* self = new(ELeave) CICalViewer();
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::~CICalViewer()
+// Destructor
+// -----------------------------------------------------------------------------
+//
+CICalViewer::~CICalViewer()
+ {
+ LOG("CICalViewer::~CICalViewer");
+ delete iResourceFile;
+ delete iAttaLoad;
+ delete iICalView;
+ FeatureManager::UnInitializeLib();
+ iEntries.ResetAndDestroy();
+ delete iIdleLauncher;
+ delete iImporter;
+ delete iEntryUiInParams;
+ delete iEntryUiOutParams;
+ delete iSession;
+ LOG("CICalViewer::~CICalViewer -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ViewMessageL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::ViewMessageL( RFileReadStream& aReadStream,
+ MMailAppUiInterface& aUICallBack)
+ {
+ LOG("CICalViewer::ViewMessageL (BVA)");
+
+ if (!iAppUi)
+ {
+ iAppUi = &aUICallBack;
+ }
+
+ if ( !iSession )
+ {
+ iSession = CCalSession::NewL();
+ }
+
+ TRAPD( err, iSession->OpenL( iSession->DefaultFileNameL() ) );
+ if ( err == KErrNotFound )
+ {
+ iSession->CreateCalFileL( iSession->DefaultFileNameL() );
+ iSession->OpenL( iSession->DefaultFileNameL() );
+ }
+ else
+ {
+ User::LeaveIfError( err );
+ }
+
+ if ( !iImporter )
+ {
+ iImporter = CCalenImporter::NewL( *iSession );
+ }
+
+ LOG("CICalViewer::ViewMessageL, starting iCal importing");
+ iImporter->ImportICalendarL( aReadStream, iEntries );
+
+ if( iEntries.Count() == 0 )
+ {
+ User::Leave( KErrNotFound );
+ }
+
+ LOG("CICalViewer:: ...importing finished");
+
+ LOG("CICalViewer::ViewMessageL, creating AgnEntryUi");
+ iEntryUiInParams = new(ELeave) MAgnEntryUi::TAgnEntryUiInParams(
+ TUid::Uid( KUidBVAApplication ),
+ *iSession,
+ MAgnEntryUi::EViewEntry );
+
+ LOG("CICalViewer::ViewMessageL, launching viewer");
+ // In case of BVA we can always launch the default AgnEntryUi
+ // -> this can be achieved by giving SMTP mtm uid
+ DoViewMessageL( KSenduiMtmSmtpUid );
+ LOG("CICalViewer::ViewMessageL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ParseMessageToCalEntryL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::ParseMessageToCalEntryL( CMailMessage& aMessage )
+ {
+ LOG("CICalViewer::ParseMessageToCalEntryL");
+ if ( !iSession )
+ {
+ iSession = CCalSession::NewL();
+ }
+
+ TRAPD( err, iSession->OpenL( iSession->DefaultFileNameL() ) );
+ if ( err == KErrNotFound )
+ {
+ iSession->CreateCalFileL( iSession->DefaultFileNameL() );
+ iSession->OpenL( iSession->DefaultFileNameL() );
+ }
+ else
+ {
+ User::LeaveIfError( err );
+ }
+
+ LOG("CICalViewer::ParseMessageToCalEntryL, checking attachment info");
+
+ MMsvAttachmentManager& attachmentManager =
+ aMessage.AttachmentManager();
+
+ TInt attaCount = attachmentManager.AttachmentCount();
+
+ if ( attaCount > 0 )
+ {
+ CMsvAttachment* info = attachmentManager.GetAttachmentInfoL(0);
+ CleanupStack::PushL(info);
+
+ const TDesC& filePath = info->FilePath();
+
+ RFile attachment = attachmentManager.GetAttachmentFileL( 0 );
+ CleanupClosePushL( attachment ); // RFile must be closed
+
+ RFileReadStream stream( attachment, 0 );
+ CleanupClosePushL( stream );
+
+ if ( !iImporter )
+ {
+ iImporter = CCalenImporter::NewL( *iSession );
+ }
+
+ LOG("CICalViewer:: starting iCal importing");
+ iImporter->ImportICalendarL( stream, iEntries );
+
+ if( iEntries.Count() == 0 )
+ {
+ User::Leave( KErrNotFound );
+ }
+
+ LOG("CICalViewer:: ...importing finished");
+
+ //checking of ical entry on rudimentary level
+ //so that we can make a leave here...
+ //even so... the ical cant be launched from plain text viewer
+ //only the alternative description text is shown to user
+
+ CCalEntry& entry = *( iEntries[0] );
+ switch ( entry.MethodL() )
+ {
+ case CCalEntry::EMethodNone:
+ case CCalEntry::EMethodPublish:
+ case CCalEntry::EMethodAdd:
+ case CCalEntry::EMethodRefresh:
+ case CCalEntry::EMethodCounter:
+ case CCalEntry::EMethodDeclineCounter:
+ {
+ User::Leave( KErrNotSupported );
+ }
+ }
+
+ CleanupStack::PopAndDestroy( 3 ); // CSI: 47 # stream, attachment, info
+ }
+ LOG("CICalViewer::ParseMessageToCalEntryL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ViewMessageL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::ViewMessageL(
+ CMailMessage& aMessage,
+ MMailAppUiInterface& aUICallBack,
+ TUint& aParam )
+ {
+ LOG("CICalViewer::ViewMessageL (mail)");
+
+ aParam |= EMailUseDefaultNaviPane;
+
+ iMsg = aMessage.MessageEntry();
+
+ if (!iAppUi)
+ {
+ iAppUi = &aUICallBack;
+ }
+
+ LOG("CICalViewer::ViewMessageL, creating AgnEntryUi");
+ iEntryUiInParams = new(ELeave) MAgnEntryUi::TAgnEntryUiInParams(
+ TUid::Uid( KUidMsgMailViewer ),
+ *iSession,
+ MAgnEntryUi::EViewEntry );
+
+ iEntryUiInParams->iMailBoxId = iMsg.iServiceId;
+ iEntryUiInParams->iMsgSession = aMessage.Session();
+ iEntryUiInParams->iMessageId = iMsg.Id();
+
+ // Load attachments, otherwise they won't be visible in the
+ // attachement manager. CICalViewer::MessageLoadL() received
+ // also attachments ready signal, but attachment manager was
+ // resetted after that.
+ if ( !iAttaLoad )
+ {
+ iAttaLoad = CICalAttaLoader::NewL( *iAppUi );
+ }
+ iAttaLoad->StartLoadingL( aMessage );
+
+ LOG("CICalViewer::ViewMessageL, launching viewer");
+ DoViewMessageL( iMsg.iMtm );
+ LOG("CICalViewer::ViewMessageL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::IdleTimerCallbackL
+// This method must be leaving so that exiting from viewer
+// is possible (done using basched.h KLeaveExit)
+// -----------------------------------------------------------------------------
+//
+TInt CICalViewer::IdleTimerCallbackL(TAny* aViewer) // CSI: 40 # We must return
+ // the integer value although this
+ // is a leaving method.
+ {
+ CICalViewer* thisViewer = static_cast<CICalViewer*>( aViewer );
+ TRAPD( err, thisViewer->DoOMRViewerLaunchL() );
+ if ( err != KErrNone )
+ {
+ LOG("CIcalViewer::IdleTimerCallback, leave occurred, exiting");
+ thisViewer->iAppUi->AppUiHandleCommandL( EAknSoftkeyBack );
+ }
+ return EFalse;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::DoOMRViewerLaunchL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::DoOMRViewerLaunchL()
+ {
+ LOG("CICalViewer::DoOMRViewerLaunchL");
+ iEntryUiOutParams = new(ELeave) MAgnEntryUi::TAgnEntryUiOutParams();
+ ASSERT( iSession );
+
+ LOG("CICalViewer::DoOMRViewerLaunchL, executing viewer");
+ iRetVal = iICalView->ExecuteViewL( iEntries,
+ *iEntryUiInParams,
+ *iEntryUiOutParams,
+ *this );
+ LOG("CICalViewer::DoOMRViewerLaunchL, viewer finished");
+ //we need to call back to ui for exiting the mail application
+ iAppUi->AppUiHandleCommandL( EAknSoftkeyBack );
+
+ LOG("CICalViewer::DoOMRViewerLaunchL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::DoGetCorrectDllDriveL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::DoGetCorrectDllDriveL( TFileName& aDriveName )
+ {
+ TParse parse;
+ Dll::FileName( aDriveName );
+ User::LeaveIfError( parse.Set( aDriveName, NULL, NULL ) );
+ aDriveName = parse.Drive(); // contains drive, e.g. "c:"
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::DoViewMessageL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::DoViewMessageL( TUid aMtmUid )
+ {
+
+ if ( iAppUi->IsNextMessageAvailableL( ETrue ) )
+ {
+ iFlags |= EFlagIsNavigableForward;
+ }
+
+ if ( iAppUi->IsNextMessageAvailableL( EFalse ) )
+ {
+ iFlags |= EFlagIsNavigableBackward;
+ }
+
+
+ LOG("CICalViewer::DoViewMessageL");
+ iAppUi->SetTitleTextL(R_QTN_MAIL_TITLE_MTG_REQUEST);
+
+ iICalView = CICalViewerView::NewL( aMtmUid );
+
+ LOG("CICalViewer:: adding ical viewer control");
+ iAppUi->AddControlL(*iICalView);
+
+ //idle timer
+ iIdleLauncher = CIdle::NewL(CActive::EPriorityIdle);
+ LOG("CICalViewer:: starting idle launcher");
+ iIdleLauncher->Start(TCallBack(IdleTimerCallbackL,this));
+ LOG("CICalViewer::DoViewMessageL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::DynInitMenuPaneL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::DynInitMenuPaneL(TInt /*aResourceId*/,
+ CEikMenuPane* /*aMenuPane*/)
+ {
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::HandleCommandL
+// -----------------------------------------------------------------------------
+//
+TBool CICalViewer::HandleCommandL(TInt /*aCommand*/)
+ {
+ return EFalse;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::HandleKeyEventL
+// -----------------------------------------------------------------------------
+//
+TKeyResponse CICalViewer::HandleKeyEventL(const TKeyEvent& /*aKeyEvent*/,
+ TEventCode /*aType*/)
+ {
+ return EKeyWasConsumed;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ResourceFile
+// -----------------------------------------------------------------------------
+//
+const TDesC& CICalViewer::ResourceFile()
+ {
+ return *iResourceFile;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::MessageLoadL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::MessageLoadL( TInt aState, CMailMessage& aMessage )
+ {
+ LOG("CICalViewer::MessageLoadL");
+ switch (aState)
+ {
+ case CMailMessage::EHeaderReady:
+ {
+ LOG("CICalViewer::aState == EHeaderReady");
+ // This switch case doesn't seem to ever get called
+ break;
+ }
+ case CMailMessage::EAttachmentsReady:
+ {
+ LOG("CICalViewer::aState == EAttachmentsReady");
+
+ if ( !aMessage.MessageEntry().ICalendar() )
+ { // check that the entry is ical message
+ LOG("TMsvEmailEntry::ICalendar() returned EFalse");
+ User::Leave( KErrUnknown );
+ }
+
+ RFile attachment;
+ TInt count = aMessage.AttachmentManager().AttachmentCount();
+
+ if ( count > 0 )
+ {
+ attachment =
+ aMessage.AttachmentManager().GetAttachmentFileL( 0 );
+ CleanupClosePushL( attachment );
+
+ RApaLsSession apaSession;
+ User::LeaveIfError( apaSession.Connect() );
+ CleanupClosePushL( apaSession );
+ TUid appUID( KNullUid );
+ TDataType dataType;
+ // Check only first attachment
+ User::LeaveIfError( apaSession.AppForDocument( attachment,
+ appUID,
+ dataType ) );
+ CleanupStack::PopAndDestroy( 2 ); // CSI: 47 # apaSession, attachment
+
+ if ( dataType.Des8().FindF(
+ KDataTypeVCalendar2 ) != KErrNotFound ||
+ dataType.Des8().FindF(
+ KDataTypeVCalendar3 ) != KErrNotFound )
+ {
+ LOG("CICalViewer::starting msg parsing");
+ //we can do attachment parsing only here as
+ //attachment manager is resetted after this
+
+ ParseMessageToCalEntryL( aMessage );
+
+ iFlags |= EFlagRecognized;
+ LOG("CICalViewer::recognized!");
+ }
+ else
+ {
+ LOG("CICalViewer::datatype unknown");
+ // unknown
+ User::Leave( KErrUnknown );
+ }
+ }
+ else
+ {
+ User::Leave( KErrUnknown );
+ }
+ break;
+ }
+ case CMailMessage::ELoadEnd:
+ {
+ LOG("CICalViewer::aState == ELoadEnd");
+ if ( !(iFlags & EFlagRecognized) )
+ {
+ // Not valid message
+ User::Leave( KErrUnknown );
+ }
+ if ( aMessage.IsNew() )
+ {
+ iFlags |= EFlagIsUnread;
+ }
+ break;
+ }
+ default:
+ {
+ // do nothing
+ break;
+ }
+ }
+ LOG("CICalViewer::MessageLoadL -> End");
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::IsCommandAvailable
+// -----------------------------------------------------------------------------
+//
+TBool CICalViewer::IsCommandAvailable( TInt aCommandId )
+ {
+ TBool retVal( EFalse );
+ switch ( aCommandId )
+ {
+ case EMRCommandRetrieve:
+ {
+ retVal = iMsg.PartialDownloaded();
+ break;
+ }
+ case EMRCommandAttachments:
+ {
+ retVal = ( iAttaLoad && iAttaLoad->FinishedWithAttachments() );
+ break;
+ }
+ case EMRCommandUnreadOpeningNote:
+ {
+ retVal = ( ( iFlags & EFlagIsUnread ) != 0 );
+ break;
+ }
+ case EMRCommandNavigateBackward:
+ {
+ retVal = ( ( iFlags & EFlagIsNavigableBackward ) != 0 );
+ }
+ case EMRCommandNavigateForward:
+ {
+ retVal = ( ( iFlags & EFlagIsNavigableForward ) != 0 );
+ break;
+ }
+ default:
+ {
+ break;
+ }
+ }
+ return retVal;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ProcessCommandWithResultL
+// -----------------------------------------------------------------------------
+//
+TInt CICalViewer::ProcessCommandWithResultL( TInt aCommandId ) // CSI: 40 # We must return
+ // the integer value although this
+ // is a leaving method.
+ {
+ LOG("CICalViewer::ProcessCommandWithResultL -> End");
+ TInt retVal( KErrNone );
+ switch ( aCommandId )
+ {
+ case EMRCommandForward:
+ {
+ LOG("Calling AppUiHandleCommandL with forward cmd...");
+ iAppUi->AppUiHandleCommandL( EMsgMailViewerCmdForward );
+ break;
+ }
+ case EMRCommandRetrieve:
+ {
+ iAppUi->AppUiHandleCommandL( EMsgMailViewerCmdRetrieve );
+ break;
+ }
+ case EMRCommandAttachments:
+ {
+ iAppUi->AppUiHandleCommandL( EMsgMailViewerCmdAttachments );
+ break;
+ }
+ case EMRCommandMessageDetails:
+ {
+ iAppUi->AppUiHandleCommandL( EMsgMailViewerCmdMessageInfo );
+ break;
+ }
+ case EMRCommandNavigateBackward:
+ {
+ iAppUi->NextMessageL( EFalse );
+ break;
+ }
+ case EMRCommandNavigateForward:
+ {
+ iAppUi->NextMessageL( ETrue );
+ break;
+ }
+ default:
+ {
+ User::Leave( KErrNotSupported );
+ return KErrNotSupported;
+ }
+ }
+ LOG("CICalViewer::ProcessCommandWithResultL -> End");
+ return retVal;
+ }
+
+// -----------------------------------------------------------------------------
+// CICalViewer::ProcessCommandL
+// -----------------------------------------------------------------------------
+//
+void CICalViewer::ProcessCommandL( TInt aCommandId )
+ {
+ ProcessCommandWithResultL( aCommandId );
+ }
+
+// End of File
+