simPersistSet.cpp
Engine/source/console/simPersistSet.cpp
Public Functions
ConsoleDocClass(SimPersistSet , "@brief A <a href="/coding/class/classsimset/">SimSet</a> that can be safely <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">persisted.\n\n</a>" "Uses SimPersistIDs <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> reference objects in the set " "<a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a0e48c1f64b558d03d870367324920354">while</a> persisted on disk. This allows the set <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> resolve " "its references no matter whether they are loaded before or " "after the set is <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">created.\n\n</a>" "Not intended <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a2732ab74fa0237854c2ba0f75f88a624">for</a> game development, <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a2732ab74fa0237854c2ba0f75f88a624">for</a> editors or internal use <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">only.\n\n</a> " " @internal" )
DefineEngineMethod(SimPersistSet , resolvePersistentIds , void , () , "() - Try <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> bind unresolved persistent IDs in the set." )
Detailed Description
Public Functions
ConsoleDocClass(SimPersistSet , "@brief A <a href="/coding/class/classsimset/">SimSet</a> that can be safely <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">persisted.\n\n</a>" "Uses SimPersistIDs <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> reference objects in the set " "<a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a0e48c1f64b558d03d870367324920354">while</a> persisted on disk. This allows the set <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> resolve " "its references no matter whether they are loaded before or " "after the set is <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">created.\n\n</a>" "Not intended <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a2732ab74fa0237854c2ba0f75f88a624">for</a> game development, <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1a2732ab74fa0237854c2ba0f75f88a624">for</a> editors or internal use <a href="/coding/file/cmdscan_8cpp/#cmdscan_8cpp_1aeab71244afb687f16d8c4f5ee9d6ef0e">only.\n\n</a> " " @internal" )
DefineEngineMethod(SimPersistSet , resolvePersistentIds , void , () , "() - Try <a href="/coding/file/cmdgram_8cpp/#cmdgram_8cpp_1a5bafda9519252aa2d0fd038153f77dca">to</a> bind unresolved persistent IDs in the set." )
IMPLEMENT_CONOBJECT(SimPersistSet )
1 2//----------------------------------------------------------------------------- 3// Copyright (c) 2012 GarageGames, LLC 4// 5// Permission is hereby granted, free of charge, to any person obtaining a copy 6// of this software and associated documentation files (the "Software"), to 7// deal in the Software without restriction, including without limitation the 8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or 9// sell copies of the Software, and to permit persons to whom the Software is 10// furnished to do so, subject to the following conditions: 11// 12// The above copyright notice and this permission notice shall be included in 13// all copies or substantial portions of the Software. 14// 15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 21// IN THE SOFTWARE. 22//----------------------------------------------------------------------------- 23 24#include "console/simPersistSet.h" 25#include "console/simPersistID.h" 26#include "console/consoleTypes.h" 27#include "console/engineAPI.h" 28 29 30IMPLEMENT_CONOBJECT( SimPersistSet ); 31 32ConsoleDocClass( SimPersistSet, 33 "@brief A SimSet that can be safely persisted.\n\n" 34 "Uses SimPersistIDs to reference objects in the set " 35 "while persisted on disk. This allows the set to resolve " 36 "its references no matter whether they are loaded before or " 37 "after the set is created.\n\n" 38 "Not intended for game development, for editors or internal use only.\n\n " 39 "@internal"); 40 41//----------------------------------------------------------------------------- 42 43SimPersistSet::SimPersistSet() 44 : mIsResolvingPIDs( false ) 45{ 46 VECTOR_SET_ASSOCIATION( mUnresolvedPIDs ); 47} 48 49//----------------------------------------------------------------------------- 50 51bool SimPersistSet::processArguments( S32 argc, ConsoleValueRef *argv ) 52{ 53 for( U32 i = 0; i < argc; ++ i ) 54 { 55 // Parse the UUID. 56 Torque::UUID uuid; 57 if( !uuid.fromString( argv[ i ] ) ) 58 { 59 Con::errorf( "SimPersistSet::processArguments - could not read UUID at index %i: %s", i, (const char*)argv[ i ] ); 60 continue; 61 } 62 63 // Find or create the respective persistent ID. 64 SimPersistID* pid = SimPersistID::findOrCreate( uuid ); 65 if( pid->getObject() ) 66 { 67 // There's already an object attached to this PID so just 68 // add the object to the set. 69 addObject( pid->getObject() ); 70 } 71 else 72 { 73 // There not yet an object attached to the PID so push it 74 // onto the stack to resolve it later. 75 pid->incRefCount(); 76 mUnresolvedPIDs.push_back( pid ); 77 } 78 } 79 80 return true; 81} 82 83//----------------------------------------------------------------------------- 84 85void SimPersistSet::write( Stream& stream, U32 tabStop, U32 flags ) 86{ 87 if( ( flags & SelectedOnly ) && !isSelected() ) 88 return; 89 90 // If the selection is transient, we cannot really save it. 91 // Just invoke the default SimObject::write and return. 92 93 if( !getCanSave() ) 94 { 95 Con::errorf( "SimPersistSet::write - transient set being saved: %d:%s (%s)", 96 getId(), getClassName(), getName() ); 97 Parent::write( stream, tabStop, flags ); 98 return; 99 } 100 101 // If there are unresolved PIDs, give resolving them one last 102 // chance before writing out the set. 103 104 if( !mUnresolvedPIDs.empty() ) 105 resolvePIDs(); 106 107 // Write the set out. 108 109 stream.writeTabs( tabStop ); 110 111 StringBuilder buffer; 112 buffer.format( "new %s(%s", getClassName(), getName() ? getName() : "" ); 113 114 // Write the persistent IDs of all child objects into the set's 115 // object constructor so we see them passed back to us through 116 // processArguments when the object gets read in. 117 118 const U32 numChildren = size(); 119 for( U32 i = 0; i < numChildren; ++ i ) 120 { 121 SimObject* child = at( i ); 122 123 SimPersistID* pid = child->getPersistentId(); 124 AssertWarn( pid != NULL, "SimPersistSet::write - object without pid in persistent selection!" ); 125 if( !pid ) 126 continue; 127 128 buffer.append( ',' ); 129 buffer.append( '"' ); 130 buffer.append( pid->getUUID().toString() ); 131 buffer.append( '"' ); 132 } 133 134 buffer.append( ") {\r\n" ); 135 136 stream.write( buffer.length(), buffer.data() ); 137 138 // Write our object fields. 139 140 writeFields( stream, tabStop + 1 ); 141 142 // Close our object definition. 143 144 stream.writeTabs( tabStop ); 145 stream.write( 4, "};\r\n" ); 146} 147 148//----------------------------------------------------------------------------- 149 150void SimPersistSet::resolvePIDs() 151{ 152 if( mIsResolvingPIDs ) 153 return; 154 155 lock(); 156 mIsResolvingPIDs = true; 157 158 for( U32 i = 0; i < mUnresolvedPIDs.size(); ++ i ) 159 if( mUnresolvedPIDs[ i ]->getObject() != NULL ) 160 { 161 addObject( mUnresolvedPIDs[ i ]->getObject() ); 162 mUnresolvedPIDs[i]->decRefCount(); 163 mUnresolvedPIDs.erase( i ); 164 -- i; 165 } 166 167 mIsResolvingPIDs = false; 168 unlock(); 169} 170 171//----------------------------------------------------------------------------- 172 173void SimPersistSet::addObject( SimObject* object ) 174{ 175 // If this set isn't transient, make sure the object has a valid 176 // persistent ID. 177 178 if( getCanSave() ) 179 object->getOrCreatePersistentId(); 180 181 Parent::addObject( object ); 182} 183 184//============================================================================= 185// Console Methods. 186//============================================================================= 187// MARK: ---- Console Methods ---- 188 189//----------------------------------------------------------------------------- 190 191DefineEngineMethod( SimPersistSet, resolvePersistentIds, void, (), , "() - Try to bind unresolved persistent IDs in the set." ) 192{ 193 object->resolvePIDs(); 194} 195