psln/pslnengine/src/PslnSkinStore.cpp
changeset 37 89c890c70182
parent 34 6b5204869ed5
child 45 667edd0b8678
equal deleted inserted replaced
34:6b5204869ed5 37:89c890c70182
     1 /*
       
     2 * Copyright (c) 2004-2007 Nokia Corporation and/or its subsidiary(-ies).
       
     3 * All rights reserved.
       
     4 * This component and the accompanying materials are made available
       
     5 * under the terms of "Eclipse Public License v1.0"
       
     6 * which accompanies this distribution, and is available
       
     7 * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 *
       
     9 * Initial Contributors:
       
    10 * Nokia Corporation - initial contribution.
       
    11 *
       
    12 * Contributors:
       
    13 *
       
    14 * Description:  Skin store.
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 // INCLUDE FILES
       
    20 
       
    21 // Psln specific.
       
    22 #include "PslnSkinStore.h"
       
    23 #include "PslnModel.h"
       
    24 #include "PslnSkinEntry.h"
       
    25 #include "PslnDebug.h"
       
    26 
       
    27 // Repository
       
    28 #include <centralrepository.h>
       
    29 #include <AknSkinsInternalCRKeys.h>
       
    30 #include <AknsSkinUID.h>
       
    31 
       
    32 #ifdef RD_MULTIPLE_DRIVE
       
    33 #include <driveinfo.h>
       
    34 #endif //RD_MULTIPLE_DRIVE
       
    35 
       
    36 void CleanupDeleteArray( TAny* aArray )
       
    37     {
       
    38     static_cast<RPointerArray<CPslnSkinNameEntry>*>
       
    39         (aArray)->ResetAndDestroy();
       
    40     delete aArray;
       
    41     aArray = NULL;
       
    42     }
       
    43 
       
    44 // ============================ MEMBER FUNCTIONS ===============================
       
    45 
       
    46 // -----------------------------------------------------------------------------
       
    47 // C++ default constructor can NOT contain any code, that
       
    48 // might leave.
       
    49 // -----------------------------------------------------------------------------
       
    50 //
       
    51 CPslnSkinStore::CPslnSkinStore()
       
    52     {
       
    53     }
       
    54 
       
    55 // -----------------------------------------------------------------------------
       
    56 // Symbian 2nd phase constructor can leave.
       
    57 // -----------------------------------------------------------------------------
       
    58 //
       
    59 void CPslnSkinStore::ConstructL( CPslnModel* aModel )
       
    60     {
       
    61     iModel = aModel;
       
    62 
       
    63     CRepository* repository = CRepository::NewLC( KCRUidPersonalisation );
       
    64     TInt value = KAknsNullPkgID.iNumber;
       
    65     iDefaultSkinPID.Set( KAknsPIDS60DefaultSkin );
       
    66     TBuf<32> buf;
       
    67     TAknsPkgID defaultSkin = KAknsNullPkgID;
       
    68 
       
    69     TInt err = repository->Get( KPslnDefaultSkinUID, buf );
       
    70     if ( err != KErrNone || buf.Length() == 0 )
       
    71         {
       
    72         err = repository->Get( KPslnDefaultSkinID, value );
       
    73         if( err == KErrNone )
       
    74             {
       
    75             defaultSkin.Set( TUid::Uid( value ) );
       
    76             }
       
    77         }
       
    78     else
       
    79         {
       
    80         TInt bufLength = buf.Length();
       
    81         // If its 8 characters long, its UID.
       
    82         // PIDs are 16 characters (8 ID + 8 timestamp)
       
    83         if ( bufLength == 8 )
       
    84             {
       
    85             // Let's try to set it directly as Hex.
       
    86             TLex hexLex( buf );
       
    87             TUint pid;
       
    88             err = hexLex.Val( pid, EHex );
       
    89             if (!err)
       
    90                 {
       
    91                 // UIDs have no timestamp.
       
    92                 defaultSkin.Set( 0, pid );
       
    93                 }
       
    94             }
       
    95         else
       
    96             {
       
    97             // The skin PID is set in CenRep in format <PID1><PID2> and
       
    98             // values are in hex.
       
    99             TLex lex ( buf.Left( 8 ) );
       
   100             TLex lex2 ( buf.Right( 8 ) );
       
   101             TUint pid;
       
   102             TUint timeStamp;
       
   103             err = lex.Val( pid, EHex );
       
   104             if ( !err )
       
   105                 {
       
   106                 err = lex2.Val( timeStamp, EHex );
       
   107                 }
       
   108             if ( !err )
       
   109                 {
       
   110                 defaultSkin.Set( timeStamp, pid );
       
   111                 }
       
   112             }
       
   113         }
       
   114     iDefaultSkinPID = defaultSkin;
       
   115     CleanupStack::PopAndDestroy( repository );
       
   116     }
       
   117 
       
   118 // -----------------------------------------------------------------------------
       
   119 // Two-phased constructor.
       
   120 // -----------------------------------------------------------------------------
       
   121 //
       
   122 CPslnSkinStore* CPslnSkinStore::NewL( CPslnModel* aModel )
       
   123     {
       
   124     PSLN_TRACE_DEBUG("CPslnSkinStore::NewL");
       
   125 
       
   126     CPslnSkinStore* self = new( ELeave ) CPslnSkinStore;
       
   127     CleanupStack::PushL( self );
       
   128     self->ConstructL( aModel );
       
   129     CleanupStack::Pop( self );
       
   130     return self;
       
   131     }
       
   132 
       
   133 // -----------------------------------------------------------------------------
       
   134 // Destructor.
       
   135 // -----------------------------------------------------------------------------
       
   136 //
       
   137 CPslnSkinStore::~CPslnSkinStore()
       
   138     {
       
   139     iSkinArray.ResetAndDestroy();
       
   140     }
       
   141 
       
   142 // -----------------------------------------------------------------------------
       
   143 // CPslnSkinStore::UpdateAllSkinsL
       
   144 // -----------------------------------------------------------------------------
       
   145 //
       
   146 void CPslnSkinStore::UpdateAllSkinsL( RFs& aFsSession )
       
   147     {
       
   148     PSLN_TRACE_DEBUG("CPslnSkinStore::UpdateAllSkinsL");
       
   149 
       
   150     TInt i = KErrNone;
       
   151 
       
   152     // Mark all the existing skins
       
   153     for( ; i < iSkinArray.Count(); i++ )
       
   154         {
       
   155         CPslnSkinEntry* entry = iSkinArray[i];
       
   156         entry->SetDeleteFlag( ETrue );
       
   157         }
       
   158     UpdateAllSkinsL( EAknsSrvAll, aFsSession );
       
   159 
       
   160     // Remove any skins that haven't existed (they no longer exist)
       
   161     TInt skinCount = iSkinArray.Count() - 1;
       
   162     for( i = skinCount; i >= 0; i-- )
       
   163         {
       
   164         CPslnSkinEntry* entry = iSkinArray[i];
       
   165         if( entry && entry->IsDeleteFlag() )
       
   166             {
       
   167             delete entry;
       
   168             iSkinArray.Remove( i );
       
   169             }
       
   170         }
       
   171 
       
   172     // Then sort the array
       
   173     iSkinArray.Sort( CPslnSkinEntry::LinearOrder );
       
   174 
       
   175     // Finally, move default skin as first item in the array.
       
   176     i = KErrNotFound;
       
   177     skinCount = iSkinArray.Count() - 1;
       
   178     CPslnSkinEntry* entry = NULL;
       
   179     for( i = skinCount; i >= 0; i-- )
       
   180         {
       
   181         entry = iSkinArray[i];
       
   182         // move default theme first, if it is not already there.
       
   183         if ( ( entry->PkgID() == iDefaultSkinPID ) && ( i != 0 ) )
       
   184             {
       
   185             // Default skin found.
       
   186             iSkinArray.Remove( i );
       
   187             iSkinArray.Insert( entry, 0 );
       
   188             entry = NULL; // this is not owned by us.
       
   189             break;
       
   190             }
       
   191         }
       
   192     }
       
   193 
       
   194 // -----------------------------------------------------------------------------
       
   195 // CPslnSkinStore::Find
       
   196 // -----------------------------------------------------------------------------
       
   197 //
       
   198 CPslnSkinEntry* CPslnSkinStore::Find( const TAknsPkgID& aPID, 
       
   199     TAknSkinSrvSkinPackageLocation aLocation )
       
   200     {
       
   201     PSLN_TRACE_DEBUG("CPslnSkinStore::Find");
       
   202     TBool allLocations = ( aLocation == EAknsSrvAll );
       
   203     CPslnSkinEntry* entry = NULL;
       
   204 
       
   205     for( TInt i = 0; i < iSkinArray.Count(); i++ )
       
   206         {
       
   207         entry = iSkinArray[i];
       
   208 
       
   209         // If PID matches AND
       
   210         // location mathes (or is looking from all locations).
       
   211         if( ( entry && entry->PkgID() == aPID ) &&
       
   212               ( ( allLocations ) ||
       
   213               ( entry->Location() == aLocation ) ) )
       
   214             {
       
   215             // this entry is the one we are looking for.
       
   216             break;
       
   217             }
       
   218         else
       
   219             {
       
   220             entry = NULL;
       
   221             }
       
   222         }
       
   223 
       
   224     return entry;
       
   225     }
       
   226 
       
   227 // -----------------------------------------------------------------------------
       
   228 // CPslnSkinStore::UpdateOrAddL
       
   229 // -----------------------------------------------------------------------------
       
   230 //
       
   231 CPslnSkinEntry* CPslnSkinStore::UpdateOrAddL( 
       
   232     CAknsSrvSkinInformationPkg* aInfo, RFs& aFsSession )
       
   233     {
       
   234     PSLN_TRACE_DEBUG("CPslnSkinStore::UpdateOrAddL");
       
   235 
       
   236     if( !aInfo )
       
   237         {
       
   238         User::Leave( KErrArgument );
       
   239         }
       
   240     CleanupStack::PushL( aInfo );
       
   241 
       
   242     CPslnSkinEntry* entry = Find( aInfo->PID(),
       
   243         CPslnSkinEntry::LocationFromPath( aInfo->IniFileDirectory() ) );
       
   244 
       
   245 #ifdef RD_MULTIPLE_DRIVE
       
   246     TInt drive = EDriveC;
       
   247     TUint driveStatus = 0;
       
   248     TFileName fileName;
       
   249 #endif // RD_MULTIPLE_DRIVE
       
   250 
       
   251     if( entry )
       
   252         {
       
   253 #ifdef RD_MULTIPLE_DRIVE
       
   254         entry->GetSkinPath( fileName );
       
   255         User::LeaveIfError( RFs::CharToDrive( fileName[0], drive ) );
       
   256         User::LeaveIfError( DriveInfo::GetDriveStatus( 
       
   257             aFsSession, drive, driveStatus ) );
       
   258         if ( driveStatus & DriveInfo::EDriveExternallyMountable &&
       
   259              driveStatus & DriveInfo::EDriveRemovable )
       
   260             {
       
   261             entry->SetMemoryCardFlag( ETrue );
       
   262             }
       
   263         else if ( driveStatus & DriveInfo::EDriveExternallyMountable )
       
   264             {
       
   265             entry->SetMassDriveFlag( ETrue );
       
   266             }
       
   267 #endif // RD_MULTIPLE_DRIVE
       
   268 
       
   269         entry->SetProtection( aInfo->ProtectionType() );
       
   270         CleanupStack::PopAndDestroy( aInfo );
       
   271         }
       
   272     else
       
   273         {
       
   274         // Ownership of aInfo is transferred to CPslnSkinEntry.
       
   275         entry = CPslnSkinEntry::NewL( aInfo );
       
   276         CleanupStack::Pop( aInfo );
       
   277         CleanupStack::PushL( entry );
       
   278 
       
   279 #ifdef RD_MULTIPLE_DRIVE
       
   280         entry->GetSkinPath( fileName );
       
   281         User::LeaveIfError( RFs::CharToDrive( fileName[0], drive ) );
       
   282         User::LeaveIfError( DriveInfo::GetDriveStatus( 
       
   283             aFsSession, drive, driveStatus ) );
       
   284         if ( driveStatus & DriveInfo::EDriveExternallyMountable &&
       
   285              driveStatus & DriveInfo::EDriveRemovable )
       
   286             {
       
   287             entry->SetMemoryCardFlag( ETrue );
       
   288             }
       
   289         else if ( driveStatus & DriveInfo::EDriveExternallyMountable )
       
   290             {
       
   291             entry->SetMassDriveFlag( ETrue );
       
   292             }
       
   293 #endif // RD_MULTIPLE_DRIVE
       
   294 
       
   295         // Using Append instead of InsertInOrderAllowRepeats, since localized
       
   296         // names are not fetched yet for all the items.
       
   297         User::LeaveIfError( iSkinArray.Append( entry ) );
       
   298         CleanupStack::Pop( entry );
       
   299         }
       
   300 
       
   301     return entry;
       
   302     }
       
   303 
       
   304 // -----------------------------------------------------------------------------
       
   305 // CPslnSkinStore::CreateNameArray
       
   306 // -----------------------------------------------------------------------------
       
   307 //
       
   308 RPointerArray<CPslnSkinNameEntry>* CPslnSkinStore::CreateNameArrayL()
       
   309     {
       
   310     PSLN_TRACE_DEBUG("CPslnSkinStore::CreateNameArray");
       
   311     RPointerArray<CPslnSkinNameEntry>* array =
       
   312         new RPointerArray<CPslnSkinNameEntry>();
       
   313 
       
   314     CleanupStack::PushL( TCleanupItem( CleanupDeleteArray, array ) );
       
   315 
       
   316     for( TInt i = 0; i < iSkinArray.Count(); i++ )
       
   317         {
       
   318         AppendEntryL( *array, i );
       
   319         }
       
   320     CleanupStack::Pop(); // TCleanupItem
       
   321 
       
   322     return array;
       
   323     }
       
   324 
       
   325 // -----------------------------------------------------------------------------
       
   326 // CPslnSkinStore::UpdateAllSkinsL
       
   327 // -----------------------------------------------------------------------------
       
   328 //    
       
   329 void CPslnSkinStore::UpdateAllSkinsL(
       
   330     TAknSkinSrvSkinPackageLocation aLocation, RFs& aFsSession )
       
   331     {
       
   332     PSLN_TRACE_DEBUG("CPslnSkinStore::UpdateAllSkinsL");
       
   333     CArrayPtr<CAknsSrvSkinInformationPkg>* srvArray =
       
   334         iModel->SkinSrvSession().EnumerateSkinPackagesL( aLocation );
       
   335 
       
   336     while( srvArray && srvArray->Count() )
       
   337         {
       
   338         CAknsSrvSkinInformationPkg* info = srvArray->At( 0 );
       
   339         TRAP_IGNORE( UpdateOrAddL( info, aFsSession )->SetDeleteFlag( EFalse ) );
       
   340         srvArray->Delete( 0 );
       
   341         }
       
   342 
       
   343     if ( srvArray )
       
   344         {
       
   345         srvArray->ResetAndDestroy();
       
   346         }
       
   347     delete srvArray;
       
   348     }
       
   349 
       
   350 // -----------------------------------------------------------------------------
       
   351 // Appends entry to array.
       
   352 // -----------------------------------------------------------------------------
       
   353 // 
       
   354 void CPslnSkinStore::AppendEntryL(
       
   355     RPointerArray<CPslnSkinNameEntry>& aArray, const TInt aIndex )
       
   356     {
       
   357     PSLN_TRACE_DEBUG("CPslnSkinStore::AppendEntryL");
       
   358     // Get entry.
       
   359     CPslnSkinEntry* entry = iSkinArray[aIndex];
       
   360 
       
   361     // Get name entry.
       
   362     CPslnSkinNameEntry* nameEntry = NULL;
       
   363     nameEntry = CPslnSkinNameEntry::NewL();
       
   364     nameEntry->SetPkgID( entry->PkgID() );
       
   365     nameEntry->SetLocation( entry->Location() );
       
   366     PSLN_TRACE_DEBUG("CPslnSkinStore::AppendEntryL.2");
       
   367 
       
   368     // Get name for the entry.
       
   369     HBufC* skinName = HBufC::NewLC( KMaxName );
       
   370     TPtr skinNamePtr = skinName->Des();
       
   371     entry->GetName( skinNamePtr );
       
   372     nameEntry->SetNameL( skinNamePtr );
       
   373     CleanupStack::PopAndDestroy( skinName );
       
   374 
       
   375     if( aArray.Append( nameEntry ) )
       
   376         {
       
   377         User::Leave( KErrGeneral );
       
   378         }
       
   379     }
       
   380 
       
   381 //  End of File