phonebookui/Phonebook/Engine/src/DigViewGraph.cpp
changeset 0 e686773b3f54
equal deleted inserted replaced
-1:000000000000 0:e686773b3f54
       
     1 /*
       
     2 * Copyright (c) 2002 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: 
       
    15 *		View node class
       
    16 *
       
    17 */
       
    18 
       
    19 
       
    20 // INCLUDE FILES
       
    21 #include <DigViewGraph.h>
       
    22 #include <barsc.h>      // RResourceFile
       
    23 #include <barsread.h>   // TResourceReader
       
    24 #include <e32std.h>     
       
    25 
       
    26 
       
    27 /// Unnamed namespace for local definitions
       
    28 namespace {
       
    29 void CleanupResetAndDestroy(TAny* aObj)
       
    30     {
       
    31     if (aObj)
       
    32         {
       
    33         static_cast<CArrayPtrFlat<CDigViewNode>*>(aObj)->ResetAndDestroy();
       
    34         delete aObj;
       
    35         }
       
    36     }
       
    37 
       
    38 // LOCAL DEBUG CODE
       
    39 #ifdef _DEBUG
       
    40 // MODULE DATA STRUCTURES
       
    41 enum TPanicCode
       
    42     {    
       
    43     EPanicPre_MergeNodesL = 1
       
    44     };
       
    45 
       
    46 void Panic(TPanicCode aReason)
       
    47     {
       
    48     _LIT(KPanicText, "CDigViewGraph");
       
    49     User::Panic(KPanicText,aReason);
       
    50     }
       
    51 #endif
       
    52 }
       
    53 
       
    54 // ================= MEMBER FUNCTIONS =======================
       
    55 
       
    56 
       
    57 //
       
    58 // CDigViewNode
       
    59 // 
       
    60 EXPORT_C CDigViewNode::~CDigViewNode()
       
    61     {
       
    62     }
       
    63 
       
    64 EXPORT_C TBool CDigViewNode::FindTransition
       
    65         (const TDigViewTransition& aTransition) const
       
    66     {
       
    67     for (TInt i=0; i < iTransitions.Count(); ++i)
       
    68         {
       
    69         if (iTransitions[i] == aTransition)
       
    70             return ETrue;
       
    71         }
       
    72     return EFalse;
       
    73     }
       
    74 
       
    75 /**
       
    76  * Finds transition based on aEvent, in case not found returns NULL.
       
    77  *
       
    78  * @param aEvent event to be searched
       
    79  */
       
    80 TDigViewTransition* CDigViewNode::FindTransition(const TInt aEvent)
       
    81     {
       
    82     for (TInt i=0; i < iTransitions.Count(); ++i)
       
    83         {
       
    84         if (iTransitions[i].iEvent == aEvent)
       
    85             return &iTransitions[i];
       
    86         }
       
    87     return NULL;
       
    88     }
       
    89 
       
    90 /**
       
    91  * Appends or modify existing transition(s). 
       
    92  *
       
    93  * @param aNewNode holds transitions to be processed
       
    94  */
       
    95 void CDigViewNode::MergeL(CDigViewNode& aNewNode)
       
    96     {
       
    97     TInt transCount = aNewNode.iTransitions.Count();
       
    98     while (transCount-- > 0)
       
    99         {
       
   100         TDigViewTransition newTrans = aNewNode.iTransitions.At(transCount);
       
   101         TDigViewTransition* trans = FindTransition(newTrans.iEvent);
       
   102         if (trans)
       
   103             {
       
   104             trans->iTargetViewId = newTrans.iTargetViewId;
       
   105             }
       
   106         else 
       
   107             {
       
   108             // Add new transition
       
   109             iTransitions.AppendL(newTrans);
       
   110             }
       
   111         }
       
   112     iAdditionalResId = aNewNode.iAdditionalResId;
       
   113     }
       
   114 
       
   115 
       
   116 //
       
   117 // CDigViewGraph
       
   118 //
       
   119 EXPORT_C CDigViewGraph* CDigViewGraph::NewL(TResourceReader& aResReader)
       
   120     {
       
   121     CDigViewGraph* self = new(ELeave) CDigViewGraph;
       
   122     CleanupStack::PushL(self);
       
   123     self->ConstructL(aResReader);
       
   124     CleanupStack::Pop();  //self
       
   125     return self;
       
   126     }
       
   127 
       
   128 void CDigViewGraph::ConstructL(TResourceReader& aResReader)
       
   129     {
       
   130     iNodes = CreateUnlinkedNodesFromResourceL(aResReader);
       
   131     LinkNodesWithTransitions();    
       
   132     }
       
   133 
       
   134 EXPORT_C CDigViewGraph::~CDigViewGraph()
       
   135     {    
       
   136     if (iNodes)
       
   137         {
       
   138         iNodes->ResetAndDestroy();
       
   139         }
       
   140     delete iNodes;
       
   141     }
       
   142 
       
   143 EXPORT_C CDigViewNode* CDigViewGraph::FindNodeWithViewId(TUid aViewId) const
       
   144     {
       
   145     if (aViewId != KNullUid)
       
   146         {
       
   147         TInt count = iNodes->Count();
       
   148         while (count-- > 0)
       
   149             {
       
   150             CDigViewNode* node = iNodes->At(count);
       
   151             if (node->iViewId == aViewId)
       
   152                 return node;
       
   153             }
       
   154         }
       
   155     return NULL;
       
   156     }
       
   157 
       
   158 EXPORT_C void CDigViewGraph::ModifyViewGraphL(TResourceReader& aResReader)
       
   159     {
       
   160     CDigViewNodeArray* nodes = CreateUnlinkedNodesFromResourceL(aResReader);
       
   161     // The nodes of the array are not cleaned up by design, only the array
       
   162     // holding them. The node cleanup is handled in MergeNodesL.
       
   163     CleanupStack::PushL(nodes); 
       
   164     MergeNodesL(*nodes); // The ownership of the array's nodes is taken here
       
   165     CleanupStack::PopAndDestroy(nodes);
       
   166 
       
   167     LinkNodesWithTransitions();
       
   168     }
       
   169 
       
   170 /**
       
   171  * Creates a new view node array from resource file.
       
   172  *
       
   173  * @param aResReader containing DIG_VIEW_GRAPH resource
       
   174  */
       
   175 CDigViewGraph::CDigViewNodeArray* CDigViewGraph::
       
   176         CreateUnlinkedNodesFromResourceL(TResourceReader& aResReader)
       
   177     {
       
   178     TInt count = aResReader.ReadInt16();
       
   179     CDigViewNodeArray* nodes = new (ELeave) CDigViewNodeArray(1);
       
   180     CleanupStack::PushL(TCleanupItem(CleanupResetAndDestroy,nodes));
       
   181     if (count > 1)
       
   182         {
       
   183         nodes->SetReserveL(count);
       
   184         }
       
   185     
       
   186     while (count-- > 0)
       
   187         {            
       
   188         CDigViewNode* node = new(ELeave) CDigViewNode;
       
   189         CleanupStack::PushL(node);
       
   190         
       
   191         // DIG_VIEW_NODE
       
   192         node->iViewId.iUid = aResReader.ReadInt32();
       
   193         node->iDefaultPrevViewId.iUid = aResReader.ReadInt32(); 
       
   194         node->iDefaultPreviousNode = NULL;
       
   195         node->iPreviousNode = NULL;        
       
   196         node->iExitNode = aResReader.ReadInt8();
       
   197         
       
   198         TInt transCount = aResReader.ReadInt16(); // transitions[]
       
   199         node->iTransitions.SetReserveL(transCount);
       
   200         while (transCount-- > 0)
       
   201             {
       
   202             // DIG_VIEW_TRANSITION
       
   203             TDigViewTransition trans;
       
   204             trans.iEvent = aResReader.ReadInt32();            
       
   205             trans.iTargetViewId.iUid = aResReader.ReadInt32();
       
   206             trans.iNode = NULL;
       
   207             node->iTransitions.AppendL(trans);
       
   208             }        
       
   209         node->iAdditionalResId = aResReader.ReadInt32();
       
   210 
       
   211         nodes->AppendL(node);
       
   212         CleanupStack::Pop();
       
   213         }
       
   214     CleanupStack::Pop(nodes);
       
   215     return nodes;
       
   216     }   
       
   217 
       
   218 /**
       
   219  * Links nodes with transitions.
       
   220  */
       
   221 void CDigViewGraph::LinkNodesWithTransitions()
       
   222     {
       
   223     for (TInt i(0); i < iNodes->Count(); i++)
       
   224         {
       
   225         CDigViewNode* node = iNodes->At(i);
       
   226         node->iDefaultPreviousNode = FindNodeWithViewId
       
   227                 (node->iDefaultPrevViewId);
       
   228         TInt transCount = node->iTransitions.Count();
       
   229         while (transCount-- > 0)
       
   230             {
       
   231             TDigViewTransition& trans = node->iTransitions.At(transCount);
       
   232             trans.iNode = FindNodeWithViewId(trans.iTargetViewId);
       
   233             }
       
   234         }
       
   235     }
       
   236 
       
   237 /**
       
   238  * Merges two node arrays, iNode and aChangedNodes. 
       
   239  * Handles also destruction of nodes existing in aChangedNodes.
       
   240  *
       
   241  * @param aChangedNodes array to be merged with iNode
       
   242  */
       
   243 void CDigViewGraph::MergeNodesL(CDigViewNodeArray& aChangedNodes)
       
   244     {
       
   245     __ASSERT_DEBUG(iNodes != &aChangedNodes, Panic(EPanicPre_MergeNodesL));
       
   246 
       
   247     for ( TInt j = aChangedNodes.Count()-1; j >= 0; --j )
       
   248         {
       
   249         // Changed node has to be destroyed if not appended
       
   250         CDigViewNode* changedNode = aChangedNodes.At(j);
       
   251         CDigViewNode* node = FindNodeWithViewId(changedNode->ViewId());
       
   252         if (node)
       
   253             {
       
   254             // The changedNode is not in cleanupstack yet,
       
   255             // @see CDigViewGraph::ModifyViewGraphL
       
   256             CleanupStack::PushL(changedNode);
       
   257             node->MergeL(*changedNode);
       
   258             aChangedNodes.Delete(j);
       
   259             CleanupStack::PopAndDestroy(changedNode);
       
   260             }
       
   261         else
       
   262             {
       
   263             // The changedNode is not in cleanupstack yet,
       
   264             // @see CDigViewGraph::ModifyViewGraphL
       
   265             CleanupStack::PushL(changedNode);
       
   266             iNodes->AppendL(changedNode);
       
   267             CleanupStack::Pop(changedNode);
       
   268             }
       
   269         }
       
   270     }
       
   271 
       
   272 
       
   273 //  End of File