Symbian3/SDK/Source/GUID-38A656D3-F830-5E26-8167-3638B6BC5DF6.dita
changeset 0 89d6a7a84779
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Symbian3/SDK/Source/GUID-38A656D3-F830-5E26-8167-3638B6BC5DF6.dita	Thu Jan 21 18:18:20 2010 +0000
@@ -0,0 +1,60 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (c) 2007-2010 Nokia Corporation and/or its subsidiary(-ies) All rights reserved. -->
+<!-- This component and the accompanying materials are made available under the terms of the License 
+"Eclipse Public License v1.0" which accompanies this distribution, 
+and is available at the URL "http://www.eclipse.org/legal/epl-v10.html". -->
+<!-- Initial Contributors:
+    Nokia Corporation - initial contribution.
+Contributors: 
+-->
+<!DOCTYPE concept
+  PUBLIC "-//OASIS//DTD DITA Concept//EN" "concept.dtd">
+<concept xml:lang="en" id="GUID-38A656D3-F830-5E26-8167-3638B6BC5DF6"><title>How to restore a compound object</title><prolog><metadata><keywords/></metadata></prolog><conbody><p>The protocol for restoring a compound object is the <codeph>RestoreL()</codeph> function. This is true whether the object has been stored in-line or out-of-line, and should be prototyped as:</p> <codeblock id="GUID-AA727C46-3D5E-53D2-8697-721ED1F0D05C" xml:space="preserve">void RestoreL(CStreamStore&amp; aStore,TStreamId anId);</codeblock> <p>The function takes a reference to the store in which streams are stored and a stream ID. In some cases, the design of a class may be such that it maintains a pointer or reference to the store. In this event, the <codeph>CStreamStore</codeph> argument would be redundant.</p> <section><title>Restoring components stored in-line</title> <p>If an object's components have been stored in-line, then all of these components have been written to the same single stream.</p> <p>For the example class <codeph>CCompound</codeph>, defined as:</p> <codeblock id="GUID-1BB27256-2ADE-516E-8213-4B901A64BB30" xml:space="preserve">CCompound class : public CBase
+    {
+    ...
+    TInt         iDdata;
+    CComponentA* iCompA;
+    CComponentB* iCompB;
+    ...
+    }</codeblock> <p>RestoreL() is implemented as: </p> <codeblock id="GUID-AD51C522-3734-5827-938A-0595DD012A79" xml:space="preserve">void CCompound::RestoreL(CStreamStore&amp; aStore,TStreamId anId)
+    {
+    RStoreReadStream instream;
+    instream.OpenLC(aStore,anId);
+    InternalizeL(instream);
+    CleanupStack::PopAndDestroy();
+    }</codeblock> <p>where the stream ID passed to the function is the ID of the single stream containing the data.</p> </section> <section><title>Restoring components stored out-of-line</title> <p>If an object's components have been stored out-of-line, then all of these components have been written to separate streams.</p> <p>For the example class <codeph>CCompound</codeph>, defined as:</p> <codeblock id="GUID-345E2356-1AD3-5CF4-9847-7AE6C383448C" xml:space="preserve">CCompound class : public CBase
+    {
+    ...
+    TInt                  iDdata;
+    TSwizzle&lt;CComponentA&gt; iCompA;
+    TSwizzle&lt;CComponentB&gt; iCompB;
+    ...
+    }</codeblock> <p>RestoreL() is implemented as:</p> <codeblock id="GUID-81FEC5E3-EDDE-5596-BE12-420CC5D19F91" xml:space="preserve">void CCompound::RestoreL(CStreamStore&amp; aStore,TStreamId anId)
+    {
+    RStoreReadStream stream;      // Construct a read stream.
+    stream.OpenLC(aStore,anId);   // Open the head stream.
+    InternalizeL(stream);         // Internalise top level stream containing CCompound
+                                  // and the IDs of its components. 
+    RestoreComponentsL(aStore);   // Restore components.
+    CleanupStack::PopAndDestroy();
+    }
+</codeblock> <p>where the stream ID passed to the function is the ID of the head stream.</p> <p>InternalizeL() internalises CCompound's data members and the stream IDs of its components:</p> <codeblock id="GUID-36C860E3-9552-52C4-AD54-53B614DE7B8A" xml:space="preserve">void CCompound::InternalizeL(RReadStream&amp; aStream)
+    {
+    aStream &gt;&gt; iDataA;
+    aStream &gt;&gt; iCompA;  
+    aStream &gt;&gt; iCompB;
+    }</codeblock> <p><codeph>RestoreComponentsL()</codeph> constructs each component object and restores them from their respective stream networks. </p> <codeblock id="GUID-FD539747-82E8-5EF1-ADF0-E5101AE8EDA3" xml:space="preserve">void CCompound::RestoreComponentsL(CStreamStore&amp; aStore)
+    { 
+    CComponentA* ptrA = new (ELeave) CComponentA;
+    CleanupStack::PushL(ptrA);
+    ptrA-&gt;RestoreL(aStore,iCompA.AsId());
+    iCompA = ptrA;
+    CleanupStack::Pop();
+    CComponentB* ptrB = new (ELeave) CComponentB;
+    CleanupStack::PushL(ptrB);
+    ptrB-&gt;RestoreL(aStore,iCompB.AsId());
+    iCompB = ptrB CleanupStack::Pop();
+    }</codeblock> <p>In general, an application might want to defer the loading of some components. This would mean either changing the implementation of <codeph>RestoreComponents()</codeph> or adding new functionality to the class. The use of Swizzles is important here as they simplify the handling of the dual representation of an object as a pointer to an in-memory object or as an ID of a stream.</p> <p>Typically, an application might use code such as:</p> <codeblock id="GUID-E2D26E4E-02C0-5E89-8D82-0F628101011C" xml:space="preserve">if (iCompA.IsId())
+    {
+    iCompA = CComponentA::NewL(iStore,iCompA.AsId());
+    }</codeblock> <p>to test whether the component is currently represented by a stream ID or by a pointer to an in-memory object. If a stream ID, then the component would be restored. In this small code fragment, an overloaded <codeph>NewL()</codeph> function is used both to construct and to restore the component object. Once this code has executed, the component is represented by a pointer.</p> <p><b>See also</b> </p> <p><xref href="GUID-C1AA34CB-D63D-57E3-87F6-28AD22537D21.dita">Store map</xref> </p> <p><xref href="GUID-53112730-5871-5920-8861-D2F6BF1595BC.dita">Swizzles and deferred loading</xref> </p> </section> </conbody></concept>
\ No newline at end of file