--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/messagingapp/msgui/msgaudiofetcher/src/msgaudiopreview.cpp Fri Jun 25 15:47:40 2010 +0530
@@ -0,0 +1,629 @@
+/*
+ * Copyright (c) 2010 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:
+ * The source file for tone previewing.
+ *
+ */
+#include "msgaudiopreview.h"
+#include <AudioPreference.h> // KAudioPriorityPreview
+#include <c3dringingtoneinterface.h> // C3DRingingToneInterface
+#include <ctsydomainpskeys.h> // for phone call states
+#include <MProfileEngine.h>
+#include <MProfile.h>
+#include <MProfileTones.h>
+#include "TProfileToneSettings.h"
+#include <MProfileExtraSettings.h>
+#include <MProfile3DToneSettings.h>
+#include <ProfileInternal.hrh>
+#include <ProfileEngineDomainCRKeys.h> // KProEngDefaultRingingTone
+#include <XQConversions>
+#include <QChar>
+#include <QDir>
+
+
+CMFPreviewHandlerBase::CMFPreviewHandlerBase( QObject *parent ) : QObject( parent )
+ {
+ iMediaType = KErrNotFound;
+ iRingingVolume = KErrNotFound;
+ iRingingType = KErrNotFound;
+ iVibra = KErrNotFound;
+ i3DEffect = KErrNotFound;
+ i3DEcho = KErrNotFound;
+ iFileSize = KErrNotFound;
+ iFullName = 0;
+ iActiveProfileRead = EFalse;
+ iPlayerStatus = EPlayerNotCreated;
+
+ }
+
+void CMFPreviewHandlerBase::ConstructL()
+ {
+ // To allow/not allow screensaver
+ // Errors ignored, no actions needed if API is not available
+ //iProperty.Attach( KPSUidScreenSaver, KScreenSaverAllowScreenSaver );
+ TRAP_IGNORE(User::LeaveIfError( iApaSession.Connect() ) );
+
+ TRAP_IGNORE( ReadDefaultToneL() );
+ // To keep backlight on while a video is being previewed
+ iBacklightTimer = CPeriodic::NewL( EPriorityLow );
+ }
+
+CMFPreviewHandlerBase::~CMFPreviewHandlerBase()
+ {
+ delete iFullName;
+ iProperty.Close();
+ iApaSession.Close();
+ }
+
+void CMFPreviewHandlerBase::SetAttr(const QString &file )
+ {
+ if ( !file.isNull() )
+ {
+ QString path = normalizeSeperator(file);
+ delete iFullName;
+ iFullName = 0;
+ iFullName = XQConversions::qStringToS60Desc( path );
+ }
+ }
+
+TInt CMFPreviewHandlerBase::RingingVolume()
+ {
+ const TInt KDefaultVolumeLevel = 7; // see profile.hrh for volume levels
+
+ if ( iRingingVolume != KErrNotFound )
+ {
+ return iRingingVolume;
+ }
+
+ if ( iActiveProfileRead )
+ {
+ return iActiveProfileRingingVolume;
+ }
+
+ return KDefaultVolumeLevel;
+ }
+
+TInt CMFPreviewHandlerBase::RingingType()
+ {
+ if ( iRingingType != KErrNotFound )
+ {
+ return iRingingType;
+ }
+
+ if ( iActiveProfileRead )
+ {
+ return iActiveProfileRingingType;
+ }
+
+ return ERingingTypeRinging;
+ }
+
+TInt CMFPreviewHandlerBase::Vibra()
+ {
+ if ( iVibra != KErrNotFound )
+ {
+ return iVibra;
+ }
+
+ if ( iActiveProfileRead )
+ {
+ return iActiveProfileVibra;
+ }
+
+ return 0; // in case of error vibra is off
+ }
+
+TInt CMFPreviewHandlerBase::Echo3D()
+ {
+ if ( i3DEcho != KErrNotFound )
+ {
+ return i3DEcho;
+ }
+
+ if ( iActiveProfileRead )
+ {
+ return iActiveProfile3DEcho;
+ }
+
+ return EProfile3DEchoOff; // from ProfileInternal.hrh
+ }
+
+TInt CMFPreviewHandlerBase::Effect3D()
+ {
+ if ( i3DEffect != KErrNotFound )
+ {
+ return i3DEffect;
+ }
+
+ if ( iActiveProfileRead )
+ {
+ return iActiveProfile3DEffect;
+ }
+
+ return EProfile3DEffectOff;
+ }
+
+TInt CMFPreviewHandlerBase::ConvertVolume( TInt aVolume, TInt aMaxVolume )
+ {
+ const TInt KMinVolumeLevel = 1;
+ const TInt KMaxVolumeLevel = 10;
+
+ TInt result = aMaxVolume * aVolume / KMaxVolumeLevel;
+
+ // if user has selected minimum volume level set HW volume 1
+ if ( aVolume == KMinVolumeLevel && result == 0 )
+ {
+ result = 1;
+ }
+
+ return result;
+ }
+
+void CMFPreviewHandlerBase::ReadActiveProfileL()
+ {
+ iActiveProfileRead = EFalse;
+
+ MProfileEngine* profileEngine = CreateProfileEngineL();
+ CleanupReleasePushL( *profileEngine );
+
+ MProfile* activeProfile = profileEngine->ActiveProfileL();
+ CleanupReleasePushL( *activeProfile );
+
+ const MProfileTones& profileTones = activeProfile->ProfileTones();
+
+ const TProfileToneSettings& toneSettings = profileTones.ToneSettings();
+ iActiveProfileVibra = toneSettings.iVibratingAlert;
+ iActiveProfileRingingVolume = toneSettings.iRingingVolume;
+ iActiveProfileRingingType = toneSettings.iRingingType;
+
+ const MProfileExtraSettings& extra = activeProfile->ProfileExtraSettings();
+ const MProfile3DToneSettings& threeD = extra.Profile3DToneSettings();
+
+ iActiveProfile3DEffect = threeD.Effect();
+ iActiveProfile3DEcho = threeD.Echo();
+
+ CleanupStack::PopAndDestroy( activeProfile );
+ CleanupStack::PopAndDestroy( profileEngine );
+
+ iActiveProfileRead = ETrue;
+ }
+
+void CMFPreviewHandlerBase::ReadDefaultToneL()
+ {
+ CRepository* cenrep = CRepository::NewLC( KCRUidProfileEngine );
+
+ User::LeaveIfError( cenrep->Get( KProEngDefaultRingingTone, iDefaultTone ) );
+ CleanupStack::PopAndDestroy( cenrep );
+ }
+
+TInt CMFPreviewHandlerBase::GetDataType( const TDesC& aFileName, TDataType& aDataType )
+ {
+ TUid dummyUid( KNullUid );
+ return iApaSession.AppForDocument( aFileName, dummyUid, aDataType );
+ }
+
+TInt CMFPreviewHandlerBase::DoResetInactivityTimer( TAny* /*aObject*/ )
+ {
+ User::ResetInactivityTime();
+ return KErrNone;
+ }
+
+void CMFPreviewHandlerBase::DisableBackLight()
+ {
+ const TInt KResetInactivityTimerDelay = 2000000;
+ iBacklightTimer->Cancel(); // Just in case
+ // Disable backlight turn off during video preview
+ iBacklightTimer->Start( KResetInactivityTimerDelay,
+ KResetInactivityTimerDelay,
+ TCallBack( DoResetInactivityTimer, 0 ) );
+
+ }
+
+
+
+MsgAudioPreview::MsgAudioPreview( QObject *parent ) : CMFPreviewHandlerBase( parent )
+ {
+ iAudioPlayerStatus = EPlayerNotCreated;
+ TRAP_IGNORE(CMFPreviewHandlerBase::ConstructL());
+ iTonePlayerStatus = EPlayerNotCreated;
+ }
+
+MsgAudioPreview::~MsgAudioPreview()
+ {
+ Cancel();
+
+ delete iAudioPlayer;
+ delete iTonePlayer;
+ delete i3dRingingTonePlugin;
+ }
+
+TBool MsgAudioPreview::IsPlaying()
+ {
+ if ( iAudioPlayerStatus != EPlayerNotCreated )
+ {
+ return ETrue;
+ }
+
+ if ( iTonePlayerStatus != EPlayerNotCreated )
+ {
+ return ETrue;
+ }
+
+ return EFalse;
+ }
+
+void MsgAudioPreview::Play()
+ {
+ TRAP_IGNORE(PlayL());
+ }
+
+void MsgAudioPreview::PlayL()
+ {
+ if( IsPlaying() )
+ {
+ Stop();
+ return;
+ }
+ //sequence for playing a beep once sound
+ _LIT8( KFileListBeepSequence, "\x00\x11\x06\x0A\x08\x73\x0A\x40\x28\x0A\xF7\
+ \x05\xFC\x40\x64\x0A\x08\x40\x32\x0A\xF7\x06\x0B" );
+
+ // rng mime type
+ _LIT( KFileListRngMimeType, "application/vnd.nokia.ringing-tone" );
+
+ Cancel(); // stop previous play
+
+ if ( !iFullName || iFullName->Des().Length() == 0 )
+ {
+ User::Leave( KErrNotFound );
+ }
+
+ TRAP_IGNORE( ReadActiveProfileL() );
+
+ TPtrC fileName( iFullName->Des() );
+ TDataType dataType;
+ TInt err = GetDataType( fileName, dataType );
+ if ( err == KErrNotFound )
+ {
+ fileName.Set( iDefaultTone );
+ if ( fileName.Length() == 0 )
+ {
+ User::Leave( KErrNotFound );
+ }
+ }
+ else if ( err != KErrNone )
+ {
+ User::Leave( err );
+ }
+
+ TBool mimeTypeRng = EFalse;
+
+ if ( err == KErrNone )
+ {
+ if( dataType.Des().CompareF( KFileListRngMimeType ) == 0 )
+ {
+ mimeTypeRng = ETrue;
+ }
+ }
+
+ TInt ringingType = RingingType();
+ if ( ringingType == ERingingTypeBeepOnce )
+ {
+ // Active profile ringing tone is set to Beep Once
+ // Don't initialize a FileSequence but use DesSequence instead
+ iTonePlayer = CMdaAudioToneUtility::NewL( *this );
+ iTonePlayer->PrepareToPlayDesSequence( KFileListBeepSequence() );
+ iTonePlayerStatus = EPlayerInitializing;
+ }
+ else
+ {
+ if( mimeTypeRng )
+ {
+ //Ringingtone is a RNG-file
+ iTonePlayer = CMdaAudioToneUtility::NewL( *this );
+ iTonePlayer->PrepareToPlayFileSequence( fileName );
+ iTonePlayerStatus = EPlayerInitializing;
+ }
+ else
+ {
+ delete iAudioPlayer;
+ iAudioPlayer = 0;
+
+ iAudioPlayer = CDrmPlayerUtility::NewFilePlayerL(
+ fileName, *this, KAudioPriorityRingingTonePreview,
+ ( TMdaPriorityPreference )KAudioPrefRingFilePreview );
+
+ iAudioPlayerStatus = EPlayerInitializing;
+ }
+ }
+ DisableBackLight();
+ }
+
+void MsgAudioPreview::Stop()
+ {
+ Cancel();
+ }
+
+TInt MsgAudioPreview::ConvertVolume( TInt aVolume )
+ {
+ TInt result = 0;
+ if ( iAudioPlayer )
+ {
+ result = CMFPreviewHandlerBase::ConvertVolume( aVolume, iAudioPlayer->MaxVolume() );
+ }
+ else if ( iTonePlayer )
+ {
+ result = CMFPreviewHandlerBase::ConvertVolume( aVolume, iTonePlayer->MaxVolume() );
+ }
+
+ //if user has selected silent ringing type, set volume off
+ TInt ringingType = RingingType();
+ if( ringingType == ERingingTypeSilent )
+ {
+ result = 0;
+ }
+
+ return result;
+ }
+
+void MsgAudioPreview::SetToneRingingType( TInt aRingingType )
+ {
+ const TInt KToneInterval = 1000000; // 1 second pause between tones
+ const TInt KAscendingVolumeInterval = 3000000; // 3 seconds
+
+ if ( !iTonePlayer )
+ {
+ return;
+ }
+
+
+ TInt ringingVolume = RingingVolume();
+
+ switch( aRingingType )
+ {
+ case ERingingTypeRinging:
+ case ERingingTypeSilent:
+ {
+ iTonePlayer->SetRepeats( KMdaAudioToneRepeatForever,
+ TTimeIntervalMicroSeconds( KToneInterval ) );
+ break;
+ }
+ case ERingingTypeAscending:
+ {
+ iTonePlayer->SetRepeats( KMdaAudioToneRepeatForever,
+ TTimeIntervalMicroSeconds( KToneInterval ) );
+
+ TInt volRamp = KAscendingVolumeInterval * ringingVolume;
+ iTonePlayer->SetVolumeRamp( TTimeIntervalMicroSeconds( volRamp ) );
+ break;
+ }
+ case ERingingTypeRingOnce:
+ case ERingingTypeBeepOnce:
+ {
+ iTonePlayer->SetRepeats( 0, TTimeIntervalMicroSeconds( KToneInterval ) );
+ break;
+ }
+ default:
+ {
+ break;
+ }
+ }
+ }
+
+void MsgAudioPreview::SetAudioRingingType( TInt aRingingType )
+ {
+ const TInt KToneInterval = 1000000; // 1 second pause between tones
+ const TInt KAscendingVolumeInterval = 3000000; // 3 seconds
+
+ if ( !iAudioPlayer )
+ {
+ return;
+ }
+
+ TInt ringingVolume = RingingVolume();
+
+ switch( aRingingType )
+ {
+ case ERingingTypeRinging:
+ case ERingingTypeSilent:
+ {
+ iAudioPlayer->SetRepeats( KMdaAudioToneRepeatForever,
+ TTimeIntervalMicroSeconds( KToneInterval ) );
+ break;
+ }
+ case ERingingTypeAscending:
+ {
+ iAudioPlayer->SetRepeats( KMdaAudioToneRepeatForever,
+ TTimeIntervalMicroSeconds( KToneInterval ) );
+ TInt volRamp = KAscendingVolumeInterval * ringingVolume;
+ iAudioPlayer->SetVolumeRamp( TTimeIntervalMicroSeconds( volRamp ) );
+ break;
+ }
+ case ERingingTypeRingOnce:
+ {
+ iAudioPlayer->SetRepeats( 0, TTimeIntervalMicroSeconds( KToneInterval ) );
+ break;
+ }
+
+ default:
+ {
+ break;
+ }
+ }
+ }
+
+void MsgAudioPreview::Cancel()
+ {
+ TBool isPlaying = EFalse;
+
+ if ( iAudioPlayer )
+ {
+ isPlaying = ETrue;
+ if ( iAudioPlayerStatus == EPlayerPlayingWith3DEffect )
+ {
+ i3dRingingTonePlugin->Stop();
+ // plugin calls AudioPlayer->Stop()
+ iAudioPlayer->Close();
+ }
+ if ( iAudioPlayerStatus == EPlayerPlaying )
+ {
+ iAudioPlayer->Stop();
+ iAudioPlayer->Close();
+ }
+
+ delete iAudioPlayer;
+ iAudioPlayer = 0;
+ iAudioPlayerStatus = EPlayerNotCreated;
+ }
+
+ if ( iTonePlayer )
+ {
+ isPlaying = ETrue;
+ if ( iTonePlayerStatus == EPlayerPlaying )
+ {
+ iTonePlayer->CancelPlay();
+ }
+
+ delete iTonePlayer;
+ iTonePlayer = 0;
+ iTonePlayerStatus = EPlayerNotCreated;
+ }
+
+
+ if ( isPlaying )
+ {
+ //User::InfoPrint(_L("cancel"));
+// EnableScreenSaver( ETrue );
+ iBacklightTimer->Cancel();
+ }
+ }
+
+void MsgAudioPreview::MatoPlayComplete( TInt aError )
+ {
+ Q_UNUSED(aError);
+ Cancel();
+ // emit notifyPreviewEvent( ToneFetcherEngine::EAudioPreviewComplete, aError );
+ }
+
+void MsgAudioPreview::MatoPrepareComplete( TInt aError )
+ {
+ if ( aError != KErrNone )
+ {
+ Cancel();
+
+ // emit notifyPreviewEvent( ToneFetcherEngine::EPreviewError, aError );
+ return;
+ }
+
+ TInt ringingVolume = RingingVolume();
+ TInt ringingType = RingingType();
+ TInt vibra = Vibra();
+
+ iTonePlayerStatus = EPlayerInitialized;
+ SetToneRingingType( ringingType );
+ iTonePlayer->SetVolume( ConvertVolume( ringingVolume ) );
+
+ TMdaPriorityPreference pref = (TMdaPriorityPreference) KAudioPrefRingFilePreview;
+ if ( vibra )
+ {
+ pref = (TMdaPriorityPreference) KAudioPrefRingFilePreviewVibra;
+ }
+ iTonePlayer->SetPriority( KAudioPriorityPreview, pref );
+
+ iTonePlayer->Play();
+ iTonePlayerStatus = EPlayerPlaying;
+ }
+
+void MsgAudioPreview::MdapcInitComplete( TInt aError,
+ const TTimeIntervalMicroSeconds& /* aDuration */ )
+ {
+ if ( aError != KErrNone )
+ {
+ Cancel();
+ // emit notifyPreviewEvent( ToneFetcherEngine::EPreviewError, aError );
+ return;
+ }
+
+
+ TInt ringingVolume = RingingVolume();
+ TInt ringingType = RingingType();
+ TInt vibra = Vibra();
+ TInt echo3D = Echo3D();
+ TInt effect3D = Effect3D();
+
+
+
+ iAudioPlayerStatus = EPlayerInitialized;
+ SetAudioRingingType( ringingType );
+ iAudioPlayer->SetVolume( ConvertVolume( ringingVolume ) );
+
+ TMdaPriorityPreference pref = (TMdaPriorityPreference) KAudioPrefRingFilePreview;
+ if ( vibra )
+ {
+ pref = (TMdaPriorityPreference) KAudioPrefRingFilePreviewVibra;
+ }
+ iAudioPlayer->SetPriority( KAudioPriorityPreview, pref );
+
+ iAudioPlayerStatus = EPlayerPlaying;
+
+ if ( effect3D == EProfile3DEffectOff )
+ {
+ iAudioPlayer->Play(); // 3D not used
+ return;
+ }
+
+ if ( !i3dRingingTonePlugin )
+ {
+ TUid emptyUid = { 0 };
+ TRAPD( err, i3dRingingTonePlugin = C3DRingingToneInterface::NewL( emptyUid ) );
+ if ( err != KErrNone || !i3dRingingTonePlugin )
+ {
+ iAudioPlayer->Play();
+ return;
+ }
+ }
+
+ i3dRingingTonePlugin->SetAttr( E3DRTIAttr3DEffect, effect3D );
+ i3dRingingTonePlugin->SetAttr( E3DRTIAttr3DEcho, echo3D );
+ i3dRingingTonePlugin->SetAttr( E3DRTIAttrDrmPlayerUtility, iAudioPlayer );
+ TRAP_IGNORE( i3dRingingTonePlugin->PlayL() );
+
+ iAudioPlayerStatus = EPlayerPlayingWith3DEffect;
+ }
+
+void MsgAudioPreview::MdapcPlayComplete( TInt aError )
+ {
+ Q_UNUSED(aError);
+ Cancel();
+ // emit notifyPreviewEvent( ToneFetcherEngine::EAudioPreviewComplete, aError );
+
+
+ }
+
+
+QString CMFPreviewHandlerBase::normalizeSeperator(const QString &path)
+{
+ QString standardpath( path );
+ QChar c('/');
+ QChar c1('\\');
+ if (standardpath.contains(c, Qt::CaseSensitive)) {
+ standardpath.replace(c, QDir::separator());
+ }
+ if (standardpath.contains(c1, Qt::CaseSensitive)) {
+ standardpath.replace(c1, QDir::separator());
+ }
+ return standardpath;
+}
+
+