uiacceltk/hitchcock/ServerCore/Src/alfappserver.cpp
changeset 0 15bf7259bb7c
child 8 10534483575f
equal deleted inserted replaced
-1:000000000000 0:15bf7259bb7c
       
     1 /*
       
     2 * Copyright (c) 2006 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:   Application Sever
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 
       
    20 #include <coemain.h>
       
    21 #include <coedef.h>
       
    22 #include <apgwgnam.h>
       
    23 #include <eiksvdef.h>
       
    24 #include <ecom.h>
       
    25 #include <uiacceltk/HuiUtil.h>
       
    26 #include <f32file.h>
       
    27 #include <TfxSrvEcomIds.h>
       
    28 #include <mtransitionserver.h>
       
    29 #include "alf/alfappserver.h"
       
    30 #include "alf/alfappui.h"
       
    31 #include "alf/alfconstants.h"
       
    32 #include "alfappsrvsession.h"
       
    33 #include "alflogger.h"
       
    34 #include "alfsrvsubsessionbase.h"
       
    35 #include "alf/alfextensionfactory.h"
       
    36 #include "alfstaticfactory.h"
       
    37 #include "alfsrvtranseffect.h"
       
    38 #include "alf/AlfTransEffectPlugin.h"
       
    39 #include <uiacceltk/HuiDisplay.h> //@todo::
       
    40 #include "alfclientserver.h"
       
    41 #include "alfsrvtexturemanager.h"
       
    42 #include "alfsrvscreenbuffermanager.h"
       
    43 
       
    44 // ----------------------------
       
    45 
       
    46 /**
       
    47  * Common command batch buffer size. This must always be larger than command 
       
    48  * header size. In practice, this should be always larger than 128.
       
    49  */
       
    50 const TInt KAlfCommonCommandBatchBufferSize = 
       
    51     KAlfClientServerDefaultCommandBatchBufferSize;
       
    52 
       
    53 // a kind of cleanup item for ecom info array
       
    54 NONSHARABLE_CLASS(CCleanupEcomArray):public CBase
       
    55     {
       
    56     public:
       
    57     ~CCleanupEcomArray()
       
    58         {
       
    59         iArray.ResetAndDestroy();
       
    60         iArray.Close();
       
    61         }
       
    62     RImplInfoPtrArray iArray;
       
    63     };
       
    64 
       
    65 
       
    66 // ECom notify helper.
       
    67 NONSHARABLE_CLASS(CAlfEcomUtil): public CActive
       
    68     {
       
    69     public:    
       
    70     
       
    71     CAlfEcomUtil(CAlfAppServer& aServer)
       
    72     :CActive(EActivePriorityDefault), iOwner(aServer)
       
    73 	    {
       
    74 	    CActiveScheduler::Add(this);
       
    75 	    }
       
    76 
       
    77     void ConstructL()
       
    78 	    {
       
    79 	    iEComSession = &REComSession::OpenL();
       
    80     	}
       
    81 
       
    82     ~CAlfEcomUtil()
       
    83 	    {
       
    84 	    Cancel();
       
    85 	    if (iEComSession)
       
    86 	        {
       
    87 	        iEComSession->Close();
       
    88 	        }
       
    89 	    iEComSession = NULL;
       
    90 	    }
       
    91 
       
    92     static CAlfEcomUtil* NewL(CAlfAppServer& aServer)
       
    93 	    {
       
    94 	    CAlfEcomUtil* self = new (ELeave) CAlfEcomUtil(aServer);
       
    95 	    CleanupStack::PushL(self);
       
    96 	    self->ConstructL();
       
    97 	    CleanupStack::Pop(self);
       
    98 	    return self;
       
    99 	    }
       
   100 
       
   101     void Start()
       
   102 	    {
       
   103 	    if (!IsActive())
       
   104 	        {
       
   105     	    iEComSession->NotifyOnChange(iStatus);
       
   106 	        SetActive();
       
   107 	        }
       
   108 	    }
       
   109 
       
   110     void RunL()
       
   111 	    {
       
   112 	    // if there was an error, just breathe a moment, i.e. don't activate new request immediately
       
   113         if (iStatus.Int() == KErrNone )
       
   114             {
       
   115     	    //Check wether plugin was installed or removed
       
   116      	    TRAP_IGNORE(iOwner.CheckForEcomPluginInstallUninstallL())
       
   117     	    Start();
       
   118             }
       
   119         __ALFLOGSTRING1( "CAlfEcomUtil::RunL: status %d", iStatus.Int() )
       
   120 	    }
       
   121 
       
   122     void DoCancel()
       
   123 	    {
       
   124 	    iEComSession->CancelNotifyOnChange(iStatus);
       
   125 	    }
       
   126 	
       
   127 	private:    
       
   128         CAlfAppServer& iOwner;
       
   129         REComSession* iEComSession;
       
   130     };
       
   131     
       
   132 
       
   133 // ======== MEMBER FUNCTIONS ========
       
   134 
       
   135 
       
   136 EXPORT_C CAlfAppServer* CAlfAppServer::NewAppServerL()
       
   137     {
       
   138     return new (ELeave) CAlfAppServer();
       
   139     }
       
   140 
       
   141 
       
   142 // ---------------------------------------------------------------------------
       
   143 // Constructor
       
   144 // ---------------------------------------------------------------------------
       
   145 //
       
   146 CAlfAppServer::CAlfAppServer():
       
   147       iLastActiveClientWg(KErrNotFound)
       
   148     {
       
   149     CCoeEnv* coe = CCoeEnv::Static();
       
   150     if (coe)
       
   151         {
       
   152         iWs = &coe->WsSession();
       
   153         }
       
   154     }
       
   155 
       
   156 // ---------------------------------------------------------------------------
       
   157 // Second phase constructor
       
   158 // ---------------------------------------------------------------------------
       
   159 //
       
   160 void CAlfAppServer::ConstructL( const TDesC& aFixedServerName )
       
   161     {
       
   162     CAknAppServer::ConstructL( aFixedServerName );
       
   163 
       
   164     iCommonCommandBatchBuffer = HBufC8::NewL( KAlfCommonCommandBatchBufferSize );
       
   165     iTextureManager = CAlfSrvTextureManager::NewL();
       
   166     iScreenBufferManager = CAlfSrvScreenBufferManager::NewL(*this);
       
   167     }
       
   168 
       
   169 // ---------------------------------------------------------------------------
       
   170 // Destructor
       
   171 // ---------------------------------------------------------------------------
       
   172 //
       
   173 CAlfAppServer::~CAlfAppServer()
       
   174     {
       
   175 	#ifdef TFXSERVER_API_V2
       
   176     if (iTfxServer)
       
   177     	{
       
   178         iTfxServer->Disconnect();
       
   179     	delete iTfxServer;
       
   180     	iTfxServer = NULL;
       
   181     	REComSession::DestroyedImplementation( iTfxServerEComDestructorUID );
       
   182     	iTfxServerEComDestructorUID.iUid = 0;	
       
   183     	}
       
   184 	#endif
       
   185 
       
   186     delete iBackgroundTimer;
       
   187     delete iTransitionEffects;
       
   188     
       
   189     delete iEcomWatcher;
       
   190     
       
   191     iWindowChangeObservers.Close();
       
   192     
       
   193     if (iAsynchOneShot)
       
   194         {
       
   195         iAsynchOneShot->Cancel();
       
   196         }
       
   197     
       
   198     delete iAsynchOneShot;
       
   199     iRemovedArray.Close();
       
   200     
       
   201     delete iObjectConIx;
       
   202 
       
   203     for (TInt ii = iCustomSessions.Count()-1; ii >= 0; ii--)
       
   204         {
       
   205         delete iCustomSessions[ii].iImpl;
       
   206         REComSession::DestroyedImplementation(
       
   207                 iCustomSessions[ii].iDestructorUid);
       
   208         }
       
   209         
       
   210     iCustomSessions.Close();
       
   211     
       
   212     // Todo: check remaining implementations
       
   213     for (TInt ii = iFactories.Count()-1; ii >= 0; ii--)
       
   214         {
       
   215         iFactories[ii].iImpl->Release();
       
   216         if (iFactories[ii].iDestructorUid.iUid)
       
   217             {
       
   218             REComSession::DestroyedImplementation(
       
   219                 iFactories[ii].iDestructorUid);
       
   220             }
       
   221         }
       
   222 
       
   223     iFactories.Close();
       
   224         
       
   225     iMetricsInterface = NULL;
       
   226     iAppUi= NULL;
       
   227 
       
   228     delete iCommonCommandBatchBuffer;
       
   229 	delete iScreenBufferManager;
       
   230     delete iTextureManager;
       
   231     }
       
   232 
       
   233 // ---------------------------------------------------------------------------
       
   234 // Called when client application exist.
       
   235 // All allocated resources for that application should be freed.
       
   236 // ---------------------------------------------------------------------------
       
   237 //
       
   238 EXPORT_C void CAlfAppServer::HandleClientExit(TInt aClientId)
       
   239     {
       
   240 	if (MetricsInterface())
       
   241 	    {
       
   242 		MetricsInterface()->SessionTerminated(aClientId);
       
   243 		}
       
   244   
       
   245     SyncEcomImplementations(aClientId);  
       
   246     
       
   247     CAlfAppSrvSessionBase* session = reinterpret_cast<CAlfAppSrvSessionBase*>(aClientId);
       
   248     
       
   249     ScreenBufferManager().RemoveScreenBufferObservers(session);
       
   250     
       
   251     if (session == iOldSession)
       
   252         {
       
   253         iOldSession = 0;
       
   254         }
       
   255     
       
   256     if (iAppUi)
       
   257         {
       
   258         iAppUi->FreeResourcesForClient(aClientId);
       
   259         }
       
   260     else 
       
   261         {
       
   262         return;
       
   263         }
       
   264         
       
   265     for (TInt i = iWindowChangeObservers.Count()-1; i >= 0 ; i--)
       
   266         {
       
   267         if (iWindowChangeObservers[i].iId == aClientId)
       
   268             {
       
   269             iWindowChangeObservers.Remove(i);
       
   270             }
       
   271         }
       
   272         
       
   273     // todo, is it true that we have no other way to check the count than using iterator?
       
   274     TInt count = 0;
       
   275     iSessionIter.SetToFirst();
       
   276     for(;iSessionIter;iSessionIter++)
       
   277         {
       
   278         count++;
       
   279         }
       
   280     
       
   281     // if this was the last client, it is ok to bail out here    
       
   282     if (count == 1)
       
   283         {
       
   284         AppUi()->UpdateActiveSession( 0 );
       
   285         AdjustWindowGroupPositionL(*CHuiStatic::RootWin(0),0,EAbsoluteBackground);
       
   286         return;
       
   287         }
       
   288 
       
   289     // Set wg position based in the topmost client app
       
   290     TInt parentWg = KErrNotFound;    
       
   291     CAlfAppSrvSessionBase* dying = reinterpret_cast<CAlfAppSrvSessionBase*>(aClientId);
       
   292 
       
   293     if ( dying->ClientWindowGroup() == KErrNotFound )
       
   294         {
       
   295         // debugging trash
       
   296         // just bail out w/o changing the order of window groups
       
   297         return;       
       
   298         }
       
   299     
       
   300     if ( dying->ClientWindowGroup() == iLastActiveClientWg )
       
   301         {
       
   302         iLastActiveClientWg = KErrNotFound;
       
   303         parentWg = dying->ParentWindowGroupId();
       
   304         }
       
   305 
       
   306     CAlfAppSrvSessionBase* newFocusSession = 0;
       
   307 
       
   308     // if parent of embedded app found, check if it ALF app and set it to focus
       
   309     if (parentWg != KErrNotFound)
       
   310         {
       
   311         iSessionIter.SetToFirst();
       
   312         while (iSessionIter)
       
   313             {
       
   314             CAlfAppSrvSessionBase* session = reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
   315             if ( session && session->ClientWindowGroup() == parentWg)
       
   316                 {
       
   317                 newFocusSession = session;
       
   318                 break;
       
   319                 }
       
   320             }
       
   321         }
       
   322         
       
   323     if (CCoeEnv::Static() && !newFocusSession) // else find topmost app and move us behind that
       
   324         {
       
   325         parentWg = KErrNotFound; // just in case app had parent but that was not ALF app
       
   326         CArrayFixFlat<TInt>* wgs = new CArrayFixFlat<TInt>(4);
       
   327         if ( wgs )
       
   328             {
       
   329             iWs->WindowGroupList(wgs);
       
   330             for ( TInt ordinal = 0 ; ordinal < wgs->Count(); ordinal++ )
       
   331                 {
       
   332                 iSessionIter.SetToFirst();
       
   333                 if( newFocusSession ) // session found from previous ordinal position.
       
   334                     {
       
   335                     break;
       
   336                     }
       
   337                 while (iSessionIter)
       
   338                     {
       
   339                     CAlfAppSrvSessionBase* session = reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
   340                     if ( session && 
       
   341                          session->ClientWindowGroup() == wgs->At( ordinal ) &&
       
   342                          (TInt)session != aClientId )
       
   343                         {
       
   344                         newFocusSession = session;
       
   345                         break;
       
   346                         }
       
   347                     }
       
   348                 }
       
   349             }
       
   350         delete wgs;
       
   351         }
       
   352     
       
   353     TRAP_IGNORE(FocusedWindowGroupChangedL(newFocusSession, parentWg))
       
   354     }
       
   355 
       
   356 
       
   357 // ---------------------------------------------------------------------------
       
   358 // Static utility used in callback
       
   359 // ---------------------------------------------------------------------------
       
   360 // 
       
   361 TInt SynchEcomImplementations(TAny* aThis)
       
   362     {
       
   363     ((CAlfAppServer*)aThis)->DoSynchEcomImplementations();
       
   364     return KErrNone;
       
   365     }
       
   366 
       
   367 // ---------------------------------------------------------------------------
       
   368 // Check if the exiting client is using ecom based session
       
   369 // if so, set asynchronous callback for notifying Ecom FW about the change
       
   370 // ---------------------------------------------------------------------------
       
   371 // 
       
   372 void CAlfAppServer::SyncEcomImplementations(TInt aClientId)  
       
   373     {
       
   374     TBool isEcom(EFalse);
       
   375     for(TInt ii = iCustomSessions.Count()-1; ii >= 0 ; ii--)
       
   376         {
       
   377         if (iCustomSessions[ii] == aClientId)
       
   378             {
       
   379             isEcom = ETrue;
       
   380             iCustomSessions[ii].iImpl = 0; // session is about to terminate, null the pointer
       
   381             break;
       
   382             }
       
   383         }
       
   384     if (isEcom)
       
   385         {
       
   386         iRemovedArray.Append(aClientId);
       
   387         if (iAsynchOneShot && !iAsynchOneShot->IsActive())
       
   388             {
       
   389             iAsynchOneShot->CallBack();
       
   390             }
       
   391         
       
   392         }
       
   393     }
       
   394 
       
   395 // ---------------------------------------------------------------------------
       
   396 // Check and notify Ecom FW about removed implementations caused by client exit
       
   397 // Called asynchronously after a client usin ecom based session has exited.
       
   398 // ---------------------------------------------------------------------------
       
   399 // 
       
   400 void CAlfAppServer::DoSynchEcomImplementations()
       
   401     {
       
   402     // check if the session was ECOM based and notify FW if so
       
   403     for (TInt i = iRemovedArray.Count()-1; i >= 0; i--)
       
   404         {
       
   405         for(TInt ii = iCustomSessions.Count()-1; ii >= 0 ; ii--)
       
   406             {
       
   407             if (iCustomSessions[ii] == iRemovedArray[i])
       
   408                 {
       
   409                 REComSession::DestroyedImplementation(
       
   410                     iCustomSessions[ii].iDestructorUid);            
       
   411                 iCustomSessions.Remove(ii);
       
   412                 }
       
   413             }
       
   414         
       
   415         }
       
   416     iRemovedArray.Reset();
       
   417     User::Heap().Compress();
       
   418     }
       
   419     
       
   420 // ---------------------------------------------------------------------------
       
   421 // From class CAknAppServer.
       
   422 // Called when all clients have existed.
       
   423 // ---------------------------------------------------------------------------
       
   424 // 
       
   425 void CAlfAppServer::HandleAllClientsClosed()
       
   426     {
       
   427     if (iAppUi)
       
   428         iAppUi->AllClientsClosed();
       
   429     }
       
   430         
       
   431 // ---------------------------------------------------------------------------
       
   432 // From class CAknAppServer.
       
   433 // Allocates the session instance
       
   434 // ---------------------------------------------------------------------------
       
   435 //
       
   436 CApaAppServiceBase* CAlfAppServer::CreateServiceL( TUid aServiceType ) const
       
   437     {
       
   438     CApaAppServiceBase* session = 0;
       
   439     if (aServiceType == KAlfServiceUid)   
       
   440 		{
       
   441 		session = CAlfAppSrvSession::NewL(this);
       
   442 		}
       
   443     else
       
   444 	    { // nasty const cast
       
   445     	session = ((CAlfAppServer*)this)->LoadServiceExtensionL(aServiceType);		    
       
   446 	    }
       
   447 	
       
   448 	if(session)	
       
   449 	    {
       
   450 		if (MetricsInterface())
       
   451 		    {
       
   452 		    const_cast<MAlfMetricsInterface*>(MetricsInterface())->SessionCreated(reinterpret_cast<TInt>(session));
       
   453 		    }
       
   454 		    
       
   455 	    return session;
       
   456 	    }
       
   457 	else
       
   458 		{
       
   459 		return CAknAppServer::CreateServiceL(aServiceType);	
       
   460 		}
       
   461     }
       
   462     
       
   463 // ---------------------------------------------------------------------------
       
   464 // Adjusts server's wg according to client's wg.
       
   465 // ---------------------------------------------------------------------------
       
   466 // 
       
   467 EXPORT_C void CAlfAppServer::AdjustWindowGroupPositionL(
       
   468     RWindowGroup& aWindowGroup, 
       
   469     TInt aParentIdentifier, 
       
   470     TAlfWGPostion aPosition)
       
   471     {
       
   472     if (!iAppUi )
       
   473         {
       
   474         return;  
       
   475         }
       
   476 
       
   477     // Update the member variable based on the WG the server follows.
       
   478     if (aPosition != EAbsoluteBackground)
       
   479         {
       
   480         iLastActiveClientWg = aParentIdentifier;
       
   481         }
       
   482         
       
   483     if (!CCoeEnv::Static())
       
   484         {
       
   485         iAppUi->AdjustWindowGroupPositionL(
       
   486                     aParentIdentifier, 
       
   487                     aPosition);
       
   488         return;
       
   489         }
       
   490         
       
   491 #ifdef _ALF_LOGGING
       
   492     LogWindowGroupsL();
       
   493     switch( aPosition )
       
   494         {
       
   495         case EBehindOfParent:
       
   496             __ALFLOGSTRING1( "CAlfAppServer::AdjWinGrpPosL EBehindOfParent parent id %d", aParentIdentifier )
       
   497             break;
       
   498         case EOnTopOfParent:
       
   499             __ALFLOGSTRING1( "CAlfAppServer::AdjWinGrpPosL EOnTopOfParent parent id %d", aParentIdentifier )
       
   500             break;
       
   501         case EAbsoluteBackground:
       
   502             __ALFLOGSTRING1( "CAlfAppServer::AdjWinGrpPosL EAbsoluteBackground parent id %d", aParentIdentifier )
       
   503             break;
       
   504         default:
       
   505             __ALFLOGSTRING2( "CAlfAppServer::AdjWinGrpPosL UNKNOWN parent id %d pos %d", aParentIdentifier, aPosition )
       
   506             break;
       
   507         }
       
   508 #endif
       
   509     
       
   510     if (aPosition == EAbsoluteBackground) // just for convenience
       
   511         {
       
   512         aWindowGroup.SetOrdinalPosition(0,ECoeWinPriorityNeverAtFront);
       
   513         LogWindowGroupsL();
       
   514         return;
       
   515         }
       
   516             
       
   517     TInt parentPriority = iWs->GetWindowGroupOrdinalPriority(aParentIdentifier);
       
   518 
       
   519     // perhaps we should maintain wg-list elsewhere
       
   520     CArrayFixFlat<TInt>* wgs = new (ELeave) CArrayFixFlat<TInt>(1); 
       
   521     CleanupStack::PushL(wgs);
       
   522     iWs->WindowGroupList(parentPriority,wgs);
       
   523     
       
   524     TInt pos = KErrNotFound;
       
   525     TInt movingWgOldPos = KErrNotFound;
       
   526     TInt wgCount = wgs->Count();
       
   527     for (TInt i = 0; i < wgCount; i++)
       
   528         {
       
   529         if (aParentIdentifier == wgs->At(i))
       
   530             {
       
   531             if ( aPosition == EOnTopOfParent )
       
   532                 {
       
   533                 pos = i;
       
   534                 }
       
   535             else
       
   536                 {
       
   537                 pos = i+1;
       
   538                 }
       
   539             }
       
   540         if ( aWindowGroup.WindowGroupId() == wgs->At(i))
       
   541             {
       
   542             movingWgOldPos = i;
       
   543             }
       
   544            
       
   545         if ( pos != KErrNotFound && movingWgOldPos != KErrNotFound )
       
   546             {
       
   547             // Both found already.
       
   548             break;
       
   549             }
       
   550         }
       
   551     
       
   552     // If the moving window group has already been before the parent
       
   553     // we need to adjust the new position
       
   554     if ( movingWgOldPos < pos && movingWgOldPos != KErrNotFound )
       
   555         {
       
   556         pos--;
       
   557         }
       
   558 
       
   559 
       
   560     User::LeaveIfError(pos); // parenty not found, leave
       
   561     
       
   562     // if iBackDropWgIdentifier has been set, status pane is partly drawn to 
       
   563     // back drop window group
       
   564     if (aPosition == EBehindOfParent && 
       
   565         iBackDropWgIdentifier 
       
   566         && parentPriority == ECoeWinPriorityNormal ) // only apps with normal priority should use status pane
       
   567         {
       
   568         for (TInt ii = pos; ii < wgCount; ii++)
       
   569             {
       
   570             if (wgs->At(ii) == iBackDropWgIdentifier)
       
   571                 {
       
   572                 pos = ii+1; // right behind status pane
       
   573                 break;
       
   574                 }
       
   575             }    
       
   576         
       
   577         }
       
   578     CleanupStack::PopAndDestroy(wgs);
       
   579     
       
   580     aWindowGroup.SetOrdinalPosition(pos, parentPriority);
       
   581     
       
   582     LogWindowGroupsL();
       
   583     }
       
   584    
       
   585 // ---------------------------------------------------------------------------
       
   586 // Returns server's window server session.
       
   587 // ---------------------------------------------------------------------------
       
   588 // 
       
   589 EXPORT_C RWsSession& CAlfAppServer::WsSession() const
       
   590     {
       
   591     return *iWs;
       
   592     }
       
   593 
       
   594 // ---------------------------------------------------------------------------
       
   595 // Returns the metrics interface.
       
   596 // ---------------------------------------------------------------------------
       
   597 // 
       
   598 EXPORT_C MAlfMetricsInterface* CAlfAppServer::MetricsInterface()
       
   599     {
       
   600     return iMetricsInterface;
       
   601     }
       
   602     
       
   603 // ---------------------------------------------------------------------------
       
   604 // Returns the metrics interface.
       
   605 // ---------------------------------------------------------------------------
       
   606 // 
       
   607 EXPORT_C const MAlfMetricsInterface* CAlfAppServer::MetricsInterface() const
       
   608     {
       
   609     return iMetricsInterface;
       
   610     }
       
   611 
       
   612 // ---------------------------------------------------------------------------
       
   613 // Sets the metrics interface.
       
   614 // ---------------------------------------------------------------------------
       
   615 // 
       
   616 EXPORT_C void CAlfAppServer::SetMetricsInterface(
       
   617     MAlfMetricsInterface* aMetricsInterface)
       
   618     {
       
   619     iMetricsInterface = aMetricsInterface;
       
   620     }
       
   621 
       
   622 // ---------------------------------------------------------------------------
       
   623 // Sets the AppUi.
       
   624 // ---------------------------------------------------------------------------
       
   625 // 
       
   626 void CAlfAppServer::SetAppUi(CAlfAppUi* aAppUi)
       
   627     {
       
   628     iAppUi = aAppUi;
       
   629     iWs = &CHuiStatic::WsSession();
       
   630     }
       
   631     
       
   632 // ---------------------------------------------------------------------------
       
   633 // Returns the AppUi pointer.
       
   634 // ---------------------------------------------------------------------------
       
   635 // 
       
   636 EXPORT_C CAlfAppUi* CAlfAppServer::AppUi()
       
   637     {
       
   638     __ASSERT_DEBUG(iAppUi, USER_INVARIANT());
       
   639     return iAppUi;
       
   640     }
       
   641    
       
   642 // ---------------------------------------------------------------------------
       
   643 // Called when the focused window group changes.
       
   644 // ---------------------------------------------------------------------------
       
   645 //     
       
   646 void CAlfAppServer::FocusedWindowGroupChangedL( CAlfAppSrvSessionBase* aSession, TInt aWgId)
       
   647     {
       
   648     iOldSession = NULL;
       
   649     CancelBackgroundTimer();
       
   650 
       
   651     // Find new and old focused clients
       
   652     CAlfAppSrvSessionBase* newFocusedSession = aSession;
       
   653     CAlfAppSrvSessionBase* oldFocusedSession = NULL;
       
   654     
       
   655     iSessionIter.SetToFirst();
       
   656     while (iSessionIter)
       
   657         {
       
   658         CAlfAppSrvSessionBase* session =
       
   659             reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
   660 
       
   661         if (  session && 
       
   662               !oldFocusedSession && 
       
   663               iLastActiveClientWg != KErrNotFound &&
       
   664               session->ClientWindowGroup() == iLastActiveClientWg )
       
   665             {
       
   666             oldFocusedSession = session;
       
   667             }
       
   668             
       
   669         // If found, stop the search. 
       
   670         if ( oldFocusedSession || iLastActiveClientWg == KErrNotFound )
       
   671             {
       
   672             break;
       
   673             }
       
   674         // Otherwise, keep going...
       
   675         }
       
   676         
       
   677     if ( !newFocusedSession )
       
   678         {
       
   679         // Another application got the focus
       
   680         // let the server follow the previous app wg
       
   681         if ( oldFocusedSession )
       
   682             {
       
   683             oldFocusedSession->ResetRootlayerTransformationsL();
       
   684             oldFocusedSession->FocusLostL( EFalse );
       
   685             AdjustWindowGroupPositionL(
       
   686                         *CHuiStatic::RootWin(),
       
   687                         oldFocusedSession->ClientWindowGroup(), 
       
   688                         oldFocusedSession->PreferredWindowGroupPosition());        
       
   689             }
       
   690         else // this will be the case when there is only direct client connections left
       
   691             {
       
   692             AdjustWindowGroupPositionL(*CHuiStatic::RootWin(0),0,EAbsoluteBackground);
       
   693             }
       
   694         AppUi()->UpdateActiveSession( 0 );
       
   695         AppUi()->SetContainerNonFading( EFalse );
       
   696         }
       
   697     else
       
   698         {
       
   699         // One of our clients got the focus
       
   700         AdjustWindowGroupPositionL( 
       
   701                 *CHuiStatic::RootWin(), 
       
   702                 newFocusedSession->ClientWindowGroup(), 
       
   703                 newFocusedSession->PreferredWindowGroupPosition() );
       
   704 #ifdef SYMBIAN_BUILD_GCE    
       
   705         newFocusedSession->ActivateContainerLayoutL(ETrue);
       
   706 #endif // #ifdef SYMBIAN_BUILD_GCE    
       
   707 
       
   708         TBool didFadeOutTransition = EFalse; // default, just make sure that visual trees are restored
       
   709         if ( oldFocusedSession && newFocusedSession != oldFocusedSession) // switching between apps
       
   710             {
       
   711             if ((oldFocusedSession->ClientWindowGroup() == newFocusedSession->ParentWindowGroupId())
       
   712                 || (newFocusedSession->ClientWindowGroup() == oldFocusedSession->ParentWindowGroupId() ))
       
   713                 { // swithching into embedded app
       
   714                 didFadeOutTransition = oldFocusedSession->FocusLostL( MAlfTransEffectPlugin::EContextEmbeddedExit );
       
   715                 if (didFadeOutTransition)
       
   716                     {
       
   717                     didFadeOutTransition = MAlfTransEffectPlugin::EContextEmbeddedStart;
       
   718                     }
       
   719                 }
       
   720             else // swithching between separate apps
       
   721                 {
       
   722                 didFadeOutTransition = oldFocusedSession->FocusLostL( MAlfTransEffectPlugin::EContextFocusLost );
       
   723                 }    
       
   724             }
       
   725         else if (!oldFocusedSession ) // New app is being launched
       
   726             {                         // or previous app destroyed  
       
   727             if (aWgId == KErrNotFound)
       
   728                 {
       
   729                 didFadeOutTransition = MAlfTransEffectPlugin::EContextFocusGained; // enable default effect
       
   730                 }
       
   731             else
       
   732                 {
       
   733                 didFadeOutTransition = MAlfTransEffectPlugin::EContextEmbeddedStart; // enable default effect
       
   734                 }
       
   735             }
       
   736         else
       
   737             {
       
   738             // Fot PC-lint
       
   739             }
       
   740         newFocusedSession->FocusGainedL( didFadeOutTransition );
       
   741         }
       
   742 #ifdef SYMBIAN_BUILD_GCE
       
   743 /*
       
   744 #ifdef HUI_FX
       
   745 */
       
   746     // Should test if transition is running
       
   747     // If transitions are disabled, no delay is needed
       
   748     if ( oldFocusedSession && oldFocusedSession != newFocusedSession )
       
   749         {
       
   750         if ( !newFocusedSession )
       
   751             {
       
   752             iOldSession = oldFocusedSession;
       
   753             StartBackgroundTimerL(iLastActiveClientWg);
       
   754             }
       
   755         else
       
   756             {
       
   757             oldFocusedSession->ActivateContainerLayoutL(EFalse);
       
   758             }
       
   759         }
       
   760 /*        
       
   761 #else  
       
   762     if (oldFocusedSession && oldFocusedSession != newFocusedSession )
       
   763         oldFocusedSession->ActivateContainerLayoutL(EFalse);
       
   764 #endif    
       
   765 */
       
   766 #endif // #ifdef SYMBIAN_BUILD_GCE    
       
   767     }
       
   768 
       
   769 
       
   770 // ---------------------------------------------------------------------------
       
   771 // Notify window visibility observers about change
       
   772 // ---------------------------------------------------------------------------
       
   773 // 
       
   774 void CAlfAppServer::WindowVisiblityChangedL( 
       
   775     TUint aVisibilityFlags, 
       
   776     CCoeControl* aDestination )
       
   777     {
       
   778     for (TInt i = 0; i < iWindowChangeObservers.Count(); i++)
       
   779         {
       
   780         if (iWindowChangeObservers[i].iPtr->CoeControl() == aDestination)
       
   781             {
       
   782             if ( aVisibilityFlags & 
       
   783                  TWsVisibilityChangedEvent::EPartiallyVisible )
       
   784                 {
       
   785                 iWindowChangeObservers[i].iPtr->WindowPartiallyVisible();
       
   786                 }
       
   787             else if ( aVisibilityFlags & 
       
   788                       TWsVisibilityChangedEvent::EFullyVisible )
       
   789                 {
       
   790                 iWindowChangeObservers[i].iPtr->WindowFullyVisible();
       
   791                 }
       
   792             else if ( aVisibilityFlags & 
       
   793                       TWsVisibilityChangedEvent::ENotVisible )
       
   794                 {
       
   795                 iWindowChangeObservers[i].iPtr->WindowNotVisible();
       
   796                 }
       
   797             else
       
   798                 {
       
   799                 // For PC-lint
       
   800                 }
       
   801             
       
   802             break;
       
   803             }
       
   804         }
       
   805     }
       
   806     
       
   807 // ---------------------------------------------------------------------------
       
   808 // Loads a session extension.
       
   809 // ---------------------------------------------------------------------------
       
   810 // 
       
   811 CAlfAppSrvSessionBase* CAlfAppServer::LoadServiceExtensionL(TUid aServiceType)
       
   812     {
       
   813     CAlfAppSrvSessionBase* newSession = 0;
       
   814     // check if lib already loaded
       
   815     if (ImplementationExists(aServiceType)) // no need to scan
       
   816         {
       
   817         newSession = NewImplementationL(aServiceType);       
       
   818         }
       
   819     else
       
   820         {
       
   821         // perform plugin scan
       
   822         CCleanupEcomArray* ecomInfoArray = new (ELeave) CCleanupEcomArray;
       
   823         CleanupStack::PushL(ecomInfoArray);
       
   824         REComSession::ListImplementationsL(TUid::Uid(K_ALF_SERVICE_INTERFACE), ecomInfoArray->iArray);
       
   825         // check if plugin with implementation uid matches 
       
   826         TInt count = ecomInfoArray->iArray.Count();
       
   827         for (TInt ii = count-1; ii >= 0; ii-- )
       
   828             {
       
   829             if ((ecomInfoArray->iArray[ii])->ImplementationUid() 
       
   830                     == aServiceType)
       
   831                 {
       
   832                 newSession = NewImplementationL(aServiceType);       
       
   833                 break;
       
   834                 }
       
   835             }
       
   836         CleanupStack::PopAndDestroy();    
       
   837         }
       
   838 
       
   839     if (newSession && !iAsynchOneShot)
       
   840         { // instantiate remove callback here if it does not exist yet
       
   841         iAsynchOneShot = 
       
   842             new (ELeave) CAsyncCallBack(
       
   843                 TCallBack(SynchEcomImplementations, this), 
       
   844                 EActivePriorityDefault);
       
   845         }
       
   846 
       
   847     
       
   848     return newSession;
       
   849     }
       
   850 
       
   851 // ---------------------------------------------------------------------------
       
   852 // Checks if implementation of this type has been loaded already, 
       
   853 // no need to perform scan if this is the case 
       
   854 // ---------------------------------------------------------------------------
       
   855 // 
       
   856 TBool CAlfAppServer::ImplementationExists(TUid aServiceType) const
       
   857     {
       
   858     for(TInt ii = iCustomSessions.Count()-1; ii >= 0; ii--)
       
   859         {
       
   860         if (aServiceType==iCustomSessions[ii].iServiceUid)
       
   861             {
       
   862             return ETrue;
       
   863             }
       
   864         }
       
   865 
       
   866     return EFalse;
       
   867     }
       
   868 
       
   869 // ---------------------------------------------------------------------------
       
   870 // Loads and instantiates actual implementation using ECOM 
       
   871 // ---------------------------------------------------------------------------
       
   872 // 
       
   873 CAlfAppSrvSessionBase* CAlfAppServer::NewImplementationL(TUid aServiceType)
       
   874     {
       
   875     TServiceExtension ext;
       
   876     ext.iServiceUid = aServiceType;
       
   877     ext.iImpl = 
       
   878         (CAlfAppSrvSessionBase*)REComSession::CreateImplementationL(
       
   879             aServiceType, 
       
   880             ext.iDestructorUid, 
       
   881             this);
       
   882     iCustomSessions.AppendL(ext);
       
   883 
       
   884     // set notify for changes in plugins (if it does not exist already) 
       
   885     if (!iEcomWatcher)
       
   886         {
       
   887         iEcomWatcher = CAlfEcomUtil::NewL(*this);
       
   888         iEcomWatcher->Start();
       
   889         }
       
   890   
       
   891     return ext.iImpl;
       
   892     }
       
   893 
       
   894 // ---------------------------------------------------------------------------
       
   895 // Something has changed in ECom, check if we are affected
       
   896 // ---------------------------------------------------------------------------
       
   897 // 
       
   898 void CAlfAppServer::CheckForEcomPluginInstallUninstallL()
       
   899     {
       
   900     // cross-check services loaded
       
   901     TInt csCount = iCustomSessions.Count();
       
   902     if (csCount)
       
   903         {
       
   904         CCleanupEcomArray* ecomInfoArray = new (ELeave) CCleanupEcomArray;
       
   905         CleanupStack::PushL(ecomInfoArray);
       
   906         REComSession::ListImplementationsL(TUid::Uid(K_ALF_SERVICE_INTERFACE), 
       
   907                                             ecomInfoArray->iArray);
       
   908         // check if plugin with implementation uid matches 
       
   909         TInt count = ecomInfoArray->iArray.Count();
       
   910         while (csCount > 0)
       
   911             {
       
   912             csCount--;
       
   913             TUid csUid = iCustomSessions[csCount].iServiceUid;
       
   914             TBool found(EFalse);
       
   915             for (TInt ii = count-1; ii >= 0; ii-- )
       
   916                 {
       
   917                 if ((ecomInfoArray->iArray[ii])->ImplementationUid() 
       
   918                     == csUid)
       
   919                     {
       
   920                     found = ETrue;       
       
   921                     break;
       
   922                     }
       
   923                 }
       
   924             if (!found)
       
   925                 { // notifies ECom about destroyed implementation
       
   926                 delete iCustomSessions[csCount].iImpl;
       
   927                 }
       
   928             }
       
   929             
       
   930         CleanupStack::PopAndDestroy();            
       
   931         }
       
   932 
       
   933     TInt factoryCount = iFactories.Count();
       
   934     if (factoryCount)
       
   935         {
       
   936         CCleanupEcomArray* ecomInfoArray = new (ELeave) CCleanupEcomArray;
       
   937         CleanupStack::PushL(ecomInfoArray);
       
   938         REComSession::ListImplementationsL(TUid::Uid( K_ALF_FACTORY_INTERFACE), 
       
   939                                             ecomInfoArray->iArray);
       
   940         // check if plugin with implementation uid matches 
       
   941         TInt count = ecomInfoArray->iArray.Count();
       
   942         while (factoryCount > 0 )
       
   943             {
       
   944             factoryCount--;
       
   945             TUid fUid = iFactories[factoryCount].iUid;
       
   946             if (fUid == KNullUid) // fixed factory
       
   947                 {
       
   948                 continue;                
       
   949                 }
       
   950                 
       
   951             TBool found(EFalse);
       
   952             for (TInt ii = count-1; ii >= 0; ii-- )
       
   953                 {
       
   954                 if ((ecomInfoArray->iArray[ii])->ImplementationUid() 
       
   955                     == fUid)
       
   956                     {
       
   957                     found = ETrue;       
       
   958                     break;
       
   959                     }
       
   960                 }
       
   961             if (!found)
       
   962                 { // notifies ECom about destroyed implementation
       
   963                 NotifySessionsAboutDestroyedImplementation(iFactories[factoryCount].iUid.iUid);
       
   964                 iFactories[factoryCount].iImpl->Release();
       
   965                 }
       
   966             }
       
   967             
       
   968         CleanupStack::PopAndDestroy();            
       
   969         }
       
   970 
       
   971     if (iCustomSessions.Count() == 0 && 
       
   972         (iFactories.Count() == 0 || (iFactories.Count() == 1 && iFactories[0].iUid == KNullUid) ) )
       
   973         { // no active extensions -> cancel notify
       
   974         delete iEcomWatcher;
       
   975         iEcomWatcher = 0;    
       
   976         }
       
   977     
       
   978     }
       
   979 
       
   980 // ---------------------------------------------------------------------------
       
   981 // Appends new window visibility observer
       
   982 // ---------------------------------------------------------------------------
       
   983 // 
       
   984 EXPORT_C void CAlfAppServer::SetWindowChangeObserverL(
       
   985     MWindowVisibilityObserver* aObserver, TInt aClientId) 
       
   986     {
       
   987     iWindowChangeObservers.AppendL(TWindowChangeObserver(aObserver,aClientId));
       
   988     }
       
   989     
       
   990 TBool IsNewStatusPaneArchL()
       
   991     {
       
   992     _LIT(KS60ProductIDFile, "Series60v*.sis");
       
   993     _LIT(KROMInstallDir, "z:\\system\\install\\");
       
   994 
       
   995     TFindFile ff( CHuiStatic::FsSession());
       
   996     CDir* result;
       
   997     User::LeaveIfError( ff.FindWildByDir( KS60ProductIDFile, KROMInstallDir, result ) );
       
   998     CleanupStack::PushL( result );
       
   999     User::LeaveIfError( result->Sort( ESortByName|EDescending ) );
       
  1000 
       
  1001     TInt major = (*result)[0].iName[9] - '0';
       
  1002     TInt minor = (*result)[0].iName[11] - '0';
       
  1003 
       
  1004     CleanupStack::PopAndDestroy(); // result
       
  1005     return ((major>3) || (major == 3 && minor >= 2));
       
  1006     }
       
  1007 
       
  1008 void ResolveBdWgIdL(TInt& aId, RWsSession& aWs, CAlfAppUi& /*aAppUi*/)
       
  1009     {
       
  1010     if (!IsNewStatusPaneArchL())
       
  1011         {
       
  1012         CArrayFixFlat<TInt>* wgs = new (ELeave) CArrayFixFlat<TInt>(1); 
       
  1013         CleanupStack::PushL(wgs);
       
  1014         aWs.WindowGroupList(ECoeWinPriorityNormal,wgs);
       
  1015         TInt wgCount = wgs->Count();
       
  1016 
       
  1017         CApaWindowGroupName* wgName = CApaWindowGroupName::NewLC(aWs); 
       
  1018         HBufC* buf = HBufC::NewL(CApaWindowGroupName::EMaxLength);
       
  1019         wgName->SetWindowGroupName(buf);
       
  1020 
       
  1021         for ( TInt spPos = 0; spPos < wgCount; spPos++)
       
  1022             {
       
  1023             TPtr des = buf->Des();
       
  1024             TInt err = aWs.GetWindowGroupNameFromIdentifier(wgs->At(spPos), des);
       
  1025             if (!err)
       
  1026                 {
       
  1027                 if ( wgName->Caption().Compare(EIKON_SERVER_BACKDROP_WINDOW_GROUP_NAME) == 0)
       
  1028                     {
       
  1029                     aId = wgs->At(spPos);
       
  1030                     break;
       
  1031                     }
       
  1032                 }
       
  1033             }
       
  1034         CleanupStack::PopAndDestroy(2); // wgName, wgs
       
  1035         }
       
  1036     }
       
  1037 
       
  1038 // ---------------------------------------------------------------------------
       
  1039 // Creates container for session in which it holds the sub sessions.
       
  1040 // ---------------------------------------------------------------------------
       
  1041 // 
       
  1042 CObjectCon* CAlfAppServer::NewContainerL()
       
  1043     {
       
  1044     if ( !iObjectConIx )
       
  1045         {
       
  1046         iObjectConIx = CObjectConIx::NewL();
       
  1047         // we don't have ConstructL, so this would be suitable place to do one-shot-only construction 
       
  1048         if(CCoeEnv::Static())
       
  1049             {
       
  1050             ResolveBdWgIdL(iBackDropWgIdentifier, *iWs, *iAppUi);
       
  1051             }
       
  1052         }
       
  1053         
       
  1054     return iObjectConIx->CreateL();
       
  1055     }
       
  1056 
       
  1057 // ======== RnD FUNCTIONS ========
       
  1058 
       
  1059 // ---------------------------------------------------------------------------
       
  1060 // Logs window groups
       
  1061 // ---------------------------------------------------------------------------
       
  1062 // 
       
  1063 void CAlfAppServer::LogWindowGroupsL() const
       
  1064     {
       
  1065 #ifdef _ALF_LOGGING
       
  1066     // uncomment block if you want to log the window group order.
       
  1067     /*
       
  1068     CArrayFixFlat<TInt>* wgs = new (ELeave) CArrayFixFlat<TInt>(4); 
       
  1069     CleanupStack::PushL(wgs);
       
  1070     iWs->WindowGroupList(wgs);
       
  1071     const TInt focusedWg = iWs->GetFocusWindowGroup();
       
  1072     
       
  1073     for ( TInt i = 0; i < wgs->Count() ; i++ )
       
  1074         {
       
  1075         TThreadId threadId;
       
  1076         iWs->GetWindowGroupClientThreadId(wgs->At(i), threadId);
       
  1077         RThread thread;
       
  1078         if ( thread.Open(threadId) == KErrNone )
       
  1079             {
       
  1080             TName name = thread.Name();
       
  1081             TPtrC ptr(name);
       
  1082             if ( wgs->At(i) == focusedWg )
       
  1083                 {
       
  1084                 __ALFLOGSTRING3( " [%d] wg:%d %S FOCUSED",i,wgs->At(i), &ptr );
       
  1085                 }
       
  1086             else
       
  1087                 {
       
  1088                 __ALFLOGSTRING3( " [%d] wg:%d %S",i,wgs->At(i), &ptr );
       
  1089                 }
       
  1090             }
       
  1091         }
       
  1092     
       
  1093     CleanupStack::PopAndDestroy( wgs );
       
  1094     */
       
  1095 #endif
       
  1096     }
       
  1097 
       
  1098 MAlfExtension* CAlfAppServer::CreateExtensionL(TInt aImplementationUid, TInt aImplementationId, const RMessage2 & aMessage )
       
  1099     {   
       
  1100     TAlfElementFactory* factory = 0;
       
  1101 
       
  1102     if (iFactories.Count() == 0)
       
  1103         {
       
  1104         TAlfElementFactory ef;
       
  1105         ef.iUid = KNullUid;
       
  1106         ef.iImpl = new (ELeave) TAlfFixedFactory;
       
  1107         ef.iDestructorUid = KNullUid;
       
  1108         iFactories.AppendL(ef);
       
  1109         }
       
  1110 
       
  1111     // Check if factory already loaded
       
  1112     for(TInt ii = iFactories.Count()-1; ii>=0;ii--)
       
  1113         {
       
  1114         if (iFactories[ii].iUid == TUid::Uid(aImplementationUid))
       
  1115             {
       
  1116             factory = &iFactories[ii];
       
  1117             break;
       
  1118             }
       
  1119         }
       
  1120 
       
  1121     if (!factory)
       
  1122         {        
       
  1123         // Todo should actually perform interface based scan and check that possible candidate (if any)
       
  1124         // implements correct interface also
       
  1125         // K_ALF_FACTORY_INTERFACE
       
  1126         
       
  1127         TAlfElementFactory ef;
       
  1128         ef.iUid = TUid::Uid(aImplementationUid);
       
  1129         ef.iImpl = (MAlfExtensionFactory*)REComSession::CreateImplementationL(
       
  1130             ef.iUid, 
       
  1131             ef.iDestructorUid);
       
  1132         User::LeaveIfNull(ef.iImpl);
       
  1133         iFactories.AppendL(ef);
       
  1134         factory = &iFactories[iFactories.Count()-1];
       
  1135 
       
  1136         if (!iEcomWatcher)
       
  1137             {
       
  1138             iEcomWatcher = CAlfEcomUtil::NewL(*this);
       
  1139             iEcomWatcher->Start();
       
  1140             }
       
  1141         }
       
  1142 
       
  1143     HBufC8* inBuf = 0;   
       
  1144     TInt paramsLenght = aMessage.GetDesLength(1);
       
  1145     if (paramsLenght > 0)
       
  1146         {
       
  1147         inBuf = HBufC8::NewLC(paramsLenght);        
       
  1148         TPtr8 ptr = inBuf->Des();
       
  1149         aMessage.ReadL(1,ptr);
       
  1150         }
       
  1151 
       
  1152     // Create implementation    
       
  1153     MAlfExtension* object = 0;
       
  1154     if (inBuf)
       
  1155         {
       
  1156         object = factory->iImpl->CreateExtensionL(aImplementationId, inBuf->Des(), *((CAlfAppSrvSessionBase*)aMessage.Session()));
       
  1157         CleanupStack::PopAndDestroy(inBuf);
       
  1158         }
       
  1159     else
       
  1160         {
       
  1161         object = factory->iImpl->CreateExtensionL(aImplementationId, KNullDesC8, *((CAlfAppSrvSessionBase*)aMessage.Session()));       
       
  1162         }    
       
  1163     
       
  1164     factory->iAccessCount++;
       
  1165 
       
  1166     if (!object) // actually factory should leave
       
  1167         {
       
  1168         User::Leave(KErrNotSupported);
       
  1169         } 
       
  1170 
       
  1171     return object;
       
  1172     }
       
  1173         
       
  1174 
       
  1175 void CAlfAppServer::DestroyedObject(TInt aFactoryUid)
       
  1176     {
       
  1177     if (!aFactoryUid)
       
  1178         {
       
  1179         return;        
       
  1180         }
       
  1181  
       
  1182     TInt ii = -1;
       
  1183     for ( ii = iFactories.Count()-1; ii >= 0; ii--)
       
  1184         {
       
  1185         if (iFactories[ii] == aFactoryUid)
       
  1186             {
       
  1187             iFactories[ii].iAccessCount--;
       
  1188             if (iFactories[ii].iAccessCount == 0)
       
  1189                 {
       
  1190                 iFactories[ii].iImpl->Release();
       
  1191                 if (iFactories[ii].iDestructorUid.iUid)
       
  1192                     {
       
  1193                     REComSession::DestroyedImplementation(
       
  1194                             iFactories[ii].iDestructorUid);
       
  1195                     }
       
  1196                 iFactories.Remove(ii);
       
  1197                 User::Heap().Compress();
       
  1198                 }
       
  1199             break;
       
  1200             }
       
  1201         }
       
  1202     }
       
  1203 
       
  1204 void CAlfAppServer::NotifySessionsAboutDestroyedImplementation(TInt aFactoryUid)
       
  1205     {
       
  1206     iSessionIter.SetToFirst();
       
  1207     while (iSessionIter)
       
  1208         {
       
  1209         CAlfAppSrvSessionBase* session =
       
  1210             reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
  1211         
       
  1212         session->FactoryDestroyed(aFactoryUid);
       
  1213         }
       
  1214     }
       
  1215 
       
  1216 
       
  1217 // ---------------------------------------------------------------------------
       
  1218 // Create a transition effect instance for the server if it does not exist
       
  1219 // ---------------------------------------------------------------------------
       
  1220 // 
       
  1221 void CAlfAppServer::CreateTransitionEffectsL()
       
  1222 	{
       
  1223 	if ( iTransitionEffects == NULL )
       
  1224 		{
       
  1225 		iTransitionEffects = CAlfSrvTransEffect::NewL();
       
  1226 		}
       
  1227 	}
       
  1228 
       
  1229 
       
  1230 // ---------------------------------------------------------------------------
       
  1231 // Return a pointer to the transition effects instance 
       
  1232 // ---------------------------------------------------------------------------
       
  1233 // 
       
  1234 CAlfSrvTransEffect* CAlfAppServer::TransitionEffects()
       
  1235 	{
       
  1236 	return( iTransitionEffects );
       
  1237 	}
       
  1238 
       
  1239 // -----------------------------------------------------------------------------
       
  1240 // Create Tfx Server client plugin and make a connection to Tfx Server
       
  1241 // -----------------------------------------------------------------------------
       
  1242 //
       
  1243 TInt CAlfAppServer::CreateTfxServerPlugin()
       
  1244     {
       
  1245     TInt err = KErrNone;
       
  1246     
       
  1247 	#ifdef TFXSERVER_API_V2
       
  1248     if (iTfxServer == NULL)
       
  1249         {
       
  1250         TUid implementationUidSrv = { KTfxSrv2EcomImpl };
       
  1251         TRAP(err, iTfxServer = (MTransitionServer2*)
       
  1252             REComSession::CreateImplementationL( implementationUidSrv, iTfxServerEComDestructorUID,
       
  1253             	NULL ));
       
  1254         }
       
  1255    	if (!err && (iTfxServer != NULL))
       
  1256 		{
       
  1257         if (!iTfxServer->IsConnected())
       
  1258     		{
       
  1259             err = iTfxServer->Connect();
       
  1260             }	
       
  1261 		}
       
  1262 	#endif
       
  1263 		
       
  1264 	return err;	
       
  1265     }
       
  1266     
       
  1267     
       
  1268 // -----------------------------------------------------------------------------
       
  1269 // Return Tfx Server client pointer if possible
       
  1270 // -----------------------------------------------------------------------------
       
  1271 //
       
  1272 MTransitionServer2* CAlfAppServer::TfxServer()
       
  1273 	{
       
  1274 	TInt err = KErrNone;
       
  1275 	#ifdef TFXSERVER_API_V2
       
  1276     if (iTfxServer && !iTfxServer->IsConnected())
       
  1277   		{
       
  1278         err = iTfxServer->Connect();
       
  1279         }	
       
  1280 	#endif
       
  1281 	return (err ? NULL : iTfxServer);
       
  1282 	}
       
  1283 	
       
  1284 
       
  1285 // ---------------------------------------------------------------------------
       
  1286 // Triggers sending a system event to clients
       
  1287 // ---------------------------------------------------------------------------
       
  1288 // 
       
  1289 void CAlfAppServer::TriggerSystemEvent(TInt aEvent)
       
  1290     {
       
  1291     iSessionIter.SetToFirst();
       
  1292     while (iSessionIter)
       
  1293         {
       
  1294         CAlfAppSrvSessionBase* session =
       
  1295             reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
  1296         
       
  1297         session->TriggerSystemEvent(aEvent);
       
  1298         }        
       
  1299     }
       
  1300  
       
  1301 TBool CrossCheckForeground(TAny* aThis)
       
  1302     {
       
  1303     CAlfAppServer* me = (CAlfAppServer*)aThis;
       
  1304     
       
  1305 //#ifdef HUI_FX
       
  1306     if ( me->iOldSession )
       
  1307         {
       
  1308         TRAP_IGNORE( me->iOldSession->ActivateContainerLayoutL(EFalse); 
       
  1309         me->iOldSession = NULL;
       
  1310         me->CancelBackgroundTimer(); );
       
  1311         return EFalse;
       
  1312         }
       
  1313 //#endif    
       
  1314     TRAP_IGNORE(me->FocusedWindowGroupChangedL(0)) // cancels the timer
       
  1315     return EFalse; 
       
  1316     }
       
  1317 
       
  1318 void CAlfAppServer::StartBackgroundTimerL(TInt aClientWg)
       
  1319     {
       
  1320     if (aClientWg != iLastActiveClientWg)
       
  1321         {
       
  1322         CancelBackgroundTimer();
       
  1323         return;
       
  1324         }
       
  1325         
       
  1326     if (!iBackgroundTimer)
       
  1327         {
       
  1328         iBackgroundTimer = CPeriodic::NewL(EPriorityNormal);
       
  1329         }
       
  1330     CancelBackgroundTimer(); // reset the time in case of active timers
       
  1331 /*    
       
  1332 #ifdef HUI_FX    
       
  1333 */
       
  1334     if ( iOldSession )
       
  1335         {
       
  1336         // longer delay to allow the application to start properly
       
  1337         iBackgroundTimer->Start(1500000,0,TCallBack(CrossCheckForeground, this));
       
  1338         }
       
  1339     else
       
  1340         {
       
  1341         iBackgroundTimer->Start(20000,0,TCallBack(CrossCheckForeground, this));
       
  1342         }
       
  1343 /*        
       
  1344 #else    
       
  1345     iBackgroundTimer->Start(20000,0,TCallBack(CrossCheckForeground, this));
       
  1346 #endif
       
  1347 */    
       
  1348     }
       
  1349     
       
  1350 void CAlfAppServer::CancelBackgroundTimer()
       
  1351     {
       
  1352     if(iBackgroundTimer)
       
  1353         {
       
  1354         iBackgroundTimer->Cancel();
       
  1355         }
       
  1356     }
       
  1357     
       
  1358 TInt CAlfAppServer::CommonCommandBatchBufferMaxLength() const
       
  1359     {
       
  1360     return iCommonCommandBatchBuffer->Des().MaxLength();
       
  1361     }
       
  1362 
       
  1363 TBool CAlfAppServer::AcquireCommonCommandBatchBuffer( TPtr8& aBuffer )
       
  1364     {
       
  1365     TBool result = EFalse;
       
  1366     
       
  1367     if ( !iCommonCommandBatchBufferInUse )
       
  1368         {
       
  1369         // In practice, iCommonCommandBatchBufferInUse might be true only
       
  1370         // if MAlfExtension::HandleCmdL starts active scheduler.
       
  1371         // (but then ServiceL should not be called again)
       
  1372 
       
  1373         result = ETrue;
       
  1374         iCommonCommandBatchBufferInUse = ETrue;
       
  1375         aBuffer.Set( iCommonCommandBatchBuffer->Des() );
       
  1376         aBuffer.Zero();
       
  1377         }
       
  1378 
       
  1379     return result;
       
  1380     }
       
  1381 
       
  1382 void CAlfAppServer::ReleaseCommonCommandBatchBuffer()
       
  1383     {
       
  1384     iCommonCommandBatchBufferInUse = EFalse;
       
  1385     }
       
  1386     
       
  1387 CAlfSrvTextureManager& CAlfAppServer::TextureManager()
       
  1388     {
       
  1389     return *iTextureManager;
       
  1390     }
       
  1391     
       
  1392 CAlfSrvScreenBufferManager& CAlfAppServer::ScreenBufferManager()
       
  1393     {
       
  1394     return *iScreenBufferManager;
       
  1395     }
       
  1396 
       
  1397 TBool CAlfAppServer::AlfClientHasFocus()
       
  1398     {
       
  1399     TBool result = EFalse;
       
  1400     TInt focusWindowGroupId = WsSession().GetFocusWindowGroup();
       
  1401 
       
  1402     iSessionIter.SetToFirst();
       
  1403     while (iSessionIter)
       
  1404       {
       
  1405       CAlfAppSrvSessionBase* session = reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
  1406       if ( session && session->ClientWindowGroup() == focusWindowGroupId )
       
  1407           {
       
  1408           result = ETrue;
       
  1409           break;
       
  1410           }
       
  1411       }
       
  1412     return result;
       
  1413     }
       
  1414 
       
  1415 CAlfAppSrvSessionBase* CAlfAppServer::UpMostClientAboveWg( TInt aWgId )
       
  1416     {
       
  1417     if (!iAppUi && !CCoeEnv::Static())
       
  1418         return 0;
       
  1419             
       
  1420     CAlfAppSrvSessionBase* sessionAboveGivenWgId = NULL;
       
  1421      
       
  1422     CArrayFixFlat<TInt>* wgs = new CArrayFixFlat<TInt>(4);
       
  1423     if ( wgs )
       
  1424         {
       
  1425         iWs->WindowGroupList( 0, wgs);
       
  1426         TInt topmostWgId = wgs->At( 0 );
       
  1427          for ( TInt ordinal = 0 ; ordinal < wgs->Count(); ordinal++ )
       
  1428             {
       
  1429             iSessionIter.SetToFirst();
       
  1430             if( sessionAboveGivenWgId || aWgId == wgs->At( ordinal ) ) 
       
  1431                {
       
  1432                 // either above client app's wg was found or there wasn't any client app's wg above given aWgId
       
  1433                 break;
       
  1434                 }
       
  1435             while (iSessionIter)
       
  1436                 {
       
  1437                 CAlfAppSrvSessionBase* session = reinterpret_cast<CAlfAppSrvSessionBase*>(iSessionIter++);
       
  1438                 if ( session && 
       
  1439                      session->ClientWindowGroup() == topmostWgId )
       
  1440                     {
       
  1441                     sessionAboveGivenWgId = session;
       
  1442                     break;
       
  1443                     }
       
  1444                  }
       
  1445             }
       
  1446         }
       
  1447     delete wgs;
       
  1448     return sessionAboveGivenWgId;
       
  1449     }
       
  1450