00001 // Copyright (c) 2000-2009 Nokia Corporation and/or its subsidiary(-ies). 00002 // All rights reserved. 00003 // This component and the accompanying materials are made available 00004 // under the terms of "Eclipse Public License v1.0" 00005 // which accompanies this distribution, and is available 00006 // at the URL "http://www.eclipse.org/legal/epl-v10.html". 00007 // 00008 // Initial Contributors: 00009 // Nokia Corporation - initial contribution. 00010 // 00011 // Contributors: 00012 // 00013 // Description: 00014 // Example to demonstrate how a network of objects can be written 00015 // to more than one stream in a direct file store, and how the loading 00016 // of an object from the store into memory may be deferred. 00017 // The example: 00018 // creates a direct file store (replacing any existing direct 00019 // file store of the same name) 00020 // constructs a CClassABC container object and then constructs a 00021 // contained CClassA, CClassB and CClassC object. 00022 // Displays the content of the CClassA, CClassB and CClassC objects 00023 // externalizes the CClassB object in its own stream and keeps hold of the 00024 // stream id. Externalizes the CClassA object, the streamid of the 00025 // CClassB object and the CClassC object in a single 00026 // stream. Makes this latter stream the root stream of the store 00027 // closes the store and deletes the container and its contained CClassA, 00028 // CClassB and CCLassC objects (from memory) 00029 // re-opens the direct file store 00030 // restores the CClassABC container object; in effect, this restores 00031 // its contained CClassA and CClassC objects and the stream id of its 00032 // CClassB object. The CClassB object is not restored into memory until 00033 // it is needed. 00034 // displays the content of the CClassA, CClassB and CClassC objects; it is 00035 // at this time that the CClassB object is restored into memory. (This 00036 // illustrates the necessity of keeping the store open. 00037 // closes the store and deletes the container and its contained CClassA, 00038 // CClassB and CCLassC objects (from memory) 00039 // Notes: 00040 // The file name and extension of the direct file store is "WriteToMany.dat". 00041 // and will be created in "\data\" folder of the writable drive. 00042 // 00043 00044 #include "WriteToMany.h" 00045 00046 00047 //*************************************************************** 00048 // 00049 // Implementations 00050 // 00051 //*************************************************************** 00052 00053 00054 // The file name, extension and path for the file store 00055 _LIT(KFullNameOfFileStore,"\\epoc32ex\\data\\WriteToMany.dat"); 00056 00057 00058 // Do the example 00059 static void doExampleL() 00060 { 00061 // make sure directory exists 00062 fsSession.MkDirAll(KFullNameOfFileStore); 00063 doMakeAndStoreL(KFullNameOfFileStore); 00064 doRestoreL(KFullNameOfFileStore); 00065 } 00066 00067 00068 static void doMakeAndStoreL(const TDesC& aName) 00069 { 00070 // Create (replace, if it exists) the direct file store 00071 TParse filestorename; 00072 fsSession.Parse(aName,filestorename); 00073 CFileStore* store = CDirectFileStore::ReplaceLC(fsSession,filestorename.FullName(),EFileWrite); 00074 00075 // Must say what kind of file store. 00076 store->SetTypeL(KDirectFileStoreLayoutUid); 00077 00078 // Construct the container object for CClassA,CClassB and CClassC. 00079 // Complete the construction of the contained CClassA, CClassB 00080 // and CClassC objects. 00081 _LIT(KTxtDataForClassA,"Data for the CClassA - AAAAA"); 00082 _LIT(KTxtDataForClassB,"Data for the CClassB - BBBBB"); 00083 _LIT(KTxtDataForClassC,"Data for the CClassC - CCCCC"); 00084 00085 CClassABC* theABC = CClassABC::NewLC(*store); 00086 theABC->ConstructAL(KTxtDataForClassA,-1,2); 00087 theABC->ConstructB(KTxtDataForClassB,-3,4,5.6); 00088 theABC->ConstructC(KTxtDataForClassC); 00089 00090 // Show contents of the CClassA, CClassB & CClassC objects 00091 _LIT(KTxtClassAContent,"CClassA content ..."); 00092 _LIT(KTxtClassBContent,"CClassB content ..."); 00093 _LIT(KTxtClassCContent,"CClassC content ..."); 00094 00095 doShow(KTxtClassAContent,*theABC->PtrA()); 00096 doShow(KTxtClassBContent,*theABC->PtrBL()); 00097 doShow(KTxtClassCContent,*theABC->PtrC()); 00098 00099 // Store the object network by: 00100 // storing the CClassB object in its own stream and 00101 // then storing: 00102 // the CClassA object 00103 // the streamid of the CClassB object 00104 // the CClassC object 00105 // in a separate stream. 00106 TStreamId id = theABC->StoreL(); 00107 00108 // Set this stream id as the root stream 00109 store->SetRootL(id); 00110 00111 // Destroy: 00112 // the container object. 00113 // the direct file store object (closes the file), 00114 // 00115 CleanupStack::PopAndDestroy(2); 00116 } 00117 00118 00119 static void doRestoreL(const TDesC& aName) 00120 { 00121 // Open the direct file store 00122 TParse filestorename; 00123 fsSession.Parse(aName,filestorename); 00124 CFileStore* store = CDirectFileStore::OpenLC(fsSession,filestorename.FullName(),EFileRead); 00125 00126 // Restore the container object from the root stream. 00127 // This constructs a CClassA and a CClassC object 00128 // and restores them from the root stream. 00129 // The swizzle for the CClassB object is 00130 // constructed from the streamid in the root stream. 00131 // Note that the CClassB object itself is not loaded into 00132 // memory until it is needed. 00133 CClassABC* theABC = CClassABC::NewLC(*store,store->Root()); 00134 00135 // Show restored contents of the CClassA, CClassB and CClassC 00136 // objects. Note that the CClassB object may not be in memory and 00137 // will be loaded in when needed. 00138 _LIT(KTxtRestoredClassA,"Restored CClassA content ..."); 00139 _LIT(KTxtRestoredClassB,"Restored CClassB content ..."); 00140 _LIT(KTxtRestoredClassC,"Restored CClassC content ..."); 00141 00142 doShow(KTxtRestoredClassA,*theABC->PtrA()); 00143 doShow(KTxtRestoredClassB,*theABC->PtrBL()); 00144 doShow(KTxtRestoredClassC,*theABC->PtrC()); 00145 00146 // Destroy: 00147 // the CClassABC object, 00148 // the direct file store object (closes the file) 00149 CleanupStack::PopAndDestroy(2); 00150 } 00151 00152 _LIT(KTxtNewLine,"\n"); 00153 _LIT(KFormatType1,"\n%S, "); 00154 _LIT(KFormatType2,"%d, "); 00155 _LIT(KFormatType3,"%u "); 00156 _LIT(KFormatType4,"%u, "); 00157 _LIT(KFormatType5,"%f "); 00158 00159 static void doShow(const TDesC& aHeading,const CClassA& anA) 00160 { 00161 console->Printf(KTxtNewLine); 00162 console->Printf(aHeading); 00163 console->Printf(KFormatType1,anA.iVarBuf); 00164 console->Printf(KFormatType2,anA.iIntValue); 00165 console->Printf(KFormatType3,anA.iUintValue); 00166 console->Printf(KTxtNewLine); 00167 } 00168 00169 00170 00171 static void doShow(const TDesC& aHeading,const CClassB& aB) 00172 { 00173 console->Printf(KTxtNewLine); 00174 console->Printf(aHeading); 00175 console->Printf(KFormatType1,&aB.iFixBuf); 00176 console->Printf(KFormatType2,aB.iIntValue); 00177 console->Printf(KFormatType4,aB.iUintValue); 00178 console->Printf(KFormatType5,aB.iRealValue); 00179 console->Printf(KTxtNewLine); 00180 } 00181 00182 static void doShow(const TDesC& aHeading,const CClassC& aC) 00183 { 00184 console->Printf(KTxtNewLine); 00185 console->Printf(aHeading); 00186 console->Printf(KFormatType1,&aC.iFixBuf); 00187 console->Printf(KTxtNewLine); 00188 } 00189 00190 00191 //*************************************************************** 00192 // 00193 // CClassABC Implementation 00194 // 00195 //*************************************************************** 00196 CClassABC::CClassABC(CStreamStore& aStore) 00197 : iStore(aStore) 00198 {} 00199 00200 CClassABC::CClassABC(CStreamStore& aStore,TStreamId anId) 00201 : iStore(aStore), iId(anId) 00202 {} 00203 00204 CClassABC* CClassABC::NewLC(CStreamStore& aStore) 00205 { 00206 CClassABC* self = new (ELeave) CClassABC(aStore); 00207 CleanupStack::PushL(self); 00208 self->ConstructL(); 00209 return self; 00210 } 00211 00212 CClassABC* CClassABC::NewLC(CStreamStore& aStore, TStreamId anId) 00213 { 00214 CClassABC* self = new (ELeave) CClassABC(aStore,anId); 00215 CleanupStack::PushL(self); 00216 self->RestoreL(); 00217 return self; 00218 } 00219 00220 void CClassABC::ConstructL() 00221 { 00222 iA = CClassA::NewL(); 00223 iB = CClassB::NewL();// assigns CClassB* to TSwizzle<CClassB>. Uses TSwizzle operator=(T*) 00224 iC = CClassC::NewL(); 00225 } 00226 00227 void CClassABC::ConstructAL(const TDesC& aData,TInt anInt,TUint aUint) 00228 { 00229 iA->iVarBuf = aData.AllocL(); 00230 iA->iIntValue = anInt; 00231 iA->iUintValue = aUint; 00232 } 00233 00234 void CClassABC::ConstructB(const TDesC& aData,TInt anInt,TUint aUint,TReal aReal) 00235 { 00236 iB->iFixBuf = aData; 00237 iB->iIntValue = anInt; 00238 iB->iUintValue = aUint; 00239 iB->iRealValue = aReal; 00240 } 00241 00242 void CClassABC::ConstructC(const TDesC& aData) 00243 { 00244 iC->iFixBuf = aData; 00245 } 00246 00247 00248 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00249 // Destructor deletes the CClassB object only if it is in memory. 00250 // The IsPtr() function can be used to determine whether the 00251 // CClassB object is memory. 00252 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00253 CClassABC::~CClassABC() 00254 { 00255 delete iA; 00256 delete iC; 00257 if (iB.IsPtr()) 00258 delete iB.AsPtr(); // can also "delete iB;" makes implicit call to "operator T*()" 00259 } 00260 00261 00262 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00263 // Stores the CClassB object in its own stream and 00264 // then stores: 00265 // the CClassA object, 00266 // the streamid of the CClassB object, 00267 // the CClassC object 00268 // in a separate stream. 00269 // Returns the streamid of this last stream 00270 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00271 TStreamId CClassABC::StoreL() 00272 { 00273 // Construct the output stream which is intended 00274 // to hold the CClassB object only. 00275 RStoreWriteStream outstream; 00276 TStreamId idForB = outstream.CreateLC(iStore); 00277 // Stream out the CClassB object. 00278 // Note that the right hand side returns a reference 00279 // to CClassB 00280 outstream << *iB; 00281 // Commit changes to the stream 00282 outstream.CommitL(); 00283 // Cleanup the stream object 00284 CleanupStack::PopAndDestroy(); 00285 // Now construct the output stream which is intended 00286 // to hold: 00287 // the CClassA object, 00288 // the streamid of the CClassB object, 00289 // the CClassC object 00290 TStreamId id = outstream.CreateLC(iStore); 00291 // Write out the CClassA object. 00292 outstream << *iA; 00293 // Write out the stream id of the CClassB object 00294 outstream << idForB; 00295 // Write out the CClassC object. 00296 outstream << *iC; 00297 // Commit changes to the stream 00298 outstream.CommitL(); 00299 // Cleanup the stream object, 00300 CleanupStack::PopAndDestroy(); 00301 // Return this stream id 00302 return id; 00303 } 00304 00305 00306 const CClassA* CClassABC::PtrA() 00307 { 00308 return iA; // Return a pointer to the contained CClassA object 00309 } 00310 00311 00312 const CClassB* CClassABC::PtrBL() 00313 { 00314 if (iB.IsId()) // If the contained CClassB object is not in memory, it must 00315 RestoreBL(); // be loaded in before a pointer can be returned to the caller 00316 return iB.AsPtr(); 00317 } 00318 00319 00320 const CClassC* CClassABC::PtrC() 00321 { 00322 return iC; //Returns a pointer to the contained CClassC object 00323 } 00324 00325 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00326 // Restores the CClassA and CClassC objects and the streamid for the 00327 // CClassB object. 00328 // The swizzle for the CClassB object is constructed from the 00329 // streamid but the CClassB object itself is NOT restored at 00330 // this time. 00331 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00332 void CClassABC::RestoreL() 00333 { 00334 // Construct the input stream. 00335 RStoreReadStream instream; 00336 instream.OpenLC(iStore,iId); 00337 // Construct a CClassA object and restore from the stream 00338 iA = CClassA::NewL(); 00339 instream >> *iA; 00340 // Construct the swizzle for the CClassB object. This 00341 // stream contains the id of the stream which 00342 // actually contains the full CClassB object. The loading of 00343 // the CClassB object into memory is deferred until later. 00344 // The resulting swizzle represents the CClassB object as 00345 // a streamid 00346 instream >> iB; 00347 // Construct a CClassC object and restrore from the stream 00348 iC = CClassC::NewL(); 00349 instream >> *iC; 00350 // Cleanup the stream object 00351 CleanupStack::PopAndDestroy(); 00352 } 00353 00354 00355 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00356 // Loads the CClassB object into memory and changes the swizzle's 00357 // representation from "streamid" to "pointer". 00358 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00359 void CClassABC::RestoreBL() 00360 { 00361 // Construct the input stream. Assumes we have the correct store (this 00362 // emphasizes the need to ensure that the store remain open) 00363 RStoreReadStream instream; 00364 instream.OpenLC(iStore,iB.AsId()); 00365 // Construct a CClassB object and restore from the stream. The 00366 // assignment: CClassB* to TSwizzle<CClassB> changes the 00367 // swizzle's representation of the CClassB object 00368 // from "streamid" to "pointer" 00369 CClassB* ptrB = CClassB::NewLC(); 00370 instream >> *ptrB; 00371 CleanupStack::Pop(); 00372 iB = ptrB; 00373 // Cleanup the stream object 00374 CleanupStack::PopAndDestroy(); 00375 } 00376 00377 //*************************************************************** 00378 // 00379 // CClassA Implementation 00380 // 00381 //*************************************************************** 00382 CClassA* CClassA::NewL() 00383 { 00384 CClassA* self = CClassA::NewLC(); 00385 CleanupStack::Pop(); 00386 return self; 00387 } 00388 00389 CClassA* CClassA::NewLC() 00390 { 00391 CClassA* self = new (ELeave) CClassA; 00392 CleanupStack::PushL(self); 00393 return self; 00394 } 00395 00396 CClassA::~CClassA() 00397 { 00398 delete iVarBuf; 00399 } 00400 00401 void CClassA::ExternalizeL(RWriteStream& aStream) const 00402 { 00403 aStream.WriteInt32L(iVarBuf->Des().MaxLength()); 00404 aStream << *iVarBuf; 00405 aStream.WriteInt32L(iIntValue); 00406 aStream.WriteUint32L(iUintValue); 00407 } 00408 00409 void CClassA::InternalizeL(RReadStream& aStream) 00410 { 00411 TInt maxlen; 00412 maxlen = aStream.ReadInt32L(); 00413 iVarBuf = HBufC::NewL(aStream,maxlen); 00414 iIntValue = aStream.ReadInt32L(); 00415 iUintValue = aStream.ReadUint32L(); 00416 } 00417 00418 00419 //*************************************************************** 00420 // 00421 // CClassB Implementation 00422 // 00423 //*************************************************************** 00424 CClassB* CClassB::NewLC() 00425 { 00426 CClassB* self = new (ELeave) CClassB; 00427 CleanupStack::PushL(self); 00428 return self; 00429 } 00430 00431 CClassB* CClassB::NewL() 00432 { 00433 CClassB* self = CClassB::NewLC(); 00434 CleanupStack::Pop(); 00435 return self; 00436 } 00437 00438 void CClassB::ExternalizeL(RWriteStream& aStream) const 00439 { 00440 aStream << iFixBuf; 00441 aStream.WriteInt32L(iIntValue); 00442 aStream.WriteUint32L(iUintValue); 00443 aStream.WriteReal64L(iRealValue); 00444 } 00445 00446 void CClassB::InternalizeL(RReadStream& aStream) 00447 { 00448 aStream >> iFixBuf; 00449 iIntValue = aStream.ReadInt32L(); 00450 iUintValue = aStream.ReadUint32L(); 00451 iRealValue = aStream.ReadReal64L(); 00452 } 00453 00454 //*************************************************************** 00455 // 00456 // CClassC Implementation 00457 // 00458 //*************************************************************** 00459 CClassC* CClassC::NewL() 00460 { 00461 CClassC* self = CClassC::NewLC(); 00462 CleanupStack::Pop(); 00463 return self; 00464 } 00465 00466 CClassC* CClassC::NewLC() 00467 { 00468 CClassC* self = new (ELeave) CClassC; 00469 CleanupStack::PushL(self); 00470 return self; 00471 } 00472 00473 void CClassC::ExternalizeL(RWriteStream& aStream) const 00474 { 00475 aStream << iFixBuf; 00476 } 00477 00478 void CClassC::InternalizeL(RReadStream& aStream) 00479 { 00480 aStream >> iFixBuf; 00481 }
Copyright ©2010 Nokia Corporation and/or its subsidiary(-ies).
All rights
reserved. Unless otherwise stated, these materials are provided under the terms of the Eclipse Public License
v1.0.