diff -r e52958d06c29 -r 5fd161fa28b6 svgtviewer/SvgtViewerPlugin/AppObserverUtilSrc/SVGTAppObserverUtil.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/svgtviewer/SvgtViewerPlugin/AppObserverUtilSrc/SVGTAppObserverUtil.cpp Thu Sep 09 11:17:40 2010 +0300 @@ -0,0 +1,2441 @@ +/* +* Copyright (c) 2004,2005 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: This class provides helper functions and a reference +* implementation for hyperlink handling, image fetching +* and saving of the svg content. +* +*/ + + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef __SERIES60_NATIVE_BROWSER +#include // Include only if s60 native + // browser available +#endif + +#include +#include // TApaTaskList +#include // RApaLsSession +#include +#include // CApDataHandler +#include // CApAccessPointItem +#include // CApUtils +#include // CApSelect +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include //TImCodecB64 +#include + +#include "SVGTViewerAppDbgFlags.hrh" +#include "SVGTViewerAppDownloads.h" +#include "SVGTAppObserver.h" // temp +#include "SVGTUIDialog.h" // AppDialog +#include "SVGTUIDialog.hrh" + +#ifdef RD_MULTIPLE_DRIVE +#include +#endif +// CONSTANTS + +_LIT( KBrowserParameter, "4" ); // magic number for browser to open the URL +_LIT( KSpace, " " ); + +_LIT(KJpg, ".jpg" ); +_LIT(KJpeg, ".jpeg" ); +_LIT(KPng, ".png" ); +_LIT(KBmp, ".bmp" ); +_LIT(KSvg, ".svg" ); +_LIT(KSvgz, ".svgz" ); + +#ifndef __SERIES60_NATIVE_BROWSER + // Below constants need to be used if s60 native browser is not used. + const TUid KCRUidBrowser = {0x10008D39}; + const TUint32 KBrowserDefaultAccessPoint = 0x0000000E; +#endif // __S60_REMOVE_BROWSER + +// SMIL Fit Value +_LIT( KSvgtDefSmilFitValue,"meet" ); +// Resource file for App Observer Util +_LIT( KResourceFileName, "Z:SVGTAppObserverUtil.rsc" ); + +_LIT( KEmptyString, "" ); +_LIT( KWww, "www" ); +_LIT( KHttp, "http://"); +_LIT( KDotDot, ".." ); +_LIT( KBSlashStr, "/" ); +_LIT( KSlashStr, "\\" ); +_LIT( KDotSlashStr, ".\\" ); +_LIT( KColonStr, ":" ); +_LIT( KNewLineStr, "\n" ); + +#ifdef SVGTVIEWERAPP_DBG_FLAG +_LIT( KFileLoggingDir, "SVGTViewer" ); +_LIT( KFileLog, "SaveLog.txt" ); +#endif + +// Maximum length of thread Id in Characters +const TInt KSvgMaxThreadIdStr = 10; + +// ============================ MEMBER FUNCTIONS =============================== + + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::NewL +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +EXPORT_C CSVGTAppObserverUtil* CSVGTAppObserverUtil::NewL( + CSVGTUIDialog* aAppDialog, + RFile* aFileHdlPtr, + const TDesC& aFilename, + TBool aIsFileFullPathAvailable, + TBool aCanSaveContent, + TBool aShouldMoveContent) + { + CSVGTAppObserverUtil* self = + CSVGTAppObserverUtil::NewLC( aAppDialog, + aFileHdlPtr, + aFilename, + aIsFileFullPathAvailable, + aCanSaveContent, + aShouldMoveContent ); + CleanupStack::Pop( self ); + return self; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::NewLC +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +CSVGTAppObserverUtil* CSVGTAppObserverUtil::NewLC( CSVGTUIDialog* aAppDialog, + RFile* aFileHdlPtr, + const TDesC& aFilename, + TBool aIsFileFullPathAvailable, + TBool aCanSaveContent, + TBool aShouldMoveContent) + { + CSVGTAppObserverUtil* self = + new( ELeave ) CSVGTAppObserverUtil( aAppDialog ); + CleanupStack::PushL( self ); + self->ConstructL( aFileHdlPtr, aFilename, aIsFileFullPathAvailable, + aCanSaveContent, aShouldMoveContent ); + return self; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::NewL +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +EXPORT_C CSVGTAppObserverUtil* CSVGTAppObserverUtil::NewL( + CSVGTUIDialog* aAppDialog, + RFile* aFileHdlPtr ) + { + CSVGTAppObserverUtil* self = + CSVGTAppObserverUtil::NewLC( aAppDialog, + aFileHdlPtr ); + CleanupStack::Pop( self ); + return self; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::NewLC +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +CSVGTAppObserverUtil* CSVGTAppObserverUtil::NewLC( + CSVGTUIDialog* aAppDialog, + RFile* aFileHdlPtr ) + { + CSVGTAppObserverUtil* self = + new( ELeave ) CSVGTAppObserverUtil( aAppDialog ); + CleanupStack::PushL( self ); + + self->ConstructL( aFileHdlPtr ); + return self; + } + +// ----------------------------------------------------------------------------- +// Destructor +// ----------------------------------------------------------------------------- +EXPORT_C CSVGTAppObserverUtil::~CSVGTAppObserverUtil() + { + +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + + CSVGTViewerAppDownloads* downloads; + + iDownloadIter.SetToFirst(); + while ((downloads = iDownloadIter++) != NULL) + { + downloads->QueLink().Deque(); + delete downloads; + iDownloadIter.SetToFirst(); + } + + // Close the DMgr UI Library first, as it uses the same + // Download Manager session that the Viewer uses + delete iDMgrUiReg; + + // Close the Download Manager connection + iDownloadMgr.Close(); + + iDMgrDownloadsList = NULL; + iDMgrUserInteractions = NULL; +#endif + // Reset the app dialog, it is already freed in OpenFileL + iAppDialog = NULL; + + delete iFileManager; + delete iSvgFileName; + delete iSvgDstFileName; + delete iDocHandler; + + delete iWaitNote; + delete iTempFileName; + if ( iResourceOffset != 0 ) + { + iEikEnv->DeleteResourceFile( iResourceOffset ); + } + + // Reset the SVG File Handle as it is owned by the caller + iSvgFileId = NULL; + // Reset the Progress Info implementor pointer + iProgressInfo = NULL; + // Reset Environment pointer + iEikEnv = NULL; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::FetchImage +// Called by Svg engine when there is an image tag encountered in the svg file +// parameters: +// aUri: the uri that needs to be downloaded or fetched locally +// aSession: File Session in which the file is opened. +// aFileHandle: handle of the downloaded file or locally fetched file. +// return value: +// KErrNone if the file is fetched successfully +// KErrNotFound if the file could not be fetched. +// ----------------------------------------------------------------------------- +// +EXPORT_C TInt CSVGTAppObserverUtil::FetchImage( + const TDesC& aUri , RFs& aSession , + RFile& aFileHandle ) + { + TInt ret = KErrNone; + + TDownloadNeeded downloadNeeded = ELocalImageFile; + TRAPD( error, downloadNeeded = IsDownloadNeededL( aUri ) ); + + if ( error != KErrNone ) + { + return KErrNotFound; + } + + if ( downloadNeeded == ELocalImageFile ) + { + TFileName fileName; + if ( GetLocalFile( aUri, fileName, *iSvgFileName ) ) + { + return aFileHandle.Open( aSession, fileName, EFileShareAny ); + } + else + { + return KErrNotFound; + } + } + else if ( downloadNeeded == ERemoteImageFile ) + { + TRAPD( err,ret = StartDownloadingImageL( aUri, + aSession, + aFileHandle, + EFalse, + EFalse /* Asynchronous mode */) ); + if ( err != KErrNone ) + { + return KErrNotFound; + } + else + { + return ret; + } + + } + else + { + return KErrNotFound; + } + + } + +TInt CSVGTAppObserverUtil::FetchFont( const TDesC& /* aUri */, + RFs& /* aSession */, RFile& /* aFileHandle */ ) + { + return KErrNotSupported; + } + +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::LinkActivated +// Callback Function called by svg engine when a hyperlink is activated +// --------------------------------------------------------------------------- +// + +EXPORT_C TBool CSVGTAppObserverUtil::LinkActivated( const TDesC& aUri ) + { + if( aUri.Length() == 0 ) + { + return KErrNone; + } + TRAPD( error, LinkActivatedL( aUri ) ); + return ( error == KErrNone ); + } + + +// -------------------------------------------------------------------- +// CSVGTAppObserverUtil::LinkActivatedWithShow +// Callback Function called by the svg engine when a hyperlink with show +// attribute is activated +// -------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::LinkActivatedWithShow( + const TDesC& aUri , + const TDesC& aShow ) + { + if( aUri.Length() == 0 ) + { + return KErrNone; + } + TRAPD( error, LinkActivatedWithShowL( aUri, aShow ) ); + return ( error == KErrNone ); + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetSmilFitValue +// Default implementation for observer function to get SMIL fit value. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::GetSmilFitValue( TDes& aSmilValue ) + { + aSmilValue.Copy( KSvgtDefSmilFitValue ); + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SetDownloadMenu +// Sets/Unsets the iDownloadMenuEnabled +// ----------------------------------------------------------------------------- +// + +EXPORT_C void CSVGTAppObserverUtil::SetDownloadMenu( TBool aAddDownloadMenu ) + { + iDownloadMenuEnabled = aAddDownloadMenu; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SetDownloadMenu +// Sets/Unsets the iDownloadMenuEnabled +// ----------------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::CanShowDownload() const + { + if(iDownloadInProgress || iDownloadDone) + { + const CDownloadArray& array = iDownloadMgr.CurrentDownloads(); + return ( array.Count() ? ETrue : EFalse ); + } + + return EFalse; + } + +// -------------------------------------------------------------------- +// void CSVGTAppObserverUtil::DisplayDownloadMenuL() +// Call back called by the UI dialog when the downloads menu is +// selected. This function calls the DisplayDownloadsListL function +// provided by the download manager ui lib. +// -------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::DisplayDownloadMenuL() + { +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + if ( iDMgrDownloadsList ) + { + TRAPD( error, iDMgrDownloadsList->DisplayDownloadsListL() ); + { + if ( error != KErrNone ) + { +#ifdef _DEBUG + TBuf<64> buffer; + _LIT(msg, "AP error : %d" ); + buffer.Format( msg, error ); + iEikEnv->InfoMsg( buffer ); +#endif + } + } + } +#endif + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::HandleDMgrEventL +// Called by Download manager when the image is being downloaded. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::HandleDMgrEventL( RHttpDownload& aDownload, + THttpDownloadEvent aEvent ) + { + +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + +#ifdef _DEBUG + TBuf<64> buffer; + _LIT(msg, "download progressing : %d, %d" ); + buffer.Format( msg, aEvent.iDownloadState, aEvent.iProgressState ); + iEikEnv->InfoMsg( buffer ); +#endif + { + + if ( EHttpDlInprogress == aEvent.iDownloadState ) + { + iDownloadInProgress = ETrue; + iDownloadDone = EFalse; + } + + if ( EHttpDlCompleted == aEvent.iDownloadState ) + { + + iDownloadInProgress = EFalse; + iDownloadDone = ETrue; + + // Get the download item from the list + CSVGTViewerAppDownloads* downloadItem; + downloadItem = FindDownload( &aDownload ); + +#ifdef _DEBUG + + + _LIT(downloadMsg, "download found" ); + iEikEnv->InfoMsg( downloadMsg ); +#endif + + + if ( downloadItem ) + { + // Get the file Name of the downloaded file + TFileName fileName; + aDownload.GetStringAttribute( EDlAttrDestFilename, fileName ); +#ifdef _DEBUG + + _LIT(fileNameMsg, "got file name " ); + iEikEnv->InfoMsg( fileNameMsg ); +#endif + +//############################################## +// For AssignImageData + DoAssignImageDataL(downloadItem, aDownload); +//############################################## + downloadItem->SetFileName( fileName ); + + // Check whether the download happened in a synchronous way + if ( downloadItem->SynchronousMode() ) + { + downloadItem->SetDownloadCompleted( ETrue ); + + // If wait note is being displayed, delete it + if ( iWaitNote ) + { + // Delete the download wait note + TRAPD( err, iWaitNote->ProcessFinishedL() ); + if ( err != KErrNone ) + { + delete iWaitNote; + iWaitNote = NULL; + } + } + + // If synchronous stop the scheduler + iWait.AsyncStop(); + } + else + { + // Otherwise check the embedded mode and open the file + // using DocHandler + downloadItem->QueLink().Deque(); + delete downloadItem; + } + } + } + else + { + // added for if user cancels the download. + if ( EHttpDlDeleting == aEvent.iDownloadState && !iDownloadDone) + { + aDownload.Pause(); + aEvent.iDownloadState = EHttpDlFailed; + } + + if ( EHttpDlFailed == aEvent.iDownloadState ) + { +#ifdef _DEBUG + + _LIT(failMsg, " downloading failed" ); + iEikEnv->InfoMsg( failMsg ); +#endif + + TInt32 error = 0; + TInt32 globalError = 0; + aDownload.GetIntAttribute( EDlAttrErrorId, error ); + aDownload.GetIntAttribute( EDlAttrGlobalErrorId, globalError ); + +#ifdef _DEBUG + TBuf<64> errorBuffer; + _LIT(failedMsg, "downloading failed : %d, %d" ); + buffer.Format( failedMsg, error, globalError ); + iEikEnv->InfoMsg( errorBuffer ); +#endif + + // Get the download item from the list + CSVGTViewerAppDownloads* downloadItem; + downloadItem = FindDownload( &aDownload ); + // Check whether the download was started synchronously + // if( !downloadItem->ImageLinkFlag()) + { + HBufC* lUriBuf = HBufC::NewLC( KMaxUrlLength ); + TPtr lUriPtr(lUriBuf->Des()); + aDownload.GetStringAttribute( EDlAttrReqUrl, lUriPtr ); + iAppDialog->AssignImageData(lUriPtr , NULL ); + CleanupStack::PopAndDestroy( lUriBuf ); + } + + if ( downloadItem ) + { + if ( downloadItem->SynchronousMode() ) + { + + downloadItem->SetDownloadCompleted( EFalse ); + if ( iWaitNote ) + { + // Delete the download wait note + TRAPD( err, iWaitNote->ProcessFinishedL() ); + if ( err != KErrNone ) + { + delete iWaitNote; + iWaitNote = NULL; + } + } + + // If synchronous, stop the scheduler started. + iWait.AsyncStop(); + } + else + { + // Otherwise delete the download item from the list + downloadItem->QueLink().Deque(); + delete downloadItem; + } + } + } + } + } +#endif + } + +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::LinkActivatedL +// Leave variant of LinkActivated +// Launches the browser in embedded mode and passes the uri to the browser +// if the uri is a web page, if the uri refers to a local image file, or a +// remote image file, launches the file using doc handler. +// --------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::LinkActivatedL( const TDesC& aUri ) + { + + TDownloadNeeded dnloadNeeded = IsDownloadNeededL( aUri ); + + if ( dnloadNeeded == ENotAnImageFile ) + { + + // (2 = length of the first parameter + space) + HBufC* parameters = NULL; + parameters = HBufC::NewLC( aUri.Length() + 2 ); + + TPtr parametersPtr = parameters->Des(); + parametersPtr.Copy( KBrowserParameter ); + parametersPtr.Append( KSpace ); + parametersPtr.Append( aUri ); + + // Create BrowserLauncher + CBrowserLauncher* launcher = NULL; + + launcher = CBrowserLauncher::NewLC(); + + TBrowserOverriddenSettings overriddenSettings; + launcher->LaunchBrowserSyncEmbeddedL( *parameters, NULL, &overriddenSettings ); + + //launcher, parameters + CleanupStack::PopAndDestroy( 2, parameters ); + } + else + { + if ( dnloadNeeded == ERemoteImageFile ) + { + RFile fileHandle; // param not going to be used + RFs fileSession; // param not going to be used + StartDownloadingImageL( aUri, + fileSession, + fileHandle, + EFalse, /* aSynchronous mode */ + ETrue, + ETrue /* Embedded mode */ ); + } + else if ( dnloadNeeded == ELocalImageFile ) + { + + TFileName fileName; + TInt error = KErrNone; + + if ( GetLocalFile( aUri, fileName, *iSvgFileName ) ) + { + TRAP( error, LaunchDownloadedFileL( fileName, ETrue, EFalse ) ); + } + else + { + error = KErrNotFound; + } + + if ( error != KErrNone ) + { + TInt resourceId; + resourceId = R_SVGT_FILE_NOT_FOUND; + // Show information note + HBufC* prompt = StringLoader::LoadLC( resourceId ); + CAknInformationNote* note = + new ( ELeave ) CAknInformationNote( ETrue ); + note->ExecuteLD( *prompt ); + + CleanupStack::PopAndDestroy( prompt ); + } + } + else + { + return; + } + } + } + + +// -------------------------------------------------------------------- +// CSVGTAppObserverUtil::LinkActivatedWithShowL +// Called by LinkActivatedWithShow +// Calls LinkActivatedL +// -------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::LinkActivatedWithShowL( + const TDesC& aUri , + const TDesC& /*aShow*/ ) + { + LinkActivatedL( aUri ); + } +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::StartDownloadingImageL +// Called by FetchImage, LinkActivated, LinkActivatedWithShow to download the +// image. This function calls the download manager client Api's to start the +// download. The download completion will be indicated by the call back +// HandleDownloadMgrEventL. As FetchImage is a synchronous function +// a CActiveSchedulerWait loop is started, after starting the http download. +// the wait loop is stopped when the call back HandleDownloadMgrEventL is +// called. +// 1. CreateDownloadAndSetAttributes +// 2. check result +// If result no +// check the status of the download +// if Completed +// return the filehandle +// if in progress +// continue downloading +// if failed +// return +// else +// Start Download +// 3. If Synchronous +// Start DownloadWaitNote +// Start ActiveSchedulerWait. +// 4. Return +// +// parameters: +// aUri: the hyperlink that needs to be downloaded. +// aSession: File session in which the file handle is opened. +// aFileHandle: Handle of the downloaded file +// aIsSynchronous: flag indicating whether download is synchronous or not +// aLinkFlag: Image flag to distinguish the Embeded & hyperlink. +// aIsEmbedded: flag indicating whether downloaded file has to opened in +// stand alone mode or embedded mode. +// --------------------------------------------------------------------------- +// +TInt CSVGTAppObserverUtil::StartDownloadingImageL( + const TDesC& aUri, + RFs& aSession, + RFile& aFileHandle, + TBool aIsSynchronous, + TBool aLinkFlag, + TBool aIsEmbedded ) + { + +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + + +#if defined(__WINS__) || defined(__WINSCW__) + //do nothing, hard code later on +#else + + + TUint32 Iapid( 0 ); + if ( !GetDefaultInetAccessPointL( Iapid ) ) + { + return KErrNotFound; + } + + + iDownloadMgr.SetIntAttribute( EDlMgrIap, (TInt32)Iapid ); +#endif // __wins__|| __winscw__ + + +#ifdef _DEBUG + _LIT( setAP, "Access point set" ); + iEikEnv->InfoMsg( setAP ); +#endif + + + TInt result = ETrue; + // Add lDownload to cleanup stack and pop it after CreateDownloadL. + CSVGTViewerAppDownloads *lDownload = CSVGTViewerAppDownloads::NewLC( + aIsEmbedded, aIsSynchronous, aLinkFlag ); + + HBufC8* url8 = NULL; + url8 = HBufC8::NewLC( aUri.Length() ); + url8->Des().Copy( aUri ); + + lDownload->SetDownloadHandle( + &iDownloadMgr.CreateDownloadL( *url8 , result ) ); + + CleanupStack::PopAndDestroy( url8 ); // url8 + +#ifdef _DEBUG + _LIT(dlCreated, "download created" ); + iEikEnv->InfoMsg( dlCreated ); +#endif + + + // Add Downloads to the Menu Option + if ( !iDownloadMenuEnabled && !aIsSynchronous ) + { + SetDownloadMenu( ETrue ); + } + + if ( !result ) + { + + // url is already being downloaded or completed + // Get the download State + TInt32 downloadState = 0; + TInt retval = KErrNone; + lDownload->DownloadHandle()->GetIntAttribute( EDlAttrState, + downloadState ); + + if ( downloadState == EHttpDlCompleted ) + { + TFileName fileName; + lDownload->DownloadHandle()->GetStringAttribute( EDlAttrDestFilename + , fileName ); + if ( aIsSynchronous ) + { + retval = aFileHandle.Open( aSession, fileName, EFileShareAny ); + } + else + { + if(aLinkFlag) + { + // Handle Launching downloaded file in asynchronous mode + LaunchDownloadedFileL( fileName, aIsEmbedded , ETrue); + } + else + { + DoAssignImageDataL(lDownload, *(lDownload->DownloadHandle())); + } + + } + + CleanupStack::PopAndDestroy( lDownload ); // lDownload + return retval; + } + else + { + if ( downloadState == EHttpDlFailed ) + { + // Retry + // Add to the linked list + iDownloads.AddFirst( *lDownload ); + CleanupStack::Pop( lDownload ); // lDownload + lDownload->DownloadHandle()->SetBoolAttribute( + EDlAttrNoContentTypeCheck, ETrue ); + // Start the download + lDownload->DownloadHandle()->Start(); + + return KErrNone; + } + else + { + + if ( !FindDownload( lDownload->DownloadHandle() ) ) + { + // Add to the linked list + iDownloads.AddFirst( *lDownload ); + CleanupStack::Pop( lDownload ); // lDownload + } + else + { + CleanupStack::PopAndDestroy( lDownload ); // lDownload + } + } + } + } + else + { + if ( aIsSynchronous ) + { + TFileName fileName( KEmptyString ); + GetFileNameFromUri( aUri, fileName ); + LaunchWaitNoteL( R_SVGT_DOWNLOAD_WAIT_NOTE, ETrue, fileName ); + } + if ( !aIsSynchronous ) + { + lDownload->DownloadHandle()->SetIntAttribute( EDlAttrAction, + lDownload->ImageLinkFlag() ? ELaunch : EDoNothing ); +// iIsFetchImageCall ? EDoNothing : ELaunch ); + } + else + { + lDownload->DownloadHandle()->SetIntAttribute( EDlAttrAction, + EDoNothing ); + lDownload->DownloadHandle()->SetBoolAttribute( EDlAttrSilent, + ETrue ); + } + + lDownload->DownloadHandle()->SetBoolAttribute( + EDlAttrNoContentTypeCheck, ETrue ); + + +#ifdef _DEBUG + _LIT(dlCreateMsg, "result true dl created" ); + iEikEnv->InfoMsg( dlCreateMsg ); +#endif + + // Add to the linked list + iDownloads.AddFirst( *lDownload ); + + CleanupStack::Pop( lDownload ); // lDownload + + // Start the download + lDownload->DownloadHandle()->Start(); + } + + if ( aIsSynchronous ) + { + // Start the Scheduler Wait + if ( !iWait.IsStarted() ) + { + iWait.Start(); + } + +#ifdef _DEBUG + _LIT(waitLoopMsg, "out of wait loop" ); + iEikEnv->InfoMsg( waitLoopMsg ); +#endif + if ( iSynchronousDownloadStopped ) + { + // Download dismissed + // Cancel the download + lDownload->DownloadHandle()->Delete(); + return KErrCancel; + } + + CSVGTViewerAppDownloads* downloadItem = NULL; + downloadItem = FindDownload( lDownload->DownloadHandle() ); + + if ( downloadItem ) + { + TInt retval = KErrNone; + TBool downloadCompleted = downloadItem->DownloadCompleted(); + + if ( downloadCompleted ) + { + retval = aFileHandle.Open( aSession, + downloadItem->FileName(), + EFileShareAny ); + } + else + { + retval = KErrNotFound; + } + + downloadItem->QueLink().Deque(); + delete downloadItem; + return retval; + } + else + { + return KErrNotFound; + } + } + else + { + return KErrNone; + } + +#else + return KErrNotFound; +#endif + + } + +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetDefaultInetAccessPointL +// if the return value is true, aIapId has the default Iap id. +// --------------------------------------------------------------------------- +EXPORT_C TBool CSVGTAppObserverUtil::GetDefaultInetAccessPointL + ( TUint32& aIapId ) const + { + + // Try to find the default AP. + // The Browser may stores the default AP in the shared data. + CRepository* repository = CRepository::NewL( KCRUidBrowser ); + CleanupStack::PushL( repository ); + + TInt wapApId = 0; + TRAPD( error, repository->Get( KBrowserDefaultAccessPoint, wapApId ) ); + if ( error != KErrNone ) + { +#ifdef _DEBUG + TBuf<64> buffer; + _LIT(msg, "AP error : %d" ); + buffer.Format( msg, error ); + iEikEnv->InfoMsg( buffer ); + User::After(1000000); +#endif + return EFalse; + } + TUint32 wapApId32( wapApId ); + TUint32 iapId32( 0 ); + + CleanupStack::PopAndDestroy( repository ); + + CCommsDatabase* commsDb = CCommsDatabase::NewL( EDatabaseTypeIAP ); + CleanupStack::PushL( commsDb ); + CApDataHandler* apDataHandler = CApDataHandler::NewLC( *commsDb ); + CApAccessPointItem* apItem = CApAccessPointItem::NewLC(); + TRAPD( err, apDataHandler->AccessPointDataL( wapApId32, *apItem ) ); + CApUtils* apUtils = CApUtils::NewLC( *commsDb ); + + TBool wapApFound( EFalse ); + TBool iapFound( EFalse ); + + if ( err == KErrNone ) + { + wapApFound = ETrue; + } + else + { + // The first valid access point has to be selected if exists + CApSelect* apSelect = CApSelect::NewLC + ( + *commsDb, + KEApIspTypeAll, + EApBearerTypeAll, + KEApSortNameAscending + ); + if ( apSelect->MoveToFirst() ) + { + wapApFound = ETrue; + wapApId32 = apSelect->Uid(); + } + CleanupStack::PopAndDestroy( apSelect ); // apSelect + } + + if ( wapApFound ) + { + // Get the IAP ID from the WAP AP ID. +#ifndef __SERIES60_WSP + iapId32 = 0; + TRAPD( errTransl, iapId32 = apUtils->IapIdFromWapIdL( wapApId32 ) ); + + if ( errTransl == KErrNone ) + { + iapFound = ETrue; + } +#else + iapId32 = wapApId32; + iapFound = ETrue; +#endif // __SERIES60_WSP + } + + CleanupStack::PopAndDestroy( 4 ); // apUtils, apItem, + // apDataHandler, commsDb + + if ( iapFound ) + { + aIapId = iapId32; + } + return iapFound; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::LaunchDownloadedFileL +// Called by Download manager when the image is downloaded. +// This function uses the document handler to launch the downloaded file. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::LaunchDownloadedFileL( const TDesC& aFileName, + TBool /* aIsEmbedded */, + TBool aAllowSave ) const + { + + TDataType dataType = TDataType(); + RFile fileHandle; + // Creates a sharable file handle + iDocHandler->OpenTempFileL( aFileName, fileHandle ); + CleanupClosePushL( fileHandle ); + if ( aAllowSave ) + { + CAiwGenericParamList& paramList = iDocHandler->InParamListL(); + // To show/hide save confirmation dlg + TAiwVariant allowSaveVariant(aAllowSave); + TAiwGenericParam genericParamAllowSave( EGenericParamAllowSave, + allowSaveVariant ); + paramList.AppendL( genericParamAllowSave ); + + iDocHandler->OpenFileEmbeddedL( fileHandle, dataType, paramList ); + } + else + { + _LIT( KSvgFile, ".svg"); + _LIT( KSvgzFile, ".svgz"); + _LIT( KSvgbFile, ".svgb"); + if(aFileName.Right(4) == KSvgFile || aFileName.Right(5) == KSvgzFile || aFileName.Right(5) == KSvgbFile) + { + iDocHandler->OpenFileEmbeddedL( fileHandle, dataType ); + } + else + { + iDocHandler->OpenFileL( fileHandle, dataType ); + } + } + CleanupStack::PopAndDestroy( &fileHandle ); // fileHandle + } + +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::IsDownloadNeededL +// Called by link activated(WithShow), FetchImage +// to check whether the uri needs a download +// If the filename is present in the uri and if it is a html, +// returns ENotAnImageFile +// If the host is present & filename is not present, +// returns ENotAnImageFile +// If the host is present & filename is present, +// returns ERemoteImageFile +// If the uri doesnt need a download and if it is locally available, +// returns ELocalImageFile +// --------------------------------------------------------------------------- +// +EXPORT_C CSVGTAppObserverUtil::TDownloadNeeded + CSVGTAppObserverUtil::IsDownloadNeededL( + const TDesC& aUri ) + { + + TUriParser UriParser; + + TBuf localUri; + // url starts with www so append http:// + if ( !aUri.Left( 4 ).Compare( KWww ) ) + { + localUri.Append( KHttp ); + localUri.Append( aUri ); + User::LeaveIfError( UriParser.Parse( localUri ) ); + } + else + { + User::LeaveIfError( UriParser.Parse( aUri ) ); + } + + if ( UriParser.IsPresent( EUriHost ) ) + { + // Extract the Path, filename and extension from the uri + TFileName filename = UriParser.Extract( EUriPath ); + TParsePtrC fileParser( filename ); + + if ( fileParser.NamePresent() && fileParser.ExtPresent() ) + { + if ( fileParser.Ext().Compare( KJpg ) == 0 || + fileParser.Ext().Compare( KJpeg ) == 0 || + fileParser.Ext().Compare( KBmp ) == 0 || + fileParser.Ext().Compare( KPng ) == 0 || + fileParser.Ext().Compare( KSvg ) == 0 || + fileParser.Ext().Compare( KSvgz ) == 0 ) + { + // file name and ext present and + // it is amy of the supported image types + return ERemoteImageFile; + } + else + { + //file Extension present but not a supported image ext, + //may be some html file + return ENotAnImageFile; + } + } + else + { + //Should be a domain name so return ENotAnImageFile + return ENotAnImageFile; + } + } + else + { + return ELocalImageFile; + } + } + +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetFileNameFromUri +// This function gets the filename from the uri, +// Returns true if the file name is retrieved +// Returns False if the file name could not be retrieved. +// --------------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::GetFileNameFromUri( const TDesC& aUri, + TDes& aFileName ) const + { + + const TChar KBSlash = '/'; + TUriParser UriParser; + if ( UriParser.Parse( aUri ) != KErrNone ) + { + return EFalse; + } + + if ( UriParser.IsPresent( EUriPath ) ) + { + // Extract the Path, filename and extension from the uri + TFileName filename = UriParser.Extract( EUriPath ); + + TParse fileParser; + fileParser.Set( filename, NULL, NULL ); + + TInt slashPos = filename.LocateReverse( KBSlash ); + if ( slashPos != KErrNotFound ) + { + aFileName = filename.Right( filename.Length() - (slashPos + 1)); + return ETrue; + } + else + { + return EFalse; + } + + } + else + { + return EFalse; + } + + } +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetLocalFile +// This function gets the filename with full path from the uri, +// Returns true if the file name is retrieved +// Returns False if the file name could not be retrieved. +// --------------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::GetLocalFile( + const TDesC& aUri, + TDes& aFileName , + const TDesC& aSvgFileName ) + { + + TBuf copyUri = aUri; + // Before giving the uri to the file parser, + // convert '/' to '\'. + TInt pos; + while( KErrNotFound != ( pos = copyUri.FindF( KBSlashStr ) ) ) + { + copyUri.Replace(pos,1,KSlashStr ); + } + + // if the uri starts with ".\" remove ".\" + if ( copyUri.Left( 2 ).Compare( KDotSlashStr ) == 0 ) + { + copyUri = copyUri.Right( copyUri.Length() - KDotSlashStr().Length() ); + } + + // If the second letter is not ':' + // and if it is not starting with '\', + // and if the path has '/', + // then prepend slash to it. + if ( copyUri.Length() >= 2 && + copyUri.Mid( 1, 1 ).Compare( KColonStr ) != 0 && + copyUri.Mid( 0, 1 ).Compare( KSlashStr ) != 0 && + ( copyUri.Find( KSlashStr ) != KErrNotFound ) ) + { + copyUri.Insert( 0, KSlashStr ); + } + + TParse fileParser; + if( fileParser.Set( copyUri, NULL, NULL ) != KErrNone ) + { + return EFalse; + } + + if ( fileParser.DrivePresent() ) + { + // The uri is an absolute path + aFileName.Append( fileParser.Drive() ); + // Append path, file name and extension from the uri. + if ( fileParser.PathPresent() ) + { + aFileName.Append( fileParser.Path() ); + } + if ( fileParser.NamePresent() ) + { + aFileName.Append( fileParser.Name() ); + } + if ( fileParser.ExtPresent() ) + { + aFileName.Append( fileParser.Ext() ); + } + RFs session; + TInt connectError=session.Connect(); + if(connectError==KErrNone) + { + RFile fileHandle; + TInt openError = fileHandle.Open( session, aFileName, EFileShareReadersOnly); + fileHandle.Close(); + session.Close(); + if ( openError != KErrNone ) + { + return EFalse; + } + return ETrue; + } + session.Close(); + return EFalse; + } + else + { + + TParse svgFilenameParser; + if ( svgFilenameParser.Set( aSvgFileName,NULL,NULL ) != KErrNone ) + { + return EFalse; + } + + if ( svgFilenameParser.DrivePresent() ) + { + aFileName.Append( svgFilenameParser.Drive() ); + } + + TInt dotdotPos = copyUri.Find( KDotDot ); + TInt rightPos = 0; + + if ( dotdotPos != KErrNotFound ) + { + // If ".." is present collapse it with the parent path + if ( svgFilenameParser.PathPresent() ) + { + do + { + if ( dotdotPos > 1 ) + { + svgFilenameParser.AddDir( copyUri.Left(dotdotPos - 1) ); + } + + if ( svgFilenameParser.PopDir() != KErrNone ) + { + return EFalse; + } + + rightPos = (copyUri.Length()) - (dotdotPos + 3); + + if ( rightPos > 0 ) + { + copyUri = copyUri.Right( rightPos ); + } + + }while ( (dotdotPos = copyUri.Find( KDotDot ) ) + != KErrNotFound ); + + aFileName.Append( svgFilenameParser.Path() ); + aFileName.Append( copyUri ); + } + else + { + return EFalse; + } + } + else + { + if ( svgFilenameParser.PathPresent() ) + { + aFileName.Append( svgFilenameParser.Path() ); + } + + // Append path, file name and extension from the uri. + if ( fileParser.PathPresent() ) + { + //deletes an extra slash in aFileName + TInt strlen = aFileName.Length(); + if(aFileName.Mid(strlen-1).Compare(KSlashStr) == 0) + { + aFileName.Delete(strlen-1, 1); + } + aFileName.Append( fileParser.Path() ); + } + + if ( fileParser.NamePresent() ) + { + aFileName.Append( fileParser.Name() ); + } + if ( fileParser.ExtPresent() ) + { + aFileName.Append( fileParser.Ext() ); + } + } + RFs session; + // The error is caught to avoid any code scanner error + TInt connectError=session.Connect(); + if(connectError==KErrNone) + { + RFile fileHandle; + TInt openError = fileHandle.Open(session, aFileName, EFileShareReadersOnly ); + fileHandle.Close(); + session.Close(); + if ( openError != KErrNone ) + { + return EFalse; + } + return ETrue; + } + session.Close(); + return EFalse; + } + } + + +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED +// --------------------------------------------------------------------------- +// CSVGTAppObserverUtil::FindDownload +// This iterates through the linked list and return the link +// corresponding to the given http download handle +// If a link is not found returns NULL. +// --------------------------------------------------------------------------- +// +CSVGTViewerAppDownloads* CSVGTAppObserverUtil::FindDownload( + const RHttpDownload* aHttpDownload ) + { + CSVGTViewerAppDownloads* downloadItem; + TDblQueIter Iter( iDownloads ); + if ( !iDownloads.IsEmpty() ) + { + Iter.SetToFirst(); + while ( ( downloadItem = Iter ) != NULL ) + { + if ( downloadItem->DownloadHandle() == aHttpDownload ) + { + return downloadItem; + } + Iter++; + } + } + return NULL; + } +#endif + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::CSVGTAppObserverUtil +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +EXPORT_C CSVGTAppObserverUtil::CSVGTAppObserverUtil( + CSVGTUIDialog* aAppDialog ) : +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + iDownloads( CSVGTViewerAppDownloads::LinkOffset() ) , + iDownloadIter( iDownloads ), + iDownloadMenuEnabled( EFalse ), // construct header & iterator + iSynchronousDownloadStopped( EFalse ), +#endif + iAppDialog( aAppDialog ), + iSavingDone( EFalse ), + iCommandId( 0 ), +// iIsFetchImageCall(EFalse), + iTempFileUsed( EFalse ), + iDownloadDone( EFalse ), + iDownloadInProgress( EFalse ) + + { + } +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::ConstructL() + { + + // Get the CEikonEnv pointer + iEikEnv = CEikonEnv::Static(); + + // Find which drive this DLL is installed. + TFileName fileName; + + // Get the full resource file + TParse fp; + + // Add the resource dir + fp.Set( KResourceFileName, &KDC_RESOURCE_FILES_DIR, NULL); + + // Get the filename with full path + fileName = fp.FullName(); + + BaflUtils::NearestLanguageFile( iEikEnv->FsSession(), fileName ); //for + // localization + iResourceOffset = iEikEnv->AddResourceFileL( fileName ); + + + // File manager utility needed for saving/moving files. + iFileManager = CSVGTFileManager::NewL(); + + iDocHandler = CDocumentHandler::NewL(); + +#ifdef SVGTVIEWERAPP_DOWNLOADMGR_ENABLED + TUid hostUid = iEikEnv->EikAppUi()->Application()->AppDllUid(); + + //creates a download manager session + //parameters - uid, mhttpdownloadmgrobserver + //embedded mode on - master flag True has to be passed when the app is + //in stand alone mode, false in case of embedded mode + iDownloadMgr.ConnectL( hostUid ,*this , EFalse /* Embedded mode*/); + // When SVGT Viewer exits, all the downloads are + // cancelled by the download manager + iDownloadMgr.SetIntAttribute( EDlMgrExitAction , EExitDelete ); + + iDMgrUiReg = CDownloadMgrUiLibRegistry::NewL( iDownloadMgr ); + iDMgrDownloadsList = &iDMgrUiReg->RegisterDownloadsListL(); + iDMgrUserInteractions = &iDMgrUiReg->RegisterUserInteractionsL(); + iDMgrUserInteractions->SetBoolAttributeL( CDownloadMgrUiUserInteractions::EAttrSuppressDownloadConfirmation, + ETrue ); +#endif + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::ConstructL( + RFile* aFileHdlPtr, + const TDesC& aFilename, + TBool aIsFileFullPathAvailable, + TBool aCanSaveContent, + TBool aShouldMoveContent ) + { + iIsFullFilePathValid = aIsFileFullPathAvailable; + iCanSaveContent = aCanSaveContent; + iShouldMoveContent = aShouldMoveContent; + iSvgFileId = aFileHdlPtr; + if ( aIsFileFullPathAvailable ) + { + iSvgFileName = aFilename.AllocL(); + } + else + { + TFileName fullPathName; + iSvgFileId->FullName( fullPathName ); + iSvgFileName = fullPathName.AllocL(); + } + ConstructL(); + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::ConstructL( + RFile* aFileHdlPtr + ) + { + TBuf<1> lDummyFileName; /* This is needed by ConstructL, + but will be ignored */ + + ConstructL( aFileHdlPtr, + lDummyFileName, + EFalse /* IsFileFullPathAvailable */, + ETrue /* CanSaveContent */, + EFalse /* aShouldMoveContent */ + ); + } +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::CanShowSave +// Tells the SVG-T dialog if the save option should be displayed. +// e.g. If the dialog is launched from SVG-T viewer and which is launched +// embedded from Browser/Messaging then Save option would be displayed. +// Also when MMS launches the dialog. +// ----------------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::CanShowSave() +{ + return iCanSaveContent; +} + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::CanShowSave +// Tells the SVG-T dialog if saving of the content is done. +// ----------------------------------------------------------------------------- +// +EXPORT_C TBool CSVGTAppObserverUtil::IsSavingDone() +{ + return iSavingDone; +} +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::DoSaveL +// Performs the save operation on the content opened. +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::DoSaveL( TInt aCommandId ) + { + iCommandId = aCommandId; + // Get filename. + // Run Dialog. + // Need to pause content + iAppDialog->ProcessCommandL( ESvgtDlgPauseCommand ); + + // Get the currently playing svg file's name and extension. + HBufC* lFileNameBuf = HBufC::NewLC( KMaxFileName ); + TPtr lFileNamePtr = lFileNameBuf->Des(); + GetFileNameAndExt( lFileNamePtr ); + + #ifndef RD_MULTIPLE_DRIVE + // Get User's choice of name and folder for target file. + TBool retval = AknCommonDialogs::RunSaveDlgNoDirectorySelectionLD( + lFileNamePtr, + R_SVGT_SAVE_LOCATIONS ); +#else + + TBool retval = AknCommonDialogsDynMem::RunSaveDlgNoDirectorySelectionLD( + AknCommonDialogsDynMem::EMemoryTypeRemote | + AknCommonDialogsDynMem::EMemoryTypePhone | + AknCommonDialogsDynMem::EMemoryTypeMMC, + lFileNamePtr, R_SVGT_SAVE_LOCATIONS); +#endif + + if ( retval ) + { + // User chose a valid file name + TBool lMoveFlag = EFalse; + TBuf<1> lDummyFileName; + RFile lDummyFile; + TInt errSaveContent = KErrNone; + TInt errSaveText = KErrNone; + + // Assume it is not the overwrite case by default + iIsOverwriteCase = EFalse; + + // Get the currently playing svg file's full path + HBufC* lFullFilePathBuf = HBufC::NewLC( KMaxFileName ); + TPtr lFullFilePathPtr = lFullFilePathBuf->Des(); + + if ( iSvgFileId ) + { + iSvgFileId->FullName( lFullFilePathPtr ); + } + // Check if file name is same as orig file -> overwrite case + if ( !( lFileNamePtr.CompareF( lFullFilePathPtr ) ) ) + { + iIsOverwriteCase = ETrue; + } + CleanupStack::PopAndDestroy( lFullFilePathBuf ); + lFullFilePathBuf = NULL; + + // Check if text edit happened + if ( iAppDialog->IsTextContentChanged() ) + { + if ( iTempFileName ) + { + delete iTempFileName; + iTempFileName = NULL; + } + iTempFileName = HBufC::NewL( KMaxFileName ); + TPtr lTempFilePtr = iTempFileName->Des(); + + // Indicate that cleanup is to be performed in SVGTSavingDoneL + iTempFileUsed = ETrue; + + TRAP( errSaveText, SaveSvgTextContentL( *iSvgFileId, lTempFilePtr ) ); + + if ( !errSaveText ) + { + // Temp file should be moved instead of + // original file + lMoveFlag = ETrue; + + if ( IsAllowMove() || iIsOverwriteCase ) + { + // Based on Move option/self overwrite case, need to close + // the content being played. + // Need to close the currently running file-handle, + // need to inform dialog to stop using it. + iAppDialog->StopUsingContentFileHandle(); + iSvgFileId->Close(); + } + + if ( IsAllowMove() ) + { + // Remember that the original file should + // be deleted if file save is successful. + iDeleteOrigFile = ETrue; + } + + + TRAP( errSaveContent, SaveContentL( + lDummyFile, + lTempFilePtr, + lFileNamePtr, + lMoveFlag )); + } + } + else // No text editing happened + { + + if ( IsAllowMove() || iIsOverwriteCase ) + { + // Based on Move option/self overwrite case, need to close + // the content being played. + // Need to close the currently running file-handle, + // need to inform dialog to stop using it. + iAppDialog->StopUsingContentFileHandle(); + iSvgFileId->Close(); + } + + if ( IsAllowMove() ) + { + lMoveFlag = ETrue; + TRAP( errSaveContent, SaveContentL( + lDummyFile, + *iSvgFileName, + lFileNamePtr, + lMoveFlag )); + } + else + { + TRAP( errSaveContent, SaveContentL( + *iSvgFileId, + lDummyFileName, + lFileNamePtr, + lMoveFlag )); + } + } + + CleanupStack::PopAndDestroy( lFileNameBuf ); + + + if ( errSaveText || errSaveContent ) + { + // If disk full problem, display note. + if ( errSaveContent == KErrDiskFull || errSaveText == KErrDiskFull ) + { + // mmc full note + HBufC* text = StringLoader::LoadLC( R_SVGT_MMC_FULL ); + CAknGlobalNote* note = CAknGlobalNote::NewLC(); + note->SetSoftkeys( R_AVKON_SOFTKEYS_OK_EMPTY__OK ); + note->ShowNoteL( EAknGlobalErrorNote, *text ); + CleanupStack::PopAndDestroy(2);// note, text + } + + // If temporary file was used, perform cleanup + if ( iTempFileUsed ) + { + if ( iTempFileName ) + { + // Try and delete the temp file, ignore the error. + iEikEnv->FsSession().Delete( iTempFileName->Des() ); + delete iTempFileName; + iTempFileName = NULL; + } + iTempFileUsed = EFalse; + } + + // If the File Couldn't be Moved, then Open the original + // file again and Set it back to dialog. + if ( IsAllowMove() ) + { + if( iSvgFileId->Open(iEikEnv->FsSession(), + iSvgFileName->Des(), EFileShareAny) != KErrNone ) + { + // This should not happen, Couldn't reopen back the + // Original content!, No Point in showing save. + iCanSaveContent = EFalse; + return; + } + else + { + iAppDialog->StartUsingContentFileHandle(); + } + } + } + else + { + LaunchWaitNoteL( R_SVGT_SAVING_WAIT_NOTE, ETrue, lDummyFileName ); + } + } + else + { + // User pressed cancel in save dialog - cleanup + CleanupStack::PopAndDestroy( lFileNameBuf ); + } + } + +EXPORT_C TInt CSVGTAppObserverUtil::NewFetchImageData( const TDesC& aUri ) + { +// iIsFetchImageCall = ETrue + TInt ret = KErrNone; + + TDownloadNeeded downloadNeeded = ELocalImageFile; + TRAPD( error, downloadNeeded = IsDownloadNeededL( aUri ) ); + + if ( error != KErrNone ) + { + return KErrNotFound; + } + + if ( downloadNeeded == ELocalImageFile ) + { + TFileName fileName; + if ( GetLocalFile( aUri, fileName, *iSvgFileName ) ) + { + TRAPD(error, DoAssignLocalFileDataL( aUri, fileName )); + return error; + } + else + { + iAppDialog->AssignImageData(aUri , NULL ); + return KErrNotFound; + } + } + else if ( downloadNeeded == ERemoteImageFile ) + { + //creatred for Dummy purpose + RFs fs; + RFile file; + + TRAPD( err,ret = StartDownloadingImageL( aUri, fs, file, + EFalse, + EFalse /* Asynchronous mode */) ); + if ( err != KErrNone ) + { + return KErrNotFound; + } + else + { + return ret; + } + + } + else + { + return KErrNotFound; + } + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SaveContentL +// Performs the save operation on the content opened given +// source file handle, src/dst filename and whether to move/copy. +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::SaveContentL( RFile& aSrcFileHandle, // Used in copy + const TDesC& aSrcFileName, // Used in move + TDes& aDstFileName, // Dest File name + TBool aMoveFlag ) // ETrue = Move + { + TInt ret = KErrNone; + // Start Saving Operation. + // Create directory + TInt error = iEikEnv->FsSession().MkDirAll( aDstFileName ); + if ( error != KErrNone && error != KErrAlreadyExists ) + { + User::Leave( error ); + } + + // Check if the content should be moved. e.g. In Browser case. + iFileManager->SetAllowMove( aMoveFlag ); + + // Ask FileManager to start saving. ObserverUtil acts as + // observer for filemanager operations. Based on whether + // the Move operation is required or not, + // there are two versions of filecopy operations. + // In Move Full filepath is required + if ( aMoveFlag ) + { + if ( IsFileFullPathAvailable() ) + { + // Keep the Destination file reference. + if ( iSvgDstFileName ) + { + delete iSvgDstFileName; + iSvgDstFileName = NULL; + } + iSvgDstFileName = aDstFileName.AllocL(); + + // Start the Move Now. + ret = iFileManager->StartCopyOperationL( + this, aSrcFileName, aDstFileName ); + } + else + { + // Shouldn't happen. If Move operation is required, + // Full file path must be there. + ret = KErrPathNotFound; + } + } + else + { + ret = iFileManager->StartCopyOperationL( + this, aSrcFileHandle, aDstFileName ); + } + User::LeaveIfError( ret ); + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetUniqueFileName +// Generates a unique filename in the private directory +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::GetUniqueFileName( TDes& aName ) const + { + TFileName lPpath; + iEikEnv->FsSession().PrivatePath( lPpath ); + RThread lThread; + _LIT( KFNameFormatStr,"%u"); + TBuf lThreadIdStr; + lThreadIdStr.Format( KFNameFormatStr, (TUint)(lThread.Id()) ); + aName.Append( lPpath ); + aName.Append( lThreadIdStr ); + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::IsGzipContent +// Checks whether the file is a GZipped content +// ----------------------------------------------------------------------------- +// +TBool CSVGTAppObserverUtil::IsGzipContent( const RFile& aFileHandle ) const +{ + TUint8 ids[2]; + TPtr8 des( ids, 0, sizeof( TUint8 ) * 2 ); + TInt zero = 0; + + // Reset to the beginning + aFileHandle.Seek( ESeekStart, zero ); + + // Read the first two bytes + if ( aFileHandle.Read( des ) != KErrNone ) + { + return EFalse; + } + + // reset to start of file + aFileHandle.Seek( ESeekStart, zero ); + return ( ids[0] == 31 && ids[1] == 139 ); +// return ( ids[0] == EZGZipFile::ID1 && ids[1] == EZGZipFile::ID2 ); +} + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SaveSvgContent +// Saves the SVG content to a temporary file +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::SaveSvgTextContentL( const RFile& aSrcFileHandle, + TDes& aTempFileName ) + { + TFileName lTempFileName; + + // Save the content path + HBufC* lOrigFileNameBuf = HBufC::NewLC( KMaxFileName ); + TPtr lOrigFileNamePtr = lOrigFileNameBuf->Des(); + aSrcFileHandle.FullName( lOrigFileNamePtr ); + + // Create the temp file in the same drive as the content file + TParsePtrC lOrigPath( lOrigFileNamePtr ); + + // Put the drive into the path + lTempFileName.Append( lOrigPath.Drive() ); + + // lOrigFileNameBuf no longer needed. No more references to + // lOrigFileNamePtr. +// CleanupStack::PopAndDestroy( lOrigFileNameBuf ); + + // Generate a unique file name + GetUniqueFileName( lTempFileName ); + + TInt lOrigFileSize = 0; + TInt lFileSizeErr = aSrcFileHandle.Size( lOrigFileSize ); + if ( lFileSizeErr ) + { + User::Leave( lFileSizeErr ); + } + + // Check whether freespace available + // Assume that the new file occupies same amount of space as the original + // file. Not so in the case of svgz file. +#ifndef RD_MULTIPLE_DRIVE + if( lOrigPath.Drive().CompareF( PathInfo::MemoryCardRootPath().Left(2) ) + == 0 ) + { + if (SysUtil::MMCSpaceBelowCriticalLevelL(&(iEikEnv->FsSession()), + lOrigFileSize )) + { + User::Leave( KErrDiskFull ); // MMC full, Avkon shows note + } + } + else + { + if (SysUtil::FFSSpaceBelowCriticalLevelL(&(iEikEnv->FsSession()), + lOrigFileSize )) + { + User::Leave( KErrDiskFull ); // Phone memory full, Avkon shows + // note + } + } +#else +//******************* Added to support multiple drives ************************* + TInt intDrive; + TChar ch = lOrigPath.Drive()[0]; + + User::LeaveIfError( RFs::CharToDrive(ch,intDrive) ); + + if( SysUtil::DiskSpaceBelowCriticalLevelL(&(iEikEnv->FsSession()), + lOrigFileSize, intDrive )) + { + User::Leave( KErrDiskFull ); // MMC full, Avkon shows note + } + +//********************************************************************************* +#endif + // lOrigFileNameBuf no longer needed. No more references to + // lOrigFileNamePtr. + CleanupStack::PopAndDestroy( lOrigFileNameBuf ); + + // Create the directory to the temp filename + TInt lDirCreateError = iEikEnv->FsSession().MkDirAll( lTempFileName ); + + // Ignore error if the directory already exists + if ( lDirCreateError != KErrNone && lDirCreateError != KErrAlreadyExists ) + { + User::Leave( lDirCreateError ); + } + + // Save the changed SVG content to that file name + iAppDialog->SaveSvgDom( lTempFileName ); + + // Check if content is gzipped + if ( IsGzipContent( aSrcFileHandle ) ) + { + // Zip the content + } + aTempFileName = lTempFileName; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::GetFileNameAndExt +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::GetFileNameAndExt(TDes& filename) const +{ + + // If FileName is valid use that, else check filehandle + // and give back file-name from that. + if ( iIsFullFilePathValid ) + { + if ( iSvgFileName ) + { + TParsePtrC p(*iSvgFileName); + TPtrC ptr(p.NameAndExt()); + filename = ptr; + } + } + else + { + if ( iSvgFileId ) + { + iSvgFileId->Name( filename ); + } + } + +} + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::IsAllowMove +// ----------------------------------------------------------------------------- +EXPORT_C TBool CSVGTAppObserverUtil::IsAllowMove() const +{ + return iShouldMoveContent; +} + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::IsFileFullPathAvailable +// ----------------------------------------------------------------------------- +EXPORT_C TBool CSVGTAppObserverUtil::IsFileFullPathAvailable() const + { + return 1; + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::LauncWaitNoteL +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::LaunchWaitNoteL(TInt aResourceId, + TBool aVisibilityDelayOff, const TDesC& aFileName ) + { + + delete iWaitNote; + iWaitNote = NULL; + iProgressInfo = NULL; + + if ( aResourceId == R_SVGT_DOWNLOAD_WAIT_NOTE ) + { + iWaitNote = new (ELeave) CAknWaitDialog( (CEikDialog**)&iWaitNote, + aVisibilityDelayOff ); + iWaitNote->PrepareLC(aResourceId); + + TInt resourceId = R_SVGT_DOWNLOADING_FILE; + HBufC* downloadMsg = StringLoader::LoadLC( resourceId ); + + TBuf titleString; + titleString.Append( downloadMsg->Des() ); + + CleanupStack::PopAndDestroy( downloadMsg ); // downloadMsg + + // Add a force line feed to the note: + // qtn_svgt_waiting_downloading [ Downloading file ], + // and the note will read like this: + // Downloading file + // filename + titleString.Append( KNewLineStr ); + + // Append the filename + titleString.Append( aFileName ); + + iWaitNote->SetTextL( titleString ); + + iWaitNoteState = EDownloadImageWait; + } + else if ( aResourceId == R_SVGT_SAVING_WAIT_NOTE ) + { + iWaitNote = new (ELeave) CAknProgressDialog( (CEikDialog**)&iWaitNote, + aVisibilityDelayOff ); + iWaitNote->PrepareLC(aResourceId); + iProgressInfo = iWaitNote->GetProgressInfoL(); + iProgressInfo->SetFinalValue( KSVGTPercent ); + iWaitNoteState = ESaveFileWait; + } + else + { + return; + } + + if ( iWaitNote ) + { + iWaitNote->SetCallback(this); + iWaitNote->RunLD(); + } + else + { + return; + } + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::DialogDismissedL +// This is for CAknWaitDialog callback +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::DialogDismissedL( TInt aButtonId ) + { + + switch (aButtonId) + { + case EAknSoftkeyQuit: + { + if ( iWaitNoteState == ESaveFileWait ) + { + // Handle Save Cancel + iFileManager->CancelCopy(); + // Resume the presentation + iAppDialog->ProcessCommandL( iCommandId ); + } + else if ( iWaitNoteState == EDownloadImageWait ) + { + if ( iWait.IsStarted() ) + { + iSynchronousDownloadStopped = ETrue; + iWait.AsyncStop(); + } + } + else + { + return; + } + break; + } + default: + break; + } + } + + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SVGTSavingDoneL +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::SVGTSavingDoneL( TInt aError ) + { +#ifdef SVGTVIEWERAPP_DBG_FLAG + TBuf<40> msg; + _LIT( errorMsg, "Save Done Err %d" ); + msg.Format(errorMsg, aError ); + PrintDebugMsg( msg ); +#endif + // If temporary file was used then, perform cleanup + if ( iTempFileUsed ) + { + if ( iTempFileName ) + { + iEikEnv->FsSession().Delete( iTempFileName->Des() ); + delete iTempFileName; + iTempFileName = NULL; + } + iTempFileUsed = EFalse; + } + + // Indicate to the dialog about the save completion + iAppDialog->SaveComplete( aError ); + + if ( !aError ) + { + iSavingDone = ETrue; + } + + if( iWaitNote ) + { + if ( !aError && iProgressInfo ) + { + iProgressInfo->SetAndDraw( KSVGTPercent ); + } + iWaitNote->ProcessFinishedL(); + delete iWaitNote; + iWaitNote = NULL; + +#ifdef SVGTVIEWERAPP_DBG_FLAG + _LIT( errorMsg, "Proc Finished called" ); + PrintDebugMsg( errorMsg() ); +#endif + + } + + if ( !aError ) + { + + // "saved" note + HBufC* text = StringLoader::LoadLC(R_SVGT_CLIP_SAVED); + CAknInformationNote* dlg = new (ELeave) CAknInformationNote( ETrue ); + dlg->ExecuteLD(*text); + CleanupStack::PopAndDestroy( text ); // text + + + } + else + { + iEikEnv->HandleError( aError ); + } + + // If move allowed or it is the overwriting self case then + if ( IsAllowMove() || iIsOverwriteCase ) + { + if ( !aError ) + { + // No error occurred + + // File has been moved and source + // deleted hence don't show save now. + iCanSaveContent = EFalse; + // If It was Move operation, then Open the new file + // and give the handle to dialog. + if ( iSvgFileId->Open(iEikEnv->FsSession(), + iSvgDstFileName->Des(), EFileShareAny) != KErrNone ) + { + // Shouldn't happen. + return; + } + else + { + iAppDialog->StartUsingContentFileHandle(); + } + } + else // Error occurred while saving, try to recover + { + // If it was Move Operation, and failed, then Open + // Original Source file again and give the handle to + // dialog. Note this could fail potentially as the + // original file could have been deleted. + if ( iSvgFileId->Open(iEikEnv->FsSession(), + iSvgFileName->Des(), EFileShareAny) != KErrNone ) + { + //Inconsistent state, can't show save also. + iCanSaveContent = EFalse; + return; + } + else + { + // Can keep showing the save option still. + iAppDialog->StartUsingContentFileHandle(); + } + } + } + + if ( !aError ) + { + if ( iDeleteOrigFile ) + { + iEikEnv->FsSession().Delete( iSvgFileName->Des() ); + iSvgFileName->Des().Zero(); + } + // Pass the command id back to UiDialog + iAppDialog->ProcessCommandL( iCommandId ); + } + } + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::SVGTPositionChanged +// ----------------------------------------------------------------------------- +// +EXPORT_C void CSVGTAppObserverUtil::SVGTPositionChanged(TInt aPosition) + { + if (iWaitNote && iProgressInfo) + { + iProgressInfo->SetAndDraw(aPosition); + } + /* + else if (iFullScreen) + { + TRAPD(ignore, iContainer->UpdateBufferingL(aPosition) ); + } // (L961) + */ + } + +#ifdef SVGTVIEWERAPP_DBG_FLAG +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::PrintDebugMsg +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::PrintDebugMsg( const TDesC& aMsg ) + { +#ifdef _DEBUG + RFileLogger::Write( KFileLoggingDir, KFileLog, + EFileLoggingModeAppend, aMsg ); +#endif + } +#endif + +// ----------------------------------------------------------------------------- +// CSVGTAppObserverUtil::DoAssignImageDataL +// Reads the downloaded file & gives data to the svg engine. +// ----------------------------------------------------------------------------- +// +void CSVGTAppObserverUtil::DoAssignImageDataL(const CSVGTViewerAppDownloads* aDownloadItem, + RHttpDownload& aDownload) + { + if( aDownloadItem && !aDownloadItem->ImageLinkFlag() ) + { + TFileName lFileName; + // Get the file path of the downloaded file + aDownload.GetStringAttribute( EDlAttrDestFilename, lFileName ); + + TInt lFileSize = 0; + RFile lSvgFile; + // Attempt to open the file in read mode + User::LeaveIfError( lSvgFile.Open(iEikEnv->FsSession(),lFileName,EFileRead ) ); + + // Save on cleanup stack + CleanupClosePushL( lSvgFile ); + + // Get the size of the data to create read buffer + User::LeaveIfError( lSvgFile.Size(lFileSize) ); + + // Create buffer that will contain the file data + HBufC8* lFileData = HBufC8::NewLC(lFileSize); + TPtr8 lFileDataPtr(lFileData->Des()); + + // Read from the file + User::LeaveIfError( lSvgFile.Read(lFileDataPtr) ); + + // Create buffer to store the URI of the file + HBufC* lUriBuf = HBufC::NewLC( KMaxUrlLength ); + TPtr lUriPtr(lUriBuf->Des()); + + // Get the URI from data structure + aDownload.GetStringAttribute( EDlAttrReqUrl, lUriPtr ); + + // Call the AssignImageData function + // Mapping is maintained between URI <-> FileData + iAppDialog->AssignImageData(lUriPtr , lFileData ); + + CleanupStack::PopAndDestroy( lUriBuf ); + CleanupStack::Pop( lFileData ); + CleanupStack::PopAndDestroy(&lSvgFile); // lSvgFile.Close() + } + } + +void CSVGTAppObserverUtil::DoAssignLocalFileDataL( const TDesC& aOriginalUri, + const TDesC& aNewUri ) const + { + TInt lFileSize = 0; + TBuflFileName; + lFileName.Copy(aNewUri); + RFile lSvgFile; + // Attempt to open the file in read mode + User::LeaveIfError( lSvgFile.Open(iEikEnv->FsSession(),lFileName,EFileRead ) ); + + // Save on cleanup stack + CleanupClosePushL( lSvgFile ); + + // Get the size of the data to create read buffer + User::LeaveIfError( lSvgFile.Size(lFileSize) ); + // Create buffer that will contain the file data + HBufC8* lFileData = HBufC8::NewLC(lFileSize); + TPtr8 lFileDataPtr(lFileData->Des()); + // Read from the file + User::LeaveIfError( lSvgFile.Read(lFileDataPtr) ); + + // Call the AssignImageData function + // Mapping is maintained between URI <-> FileData + iAppDialog->AssignImageData(aOriginalUri , lFileData ); + + CleanupStack::Pop( lFileData ); + CleanupStack::PopAndDestroy(&lSvgFile); // lSvgFile.Close() + } + +EXPORT_C void CSVGTAppObserverUtil::AssignEmbededDataL( const TDesC& aUri ) + { + HBufC8* decoded = DoGetProcessedEmbededDataL( aUri ); + if ( decoded ) + { + iAppDialog->AssignImageData( aUri, decoded ); + } + } + +HBufC8* CSVGTAppObserverUtil::DoGetProcessedEmbededDataL( const TDesC& aXlinkHrefValue ) const + { + HBufC8* retPtr = NULL; + // find positions for ';' and ',' to determine encoding, mimetype + TInt startIndex = aXlinkHrefValue.Locate( ';' ); + TInt endIndex = aXlinkHrefValue.Locate( ',' ); + + // mimetype is after 'data:' : xlink:href="data:image/png;base64, + // ignore mimetype extraction, decode will detect mimetype from decoded data. + + if ( startIndex != KErrNotFound && + endIndex != KErrNotFound && + startIndex < endIndex ) + { + // extract encoding type + TPtrC encoding( aXlinkHrefValue.Left( endIndex ).Right( endIndex - startIndex - 1 ) ); + // handle Base64 encoding + _LIT( KEncodingBase64, "base64" ); + if ( encoding == KEncodingBase64 ) + { + // find index of first character after white-space + TInt index = endIndex + 1; + while ( index < aXlinkHrefValue.Length() && TChar( aXlinkHrefValue[index] ).IsSpace() ) + index++; + + // must be 8-bit + TInt length = aXlinkHrefValue.Length() - index; + HBufC8* encoded = HBufC8::NewLC( length ); + encoded->Des().Copy( aXlinkHrefValue.Right( length ) ); + + HBufC8* decoded = HBufC8::NewLC( length ); + TPtr8 decodedDes = decoded->Des(); + + // decode + TImCodecB64 encodingBase64; + TInt decodeError = encodingBase64.Decode( *encoded, decodedDes ); + + // Cleanup + CleanupStack::Pop( decoded ); // encoded, decoded + CleanupStack::PopAndDestroy( encoded ); + //delete encoded; + + // Check for decoding error + if ( decodeError != KErrNone ) + { + delete decoded; + } + else + { + retPtr = decoded; + } + } + } + return retPtr; + } + TBool CSVGTAppObserverUtil::ExitWhenOrientationChange() + { + return EFalse; + } + +// End of File +