diff -r 26a1709b9fec -r 14979e23cb5e mpengine/src/mpmpxcollectionframeworkwrapper_p.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mpengine/src/mpmpxcollectionframeworkwrapper_p.cpp Tue Aug 31 15:12:29 2010 +0300 @@ -0,0 +1,1563 @@ +/* +* Copyright (c) 2009 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: Wrapper for mpx collection framework utilities - private implementation. +* +*/ + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "mpmpxcollectionframeworkwrapper_p.h" +#include "mpmpxcollectionframeworkwrapper.h" +#include "mpmpxcollectiondata.h" +#include "mpcommondefs.h" +#include "mptrace.h" +#include "mpsettingsmanager.h" +#include "mpsongdata.h" + +const TInt KIncrementalDelay = 0; +const TInt KIncrementalFetchBlockSize = 1000; + +const TInt KMPXChunkSize = 100; // number of songs added in each chunk, IncAddL +_LIT( KPlaylistPath, "C:\\Data\\Playlists\\" ); // Todo + +/*! + \class MpMpxCollectionFrameworkWrapperPrivate + \brief Wrapper for mpx framework utilities - private implementation. + + This is a private implementation of the mpx framework wrapper utilties interface. +*/ + +/*! + \internal + */ +MpMpxCollectionFrameworkWrapperPrivate::MpMpxCollectionFrameworkWrapperPrivate( MpMpxCollectionFrameworkWrapper *wrapper ) + : q_ptr( wrapper ), + iCollectionUtility( 0 ), + iCollectionUiHelper( 0 ), + iIncrementalOpenUtil( 0 ), + iIsolatedCollectionHelper( 0 ), + iPlaybackUtility( 0 ), + iCollectionData( 0 ), + iIsolatedCollectionData( 0 ), + iFirstIncrementalOpen( EFalse ), + iUserPlaylists( 0 ), + iRepeatFeature( ETrue ), + iShuffleFeature( ETrue ), + iReopen( EFalse ), + iShuffleAll( EFalse ), + iRestoreDefaultPath( EFalse ), + iRestorePathIndex( 0 ), + iSongData( 0 ) +{ + TX_LOG +} + +/*! + \internal + */ +MpMpxCollectionFrameworkWrapperPrivate::~MpMpxCollectionFrameworkWrapperPrivate() +{ + TX_ENTRY + delete iCollectionData; + delete iIsolatedCollectionData; + + if ( iCollectionUtility ) { + iCollectionUtility->Collection().CancelRequest(); + iCollectionUtility->Close(); + } + + if ( iCollectionUiHelper ) { + iCollectionUiHelper->Close(); + } + + if ( iPlaybackUtility ) { + iPlaybackUtility->Close(); + } + + delete iIncrementalOpenUtil; + delete iIsolatedCollectionHelper; + delete iUserPlaylists; + + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::init( TUid hostUid, MpSongData *songData ) +{ + TX_ENTRY + iHostUid = hostUid; + iSongData = songData; + TRAPD( err, DoInitL() ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::openCollection( TCollectionContext context ) +{ + TRAPD( err, DoOpenCollectionL( context ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::openCollectionItem( int index ) +{ + TRAPD( err, DoOpenCollectionItemL( index ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::reopenCollection() +{ + TRAPD( err, DoReopenCollectionL() ); + if ( err == KErrNone ) { + iReopen = ETrue; + } + else { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::back() +{ + TRAPD( err, DoBackL() ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::findPlaylists( QStringList &playlists ) +{ + TRAPD( err, DoFindPlaylistsL( playlists ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::createPlaylist( QString &playlistName, QList &selection, MpMpxCollectionData* collectionData ) +{ + TRAPD( err, DoCreatePlaylistL( playlistName, selection, collectionData ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::saveToPlaylist( int playlistIndex, QList &selection ) +{ + TRAPD( err, DoSaveToPlaylistL( playlistIndex, selection ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::saveToCurrentPlaylist( QList &selection, MpMpxCollectionData *collectionData ) +{ + TRAPD( err, DoSaveToCurrentPlaylistL( selection, collectionData ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::deleteSongs( QList &selection ) +{ + TCollectionContext context = iCollectionData->context(); + int err; + if ( context == ECollectionContextArtistAlbumsTBone + || context == ECollectionContextAlbumsTBone ) { + TRAP( err, DoDeleteAlbumSongsL( selection ) ); + } + else { + TRAP( err, DoDeleteSongsL( selection ) ); + } + if ( err == KErrNone ) { + // send signal that deleting has started. + emit q_ptr->deleteStarted(iCollectionData->context(), selection.count()); + } + else{ + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::renamePlaylist( QString &newName, int index ) +{ + TRAPD( err, DoRenamePlaylistL( newName, index ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::renamePlaylist( QString &newName ) +{ + TRAPD( err, DoRenamePlaylistL( newName ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::setShuffle( bool active ) +{ + TRAPD( err, DoSetShuffleL( active ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::previewItem( int index ) +{ + TCollectionContext context = iCollectionData->context(); + int err; + if ( context == ECollectionContextArtistAlbumsTBone + || context == ECollectionContextAlbumsTBone ) { + TRAP( err, DoPreviewAlbumSongL( index ) ); + } + else { + TRAP( err, DoPreviewSongL( index ) ); + } + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ + void MpMpxCollectionFrameworkWrapperPrivate::openIsolatedCollection( TCollectionContext context ) +{ + TRAPD( err, DoOpenIsolatedCollectionL( context ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::releaseIsolatedCollection() +{ + delete iIsolatedCollectionHelper; + iIsolatedCollectionHelper = 0; + delete iIsolatedCollectionData; + iIsolatedCollectionData = 0; +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::reorderPlaylist( int playlistId, int songId, int originalOrdinal, int newOrdinal ) +{ + TRAPD( err, DoReorderPlaylistL( playlistId, songId, originalOrdinal, newOrdinal ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::cancel() +{ + iCollectionUiHelper->Cancel(); +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::findAlbumSongs( int index ) +{ + TRAPD( err, DoFindAlbumSongsL( index ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::playAlbumSongs( int albumIndex, int songIndex, MpMpxCollectionData* collectionData ) +{ + TRAPD( err, DoPlayAlbumSongsL( albumIndex, songIndex, collectionData ? collectionData : iCollectionData ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } +} + +/*! + \internal + */ +MpMpxCollectionData *MpMpxCollectionFrameworkWrapperPrivate::collectionData() +{ + return iCollectionData; +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::openShuffleAllSongsPath() +{ + TX_ENTRY + TRAPD( err, DoOpenCollectionL(ECollectionContextAllSongs) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } + else { + iShuffleAll = ETrue; + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::retrieveSongDetails( int index ) +{ + TX_ENTRY + TRAPD( err, DoRetrieveSongDetailsL(index) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::savePath( QByteArray &data ) +{ + TX_ENTRY + TRAPD( err, DoSavePathL( data ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } + TX_EXIT + +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::restorePath( const QByteArray &data ) +{ + TX_ENTRY + TRAPD( err, DoRestorePathL( data ) ); + if ( err != KErrNone ) { + TX_LOG_ARGS( "Error: " << err << "; should never get here." ); + } + TX_EXIT +} + + +/*! + \internal + Result of open or re-open operation to the Collection Framework. + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleOpenL( + const CMPXMedia& aEntries, + TInt aIndex, + TBool aComplete, + TInt aError ) +{ + Q_UNUSED( aIndex ); + TX_UNUSED( aComplete ); + TX_ENTRY_ARGS( "aError=" << aError << "aComplete=" << aComplete ); + if ( aError == KErrNone ) { + if ( iFirstIncrementalOpen ) { + iFirstIncrementalOpen = EFalse; + if( iShuffleAll ) { + iShuffleAll = EFalse; + TX_LOG_ARGS( "Path is ready" ); + DoPlayAllSongsPlaylistL(); + } + iCollectionData->setMpxMedia( aEntries, iReopen ); + iReopen = EFalse; + } + else { + iCollectionData->incrementalOpenUpdate(); + } + } + else { + TX_LOG_ARGS( "Error: " << aError << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleOpenL( + const CMPXCollectionPlaylist& aPlaylist, + TInt aError ) +{ + TX_ENTRY_ARGS( "aError=" << aError ); + + if ( aError == KErrNone ) { + //TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + createPlaybackUtilityL(); + iPlaybackUtility->InitL( aPlaylist, ETrue ); + emit q_ptr->collectionPlaylistOpened(); + } + else { + TX_LOG_ARGS( "Error: " << aError << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleCollectionMessage( + CMPXMessage* aMsg, + TInt aErr ) +{ + TX_ENTRY_ARGS( "aErr=" << aErr ); + if ( aErr == KErrNone && aMsg ) + { + TRAP_IGNORE( DoHandleCollectionMessageL( *aMsg ) ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleCollectionMediaL( + const CMPXMedia& aMedia, + TInt aError ) +{ + TX_ENTRY + if ( KErrNone != aError ){ + TX_LOG_ARGS( "Error: " << aError << "; should never get here." ); + TX_EXIT + return; + } + iSongData->setMpxMedia( aMedia ); + TX_EXIT +} + +/*! + \internal + Handles the completion of any collection helper event. + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleOperationCompleteL( + TCHelperOperation aOperation, + TInt aErr, + void* aArgument ) +{ + TX_ENTRY_ARGS( "aErr=" << aErr ); + switch( aOperation ) { + case EDeleteOp: + emit q_ptr->songsDeleted( KErrNone == aErr ); + break; + case EAddOp: + emit q_ptr->playlistSaved( KErrNone == aErr ); + break; + case ERenameOp: + emit q_ptr->playlistsRenamed( KErrNone == aErr ); + break; + default: + break; + } + + if ( aArgument ) { + delete ( CBase* )aArgument; + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleIsolatedOpenL( const CMPXMedia& aEntries, TInt aError ) +{ + TX_ENTRY_ARGS( "aError=" << aError ); + if ( aError == KErrNone ) { + if ( iIsolatedCollectionData ) { + delete iIsolatedCollectionData; + iIsolatedCollectionData = 0; + } + iIsolatedCollectionData = new MpMpxCollectionData(); + iIsolatedCollectionData->setMpxMedia( aEntries ); + emit q_ptr->isolatedCollectionOpened( iIsolatedCollectionData ); + } + else { + TX_LOG_ARGS( "Error: " << aError << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleIsolatedOpenRestorePathL( const CMPXCollectionPath& aPath, TInt aError ) +{ + TX_ENTRY_ARGS( "aError=" << aError ); + if ( aError == KErrNone ) { + CMPXCollectionPath* cpath = CMPXCollectionPath::NewL( aPath ); + CleanupStack::PushL( cpath ); + if ( cpath->Count() <= 0 ) { + //There are no entries on the path + if ( !iRestoreDefaultPath ) { + //Try restoring default path if not already tried + //This is a special case where a playlist's songs where on the MMC and it was removed + iRestoreDefaultPath = ETrue; + iRestorePathIndex = 0; + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicAllSongsPathL(); + CleanupStack::PushL( cpath ); + iIsolatedCollectionHelper->OpenCollectionL( *cpath, iRestorePathIndex, CMpMpxIsolatedCollectionHelper::RestorePathMode ); + CleanupStack::PopAndDestroy( cpath ); + } + else { + //emit signal to go back to collection view because there is no music + emit q_ptr->restorePathFailed(); + } + } + else if ( iRestorePathIndex ) { + //If RestorePathIndex equals zero there is no need to check with previous index + //just go and create playlist below + if ( iRestorePathIndex == cpath->IndexOfId( iRestorePathIndexId ) ) { + //Song is in path and maintains previous position + cpath->Set( iRestorePathIndex ); + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + createPlaybackUtilityL(); + iPlaybackUtility->InitL( *playList, EFalse ); + CleanupStack::PopAndDestroy( playList ); + } + else { + //Re open path starting at the beginning of the collection + iRestorePathIndex = 0; + cpath->Back(); + iIsolatedCollectionHelper->OpenCollectionL( *cpath, iRestorePathIndex, CMpMpxIsolatedCollectionHelper::RestorePathMode ); + } + } + else { + //We create a playlist right away since there is no need to check the index for the first element + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + createPlaybackUtilityL(); + iPlaybackUtility->InitL( *playList, EFalse ); + CleanupStack::PopAndDestroy( playList ); + } + CleanupStack::PopAndDestroy( cpath ); + } + else if ( aError == KErrNotFound ) { + //Path not found (e.g. MMC removed) try restoring default path + iRestoreDefaultPath = ETrue; + iRestorePathIndex = 0; + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicAllSongsPathL(); + CleanupStack::PushL( cpath ); + iIsolatedCollectionHelper->OpenCollectionL( *cpath, iRestorePathIndex, CMpMpxIsolatedCollectionHelper::RestorePathMode ); + CleanupStack::PopAndDestroy( cpath ); + } + else { + //Open path failed + TX_LOG_ARGS( "Error: " << aError << "; should never get here." ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::HandleFindAllL( const CMPXMedia& aResults, TBool aComplete, TInt aError ) +{ + Q_UNUSED( aComplete ); + TX_ENTRY_ARGS( "aError=" << aError ); + + if ( aError == KErrNone ) { + iCollectionData->setAlbumContent( aResults ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoInitL() +{ + TX_ENTRY + iCollectionUtility = MMPXCollectionUtility::NewL( this, iHostUid ); + iCollectionUiHelper = CMPXCollectionHelperFactory:: NewCollectionUiHelperL( iHostUid ); + iIncrementalOpenUtil = CMPXCollectionOpenUtility::NewL( this, iHostUid ); + iCollectionData = new MpMpxCollectionData(); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoOpenCollectionL( + TCollectionContext aContext ) +{ + TX_ENTRY_ARGS( "aContext=" << aContext ); + + switch ( aContext ) { + case ECollectionContextAllSongs: + { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicAllSongsPathL(); + CleanupStack::PushL( cpath ); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + break; + } + case ECollectionContextArtists: + { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicMenuPathL(); + CleanupStack::PushL( cpath ); + cpath->AppendL( BrowseArtist ); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + break; + } + case ECollectionContextAlbums: + { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicMenuPathL(); + CleanupStack::PushL( cpath ); + cpath->AppendL( BrowseAlbum ); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + break; + } + case ECollectionContextPlaylists: + { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicPlaylistPathL(); + CleanupStack::PushL( cpath ); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + break; + } + case ECollectionContextAlbumsMediaWall: + { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicMenuPathL(); + CleanupStack::PushL( cpath ); + cpath->AppendL( BrowseAlbumMediaWall ); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + break; + } + default: + TX_LOG_ARGS( "Error: Unexpected context; should never get here." ); + break; + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoOpenCollectionItemL( TInt aIndex ) + { + TX_ENTRY_ARGS( "aIndex=" << aIndex ); + iCollectionUtility->Collection().OpenL( aIndex ); + TX_EXIT + } + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoIncrementalOpenL() +{ + TX_ENTRY + // Cancel any reads + iIncrementalOpenUtil->Stop(); + + // Start the read + iFirstIncrementalOpen = ETrue; + RArray attrs; + CleanupClosePushL( attrs ); + TArray ary = attrs.Array(); + iIncrementalOpenUtil->SetDelay( KIncrementalDelay ); + iIncrementalOpenUtil->StartL( ary, KIncrementalFetchBlockSize, + 0, CMPXCollectionOpenUtility::EFetchDown ); + CleanupStack::PopAndDestroy( &attrs ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoReopenCollectionL() +{ + TX_ENTRY + CMPXCollectionPath* cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + cpath->Back(); + iCollectionUtility->Collection().OpenL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoBackL() +{ + TX_ENTRY + iCollectionUtility->Collection().BackL(); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoFindPlaylistsL( QStringList &playlists ) +{ + TX_ENTRY + delete iUserPlaylists; + iUserPlaylists = NULL; + + RArray attrs; + CleanupClosePushL( attrs ); + attrs.AppendL( KMPXMediaGeneralId ); + attrs.AppendL( KMPXMediaGeneralTitle ); + + CMPXMedia* criteria = CMPXMedia::NewL(); + CleanupStack::PushL( criteria ); + criteria->SetTObjectValueL( + KMPXMediaGeneralType, EMPXGroup ); + criteria->SetTObjectValueL( + KMPXMediaGeneralCategory, EMPXPlaylist ); + + // Look up collection UID and set to criteria + RArray ary; + CleanupClosePushL( ary ); + ary.AppendL( TUid::Uid( EMPXCollectionPluginMusic ) ); + TUid musicCollection = iCollectionUtility->CollectionIDL( ary.Array() ); + CleanupStack::PopAndDestroy( &ary ); + + criteria->SetTObjectValueL( KMPXMediaGeneralCollectionId, musicCollection ); + + iUserPlaylists = iCollectionUtility->Collection().FindAllL( *criteria, attrs.Array() ); + CleanupStack::PopAndDestroy( criteria ); + CleanupStack::PopAndDestroy( &attrs ); + + if ( iUserPlaylists ) { + const CMPXMediaArray* mediaArray = + iUserPlaylists->Value( KMPXMediaArrayContents ); + User::LeaveIfNull( const_cast( mediaArray ) ); + TInt count = mediaArray->Count(); + for ( TInt i = 0; i < count; i++ ) { + CMPXMedia* media( mediaArray->AtL( i ) ); + const TDesC& titleText = media->ValueText( KMPXMediaGeneralTitle ); + if ( titleText.Compare( KNullDesC ) != 0 ) { + playlists += QString::fromUtf16( titleText.Ptr(), titleText.Length() ); + } + } + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoCreatePlaylistL( QString &playlistName, QList &selection, MpMpxCollectionData* collectionData ) +{ + TX_ENTRY_ARGS( "playlistName=" << playlistName ); + CMPXMedia* tracks = CMPXMedia::NewL(); + CleanupStack::PushL( tracks ); + + TPtrC ptr( reinterpret_cast( playlistName.constData() ) ); + tracks->SetTextValueL( KMPXMediaGeneralTitle, ptr ); + tracks->SetTextValueL( KMPXMediaGeneralUri, KPlaylistPath ); + //if collection data is not provided we use the browsing collection. + PreparePlaylistMediaL( *tracks, selection, collectionData ? collectionData : iCollectionData ); + + iCollectionUiHelper->IncAddL( *tracks, this, KMPXChunkSize ); + CleanupStack::PopAndDestroy( tracks ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoSaveToPlaylistL( TMPXItemId playlistId, QList &selection, MpMpxCollectionData *collectionData ) +{ + TX_ENTRY_ARGS( "playlistId=" << int( playlistId ) ); + + CMPXMedia* tracks = CMPXMedia::NewL(); + CleanupStack::PushL( tracks ); + + RArray ary; + CleanupClosePushL( ary ); + ary.AppendL( TUid::Uid( EMPXCollectionPluginMusic ) ); + TUid musicCollection = iCollectionUtility->CollectionIDL( ary.Array() ); + CleanupStack::PopAndDestroy( &ary ); + + tracks->SetTObjectValueL( KMPXMediaGeneralId, playlistId ); + tracks->SetTObjectValueL( KMPXMediaGeneralCollectionId, musicCollection ); + PreparePlaylistMediaL( *tracks, selection, collectionData ); + + iCollectionUiHelper->IncAddL( *tracks, this, KMPXChunkSize ); + CleanupStack::PopAndDestroy( tracks ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoSaveToPlaylistL( int playlistIndex, QList &selection ) +{ + TX_ENTRY_ARGS( "playlistIndex=" << playlistIndex ); + + const CMPXMediaArray* mediaArray = iUserPlaylists->Value( KMPXMediaArrayContents ); + User::LeaveIfNull( const_cast( mediaArray ) ); + CMPXMedia* media( mediaArray->AtL( playlistIndex ) ); + TMPXItemId playlistId = media->ValueTObjectL( KMPXMediaGeneralId ); + DoSaveToPlaylistL( playlistId, selection, iCollectionData ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoSaveToCurrentPlaylistL( QList &selection, MpMpxCollectionData *collectionData ) +{ + TX_ENTRY + + const CMPXMedia& container = iCollectionData->containerMedia(); + if ( container.ValueTObjectL(KMPXMediaGeneralType) != EMPXItem && + container.ValueTObjectL(KMPXMediaGeneralCategory) != EMPXPlaylist) { + User::Leave( KErrArgument ); + } + TMPXItemId playlistId( container.ValueTObjectL( KMPXMediaGeneralId ) ); + DoSaveToPlaylistL( playlistId, selection, collectionData ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoDeleteSongsL( QList &selection ) +{ + int count = selection.count(); + TX_ENTRY_ARGS( "selection count=" << count ); + + CMPXCollectionPath* path( iCollectionUtility->Collection().PathL() ); + CleanupStack::PushL( path ); + + if (count > 1) { + for ( TInt i = 0; i < count; i++ ){ + path->SelectL( selection.at( i ) ); + } + } + else { + path->Set( selection.at(0) ); + } + + iCollectionUiHelper->DeleteL( *path, this ); + CleanupStack::PopAndDestroy( path ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoDeleteAlbumSongsL( QList &selection ) +{ + int count = selection.count(); + TX_ENTRY_ARGS( "selection count=" << count ); + + CMPXCollectionPath* path( iCollectionUtility->Collection().PathL() ); + CleanupStack::PushL( path ); + MPX_DEBUG_PATH( *path ); + + CMPXMediaArray *mediaArray; + const CMPXMedia& container = iCollectionData->containerMedia(); + mediaArray = const_cast( container.Value( KMPXMediaArrayContents ) ); + int currentAlbumIndex = iCollectionData->currentAlbumIndex(); + CMPXMedia* album( mediaArray->AtL( currentAlbumIndex ) ); + if ( album->IsSupported(KMPXMediaArrayContents) ) { + const CMPXMediaArray* songs = album->Value(KMPXMediaArrayContents); + User::LeaveIfNull(const_cast(songs)); + int index = selection.at(0); + CMPXMedia* song = songs->AtL(index); + + TMPXItemId id( song->ValueTObjectL( KMPXMediaGeneralId ) ); + path->AppendL( id ); // Append the song ID to be deleted + path->Set( 0 ); // Select 1st song + + iCollectionUiHelper->DeleteL( *path, this ); + } + CleanupStack::PopAndDestroy( path ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoRenamePlaylistL( QString &newName, int index ) +{ + TX_ENTRY + CMPXMediaArray *mediaArray; + const CMPXMedia& container = iCollectionData->containerMedia(); + mediaArray = const_cast( container.Value( KMPXMediaArrayContents ) ); + CMPXMedia* currentPlaylistMedia( mediaArray->AtL( index ) ); + TMPXItemId id( currentPlaylistMedia->ValueTObjectL( KMPXMediaGeneralId ) ); + DoRenamePlaylistL( id, newName ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoRenamePlaylistL( QString &newName ) +{ + TX_ENTRY + const CMPXMedia& container = iCollectionData->containerMedia(); + TMPXItemId id( container.ValueTObjectL( KMPXMediaGeneralId ) ); + DoRenamePlaylistL( id, newName ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoRenamePlaylistL( TMPXItemId id, QString &newName ) + { + CMPXMedia* media = CMPXMedia::NewL(); + CleanupStack::PushL( media ); + media->SetTObjectValueL( + KMPXMediaGeneralType, EMPXItem ); + media->SetTObjectValueL( + KMPXMediaGeneralCategory, EMPXPlaylist ); + media->SetTObjectValueL( KMPXMediaGeneralId, id ); + TPtrC ptr( reinterpret_cast( newName.constData() ) ); + media->SetTextValueL( KMPXMediaGeneralTitle, ptr ); + iCollectionUiHelper->RenameL( *media, this ); + CleanupStack::PopAndDestroy( media ); + } + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoSetShuffleL( bool active ) +{ + TX_ENTRY + if ( iPlaybackUtility ) { + iPlaybackUtility->SetL( EPbPropertyRandomMode, active ); + } + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoPreviewSongL( int index ) +{ + TX_ENTRY + + // Get the current path + CMPXCollectionPath* cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + MPX_DEBUG_PATH( *cpath ); + cpath->Back(); + + TMPXItemId id( iCollectionData->itemId(index) ); + cpath->AppendL( id ); // Top level items of songs + cpath->Set( 0 ); // Select 1st song + + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + playList->SetToFirst(); + //TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + createPlaybackUtilityL(); + iPlaybackUtility->InitL( *playList, ETrue ); + emit q_ptr->collectionPlaylistOpened(); + + CleanupStack::PopAndDestroy( playList ); + CleanupStack::PopAndDestroy( cpath ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoPreviewAlbumSongL( int index ) +{ + TX_ENTRY + //TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + if ( !iPlaybackUtility ) { + iPlaybackUtility = MMPXPlaybackUtility::UtilityL( iHostUid ); + } + + // Get the current path + CMPXCollectionPath* cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + MPX_DEBUG_PATH( *cpath ); + + CMPXMediaArray *mediaArray; + const CMPXMedia& container = iCollectionData->containerMedia(); + mediaArray = const_cast( container.Value( KMPXMediaArrayContents ) ); + int currentAlbumIndex = iCollectionData->currentAlbumIndex(); + CMPXMedia* album( mediaArray->AtL( currentAlbumIndex ) ); + if ( album->IsSupported(KMPXMediaArrayContents) ) { + const CMPXMediaArray* songs = album->Value(KMPXMediaArrayContents); + User::LeaveIfNull(const_cast(songs)); + CMPXMedia* song = songs->AtL(index); + + TMPXItemId id( song->ValueTObjectL( KMPXMediaGeneralId ) ); + cpath->AppendL( id ); // Top level items of songs + cpath->Set( 0 ); // Select 1st song + + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + playList->SetToFirst(); + //TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + iPlaybackUtility->InitL( *playList, ETrue ); + emit q_ptr->collectionPlaylistOpened(); + + CleanupStack::PopAndDestroy( playList ); + } + CleanupStack::PopAndDestroy( cpath ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoOpenIsolatedCollectionL( TCollectionContext context ) +{ + + if ( ECollectionContextAllSongs == context ) { + CMPXCollectionPath* cpath = iCollectionUiHelper->MusicAllSongsPathL(); + CleanupStack::PushL( cpath ); + if ( !iIsolatedCollectionHelper ) { + iIsolatedCollectionHelper = CMpMpxIsolatedCollectionHelper::NewL( this ); + } + iIsolatedCollectionHelper->OpenCollectionL( *cpath ); + CleanupStack::PopAndDestroy( cpath ); + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoReorderPlaylistL( int playlistId, int songId, int originalOrdinal, int newOrdinal ) +{ + iCollectionUiHelper->ReorderPlaylistL( playlistId, songId, originalOrdinal, newOrdinal, this ); +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoFindAlbumSongsL( int index ) +{ + const CMPXMedia& container = iCollectionData->containerMedia(); + const CMPXMediaArray* mediaArray = container.Value( KMPXMediaArrayContents ); + CMPXMedia* album( mediaArray->AtL( index ) ); + + // Obtain the artistId from the container + TMPXItemId artistId = container.ValueTObjectL(KMPXMediaGeneralId); + + // Fetch the songs for the selected album and the artist + // Specifying artistId is necessary to search for songs in the artist’s unknown album. + TMPXItemId albumId = album->ValueTObjectL(KMPXMediaGeneralId); + CMPXMedia* findCriteria = CMPXMedia::NewL(); + CleanupStack::PushL( findCriteria ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralType, EMPXGroup ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralCategory, EMPXSong ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralId, albumId ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralContainerId, artistId ); + RArray attrs; + CleanupClosePushL( attrs ); + attrs.AppendL( TMPXAttribute( KMPXMediaIdGeneral, + EMPXMediaGeneralTitle | + EMPXMediaGeneralUri | + EMPXMediaGeneralId | + EMPXMediaGeneralType | + EMPXMediaGeneralCategory | + EMPXMediaGeneralFlags ) ); + attrs.AppendL( KMPXMediaMusicAlbumTrack ); + + iCollectionUtility->Collection().FindAllL( *findCriteria, attrs.Array(), *this ); + CleanupStack::PopAndDestroy( &attrs ); + CleanupStack::PopAndDestroy( findCriteria ); +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoPlayAlbumSongsL( int albumIndex, int songIndex, MpMpxCollectionData* collectionData ) +{ + TX_ENTRY + + RArray ids; + CleanupClosePushL(ids); + + CMPXCollectionPath* cpath; + + //Following check is for a use case for media wall, where it is required + //to play songs that are browsed by an isolated collection. + if ( collectionData->context() == ECollectionContextAlbumsMediaWall ) { + //Get the Media Wall path. + cpath = iCollectionUiHelper->MusicMenuPathL(); + CleanupStack::PushL( cpath ); + //TODO: change to BrowseAlbumMediaWall befor when merging with olveras changes. + cpath->AppendL( BrowseAlbum ); + const TMPXItemId albumId = collectionData->itemId( albumIndex ); + //Append the selected album. + RArray items; + CleanupClosePushL(items); + items.AppendL(albumId); + cpath->AppendL(items.Array()); + CleanupStack::PopAndDestroy( &items ); + cpath->Set( 0 ); // Set the album. + + } + else { + // Get the current path + cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + cpath->Set(albumIndex); // Set the selected album + } + MPX_DEBUG_PATH( *cpath ); + + CMPXMediaArray *mediaArray; + const CMPXMedia& container = collectionData->containerMedia(); + mediaArray = const_cast( container.Value( KMPXMediaArrayContents ) ); + CMPXMedia* album( mediaArray->AtL( albumIndex ) ); + const CMPXMediaArray* songs = album->Value(KMPXMediaArrayContents); + User::LeaveIfNull(const_cast(songs)); + + TInt count = songs->Count(); + for ( TInt i = 0; i < count; ++i ) { + CMPXMedia* song = songs->AtL(i); + const TMPXItemId id = song->ValueTObjectL(KMPXMediaGeneralId); + ids.AppendL(id); + } + + cpath->AppendL(ids.Array()); // Top level items of songs + cpath->Set(songIndex); // Set the selected song + MPX_DEBUG_PATH(*cpath); + + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + + //TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + createPlaybackUtilityL(); + iPlaybackUtility->InitL( *playList, ETrue ); + emit q_ptr->collectionPlaylistOpened(); + + CleanupStack::PopAndDestroy( playList ); + CleanupStack::PopAndDestroy( cpath ); + CleanupStack::PopAndDestroy( &ids ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::setRepeatFeatureEnabled( bool enable ) +{ + iRepeatFeature = enable; +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::setShuffleFeatureEnabled( bool enable ) +{ + iShuffleFeature = enable; +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoHandleCollectionMessageL( + const CMPXMessage& aMsg ) +{ + TX_ENTRY + TMPXMessageId id( aMsg.ValueTObjectL( KMPXMessageGeneralId ) ); + if ( KMPXMessageGeneral == id ) { + TInt event( aMsg.ValueTObjectL( KMPXMessageGeneralEvent ) ); + TInt type( aMsg.ValueTObjectL( KMPXMessageGeneralType ) ); + TInt data( aMsg.ValueTObjectL( KMPXMessageGeneralData ) ); + TX_LOG_ARGS( "event=" << event << ", type=" << type << ", data=" << data ); + + if ( event == TMPXCollectionMessage::EPathChanged && + type == EMcPathChangedByOpen && + data == EMcContainerOpened ) { + // Incremental Open when browsing to the next level + DoIncrementalOpenL(); + } + else if ( event == TMPXCollectionMessage::EPathChanged && + type == EMcPathChangedByOpen && + data == EMcItemOpened ) { + // Opened a song + // This will result in HandleOpenL with CMPXCollectionPlaylist + iCollectionUtility->Collection().OpenL(); + } + } + else if( id == KMPXMessageIdItemChanged ) { + TInt eventType( aMsg.ValueTObjectL( KMPXMessageChangeEventType ) ); + + if ( eventType == EMPXItemDeleted || eventType == EMPXItemInserted ) { + emit q_ptr->containerContentsChanged(); + } + } + TX_EXIT +} + + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::PreparePlaylistMediaL( + CMPXMedia& aMedia, + QList &selection, + MpMpxCollectionData *collectionData ) +{ + int count = selection.count(); + TX_ENTRY_ARGS( "selection count=" << count ); + + const CMPXMediaArray* mediaArray = 0; + + if ( ( collectionData->context() == ECollectionContextArtistAlbumsTBone ) || + ( collectionData->context() == ECollectionContextAlbumsTBone ) ) { + //There is no need to find the track information, for TBone we cash it under the media itself. + //Fetching song data from container media. + CMPXMedia* album; + const CMPXMediaArray* albumsArray; + albumsArray = collectionData->containerMedia().Value( KMPXMediaArrayContents ); + int index = collectionData->currentAlbumIndex(); + if ( index >= 0 ) { + album = albumsArray->AtL( collectionData->currentAlbumIndex() ); + mediaArray = album->Value( KMPXMediaArrayContents ); + } + } + else { + const CMPXMedia& container = collectionData->containerMedia(); + mediaArray = container.Value( KMPXMediaArrayContents ); + } + + User::LeaveIfNull( const_cast( mediaArray ) ); + CMPXMediaArray* tracksArray( CMPXMediaArray::NewL() ); + CleanupStack::PushL( tracksArray ); + + CMPXCollectionPath* path( iCollectionUtility->Collection().PathL() ); + CleanupStack::PushL( path ); + TMPXItemId collectionId( path->Id( 0 ) ); + CleanupStack::PopAndDestroy( path ); + + if ( collectionData->context() == ECollectionContextAlbums || + collectionData->context() == ECollectionContextArtistAlbums || + collectionData->context() == ECollectionContextArtists ) { + //Container, it is possible to append multiple containers to a playlist. + //Currently we are just using single selection from the ui. + for ( TInt i = 0; i < count; i++ ) { + CMPXMedia* results; + CMPXMedia* container( mediaArray->AtL( selection[i] ) ); + // Fetch the songs for the selected container + TMPXItemId containerId = container->ValueTObjectL( KMPXMediaGeneralId ); + CMPXMedia* findCriteria = CMPXMedia::NewL(); + CleanupStack::PushL( findCriteria ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralType, EMPXGroup ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralCategory, EMPXSong ); + findCriteria->SetTObjectValueL( KMPXMediaGeneralId, containerId ); + RArray attrs; + CleanupClosePushL( attrs ); + attrs.AppendL( TMPXAttribute( KMPXMediaIdGeneral, + EMPXMediaGeneralTitle | + EMPXMediaGeneralId ) ); + results = iCollectionUtility->Collection().FindAllL( *findCriteria, attrs.Array() ); + CleanupStack::PopAndDestroy( &attrs ); + CleanupStack::PopAndDestroy( findCriteria ); + CleanupStack::PushL( results ); + + const CMPXMediaArray* resultsArray = results->Value( KMPXMediaArrayContents ); + User::LeaveIfNull( resultsArray ); + for ( int j = 0 ; j < resultsArray->Count();j++ ) { + CMPXMedia* media( resultsArray->AtL( j ) ); + CMPXMedia* entry = CMPXMedia::NewL(); + CleanupStack::PushL( entry ); + entry->SetTextValueL( KMPXMediaGeneralTitle, + media->ValueText( KMPXMediaGeneralTitle ) ); + entry->SetTObjectValueL( KMPXMediaGeneralType, EMPXItem ); + entry->SetTObjectValueL( KMPXMediaGeneralCategory, EMPXSong ); + entry->SetTObjectValueL( KMPXMediaGeneralId, + media->ValueTObjectL( KMPXMediaGeneralId ) ); + entry->SetTObjectValueL( KMPXMediaGeneralCollectionId, collectionId ); + CleanupStack::Pop( entry ); + tracksArray->AppendL( entry ); + } + CleanupStack::PopAndDestroy( results ); + } + + } + else { + //Tracks + for ( TInt i = 0; i < count; i++ ) { + CMPXMedia* media( mediaArray->AtL( selection.at( i ) ) ); + CMPXMedia* entry = CMPXMedia::NewL(); + CleanupStack::PushL( entry ); + entry->SetTextValueL( KMPXMediaGeneralTitle, + media->ValueText( KMPXMediaGeneralTitle ) ); + entry->SetTObjectValueL( KMPXMediaGeneralType, EMPXItem ); + entry->SetTObjectValueL( KMPXMediaGeneralCategory, EMPXSong ); + entry->SetTObjectValueL( KMPXMediaGeneralId, + media->ValueTObjectL( KMPXMediaGeneralId ) ); + entry->SetTObjectValueL( KMPXMediaGeneralCollectionId, collectionId ); + CleanupStack::Pop( entry ); + tracksArray->AppendL( entry ); + } + } + aMedia.SetTObjectValueL( KMPXMediaGeneralType, EMPXItem ); + aMedia.SetTObjectValueL( KMPXMediaGeneralCategory, EMPXPlaylist ); + aMedia.SetCObjectValueL( KMPXMediaArrayContents, tracksArray ); + aMedia.SetTObjectValueL( KMPXMediaArrayCount, tracksArray->Count() ); + + emit q_ptr->aboutToAddSongs( tracksArray->Count() ); + + CleanupStack::PopAndDestroy( tracksArray ); + TX_EXIT +} + +/*! + \internal + TODO: all calls to playback utility should be done via the engine and trough the playback FW wrapper. + */ +void MpMpxCollectionFrameworkWrapperPrivate::createPlaybackUtilityL() +{ + if ( !iPlaybackUtility ) { + + iPlaybackUtility = MMPXPlaybackUtility::UtilityL( iHostUid ); + + if ( iShuffleFeature ) { + iPlaybackUtility->SetL( EPbPropertyRandomMode, MpSettingsManager::shuffle() ? ETrue : EFalse ); + } + if ( iRepeatFeature ) { + iPlaybackUtility->SetL( EPbPropertyRepeatMode, MpSettingsManager::repeat() ? EPbRepeatAll : EPbRepeatOff ); + } + } +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoPlayAllSongsPlaylistL() +{ + TX_ENTRY + CMPXCollectionPath* cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + CMPXCollectionPlaylist* playList = CMPXCollectionPlaylist::NewL( *cpath ); + CleanupStack::PushL( playList ); + playList->SetShuffleL( true, false ); + MpSettingsManager::setShuffle( true ); + createPlaybackUtilityL(); + iPlaybackUtility->InitL( *playList, ETrue ); + CleanupStack::PopAndDestroy( playList ); + CleanupStack::PopAndDestroy( cpath ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoRetrieveSongDetailsL( int index ) +{ + TX_ENTRY + RArray requestedAttr; + CleanupClosePushL( requestedAttr ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaGeneralTitle ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicArtist ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicAlbum ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaGeneralUri ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicAlbumArtFileName ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaGeneralMimeType ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicAlbumTrack ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicComposer ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicYear ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicGenre ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaGeneralDuration ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaAudioBitrate ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaAudioSamplerate ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaGeneralCopyright ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaMusicURL ) ); + requestedAttr.AppendL( TMPXAttribute( KMPXMediaDrmProtected ) ); + + CMPXCollectionPath* cpath = iCollectionUtility->Collection().PathL(); + CleanupStack::PushL( cpath ); + TCollectionContext context = iCollectionData->context(); + if ( context == ECollectionContextArtistAlbumsTBone + || context == ECollectionContextAlbumsTBone ) { + CMPXMediaArray *mediaArray; + const CMPXMedia& container = iCollectionData->containerMedia(); + mediaArray = const_cast( container.Value( KMPXMediaArrayContents ) ); + int currentAlbumIndex = iCollectionData->currentAlbumIndex(); + CMPXMedia* album( mediaArray->AtL( currentAlbumIndex ) ); + if ( album->IsSupported(KMPXMediaArrayContents) ) { + const CMPXMediaArray* songs = album->Value(KMPXMediaArrayContents); + User::LeaveIfNull(const_cast(songs)); + CMPXMedia* song = songs->AtL(index); + TMPXItemId id( song->ValueTObjectL( KMPXMediaGeneralId ) ); + cpath->AppendL( id ); // Top level items of songs + cpath->Set( 0 ); // Select 1st song + } + } + else { + cpath->Set( index ); + } + iCollectionUtility->Collection().MediaL( *cpath, requestedAttr.Array() ); + CleanupStack::PopAndDestroy( cpath ); + CleanupStack::PopAndDestroy( &requestedAttr ); + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoSavePathL( QByteArray &data ) +{ + TX_ENTRY + CBufFlat* buffer = CBufFlat::NewL( 256 ); + CleanupStack::PushL( buffer ); + TBufBuf bufBuf; + bufBuf.Set( *buffer, 0, TBufBuf::EWrite ); + + RWriteStream writeStream( &bufBuf ); + writeStream.PushL(); + + if ( iPlaybackUtility ) { + MMPXSource* source = iPlaybackUtility->Source(); + CMPXCollectionPlaylist* playList( NULL ); + if( source ) { + playList = source->PlaylistL(); + if ( playList ) { + CleanupStack::PushL( playList ); + const CMPXCollectionPath& cpath = playList->Path(); + writeStream << cpath; + writeStream.CommitL(); + CleanupStack::PopAndDestroy( playList ); + } + } + } + data.append(reinterpret_cast(buffer->Ptr(0).Ptr()) ,buffer->Ptr(0).Length()); + CleanupStack::PopAndDestroy( 2, buffer ); //writeStream and buffer + TX_EXIT +} + +/*! + \internal + */ +void MpMpxCollectionFrameworkWrapperPrivate::DoRestorePathL( const QByteArray &data ) +{ + TX_ENTRY + int dataSize = data.size(); + if ( dataSize > 0 ) { + TPtrC8 activityDataDescriptor( reinterpret_cast ( data.constData() ), data.size() ); + + //Take a copy of the data + CBufFlat* buffer = CBufFlat::NewL( dataSize ); + CleanupStack::PushL( buffer ); + buffer->InsertL( 0, activityDataDescriptor, dataSize ); + + TBufBuf bufBuf; + bufBuf.Set( *buffer, 0, TBufBuf::ERead ); + RReadStream readStream( &bufBuf ); + readStream.PushL(); + + CMPXCollectionPath* cpath( NULL ); + cpath = CMPXCollectionPath::NewL(readStream); + CleanupStack::PushL(cpath); + iRestorePathIndex = 0; + if( cpath->Levels() ) { + iRestorePathIndexId = cpath->Id(); + iRestorePathIndex = cpath->Index(); + cpath->Back(); + } + if ( !iIsolatedCollectionHelper ) { + iIsolatedCollectionHelper = CMpMpxIsolatedCollectionHelper::NewL( this ); + } + iIsolatedCollectionHelper->OpenCollectionL( *cpath, iRestorePathIndex, CMpMpxIsolatedCollectionHelper::RestorePathMode ); + + CleanupStack::PopAndDestroy( cpath ); + CleanupStack::PopAndDestroy( 2, buffer ); //readStream and buffer + } + TX_EXIT +} + +//EOF