MonoObject* ScriptSerializableUtility::internal_Create(MonoReflectionType* reflType) { if (reflType == nullptr) return nullptr; ::MonoClass* monoClass = MonoUtil::getClass(reflType); MonoClass* engineClass = MonoManager::instance().findClass(monoClass); SPtr<ManagedSerializableTypeInfo> typeInfo = ScriptAssemblyManager::instance().getTypeInfo(engineClass); if (typeInfo == nullptr) { LOGWRN("Cannot create an instance of type \"" + engineClass->getFullName() + "\", it is not marked as serializable."); return nullptr; } SPtr<ManagedSerializableFieldData> data = ManagedSerializableFieldData::createDefault(typeInfo); MemorySerializer ms; // Note: This code unnecessarily encodes to binary and decodes from it. I could have added a specialized create method that does it directly, // but didn't feel the extra code was justified. UINT32 size = 0; UINT8* encodedData = ms.encode(data.get(), size); SPtr<ManagedSerializableFieldData> createdData = std::static_pointer_cast<ManagedSerializableFieldData>(ms.decode(encodedData, size)); createdData->deserialize(); return createdData->getValueBoxed(typeInfo); }
ResourceBackupData ManagedResource::backup(bool clearExisting) { SPtr<ManagedSerializableObject> serializableObject = ManagedSerializableObject::createFromExisting(mManagedInstance); ResourceBackupData backupData; if (serializableObject != nullptr) { MemorySerializer ms; backupData.size = 0; backupData.data = ms.encode(serializableObject.get(), backupData.size); } else { backupData.size = 0; backupData.data = nullptr; } if (clearExisting) { if (mManagedInstance != nullptr) { mManagedInstance = nullptr; MonoUtil::freeGCHandle(mManagedHandle); mManagedHandle = 0; } } return backupData; }
void CmdDeleteSO::recordSO(const HSceneObject& sceneObject) { MemorySerializer serializer; mSerializedObject = serializer.encode(mSceneObject.get(), mSerializedObjectSize); HSceneObject parent = mSceneObject->getParent(); if (parent != nullptr) mSerializedObjectParentId = parent->getInstanceId(); mSceneObjectProxy = CmdUtility::createProxy(mSceneObject); }
void ManagedResource::restore(MonoObject* instance, const ResourceBackupData& data) { mManagedInstance = instance; if (mManagedInstance != nullptr) { mManagedHandle = MonoUtil::newGCHandle(mManagedInstance); if (data.data != nullptr) { MemorySerializer ms; SPtr<ManagedSerializableObject> serializableObject = std::static_pointer_cast<ManagedSerializableObject>(ms.decode(data.data, data.size)); SPtr<ManagedResourceMetaData> managedResMetaData = std::static_pointer_cast<ManagedResourceMetaData>(mMetaData); SPtr<ManagedSerializableObjectInfo> currentObjInfo = nullptr; if (ScriptAssemblyManager::instance().getSerializableObjectInfo(managedResMetaData->typeNamespace, managedResMetaData->typeName, currentObjInfo)) serializableObject->deserialize(mManagedInstance, currentObjInfo); } } else { // Could not restore resource ManagedResourceManager::instance().unregisterManagedResource(mMyHandle); } }
void ScriptSerializedSceneObject::internal_Restore(ScriptSerializedSceneObject* thisPtr) { HSceneObject sceneObj = thisPtr->mSO; if (sceneObj.isDestroyed()) return; HSceneObject parent = sceneObj->getParent(); UINT32 numChildren = sceneObj->getNumChildren(); HSceneObject* children = nullptr; if (!thisPtr->mRecordHierarchy) { children = bs_stack_new<HSceneObject>(numChildren); for (UINT32 i = 0; i < numChildren; i++) { HSceneObject child = sceneObj->getChild(i); children[i] = child; child->setParent(HSceneObject()); } } sceneObj->destroy(true); GameObjectManager::instance().setDeserializationMode(GODM_RestoreExternal | GODM_UseNewIds); MemorySerializer serializer; SPtr<SceneObject> restored = std::static_pointer_cast<SceneObject>( serializer.decode(thisPtr->mSerializedObject, thisPtr->mSerializedObjectSize)); EditorUtility::restoreIds(restored->getHandle(), thisPtr->mSceneObjectProxy); restored->setParent(parent); if (!thisPtr->mRecordHierarchy) { for (UINT32 i = 0; i < numChildren; i++) children[i]->setParent(restored->getHandle()); bs_stack_delete(children, numChildren); } restored->_instantiate(); }
ScriptSerializedSceneObject::ScriptSerializedSceneObject(MonoObject* instance, const HSceneObject& so, bool recordHierarchy) : ScriptObject(instance), mSO(so), mRecordHierarchy(recordHierarchy), mSerializedObject(nullptr), mSerializedObjectSize(0) { if (mSO.isDestroyed()) return; UINT32 numChildren = mSO->getNumChildren(); HSceneObject* children = nullptr; if (!mRecordHierarchy) { children = bs_stack_new<HSceneObject>(numChildren); for (UINT32 i = 0; i < numChildren; i++) { HSceneObject child = mSO->getChild(i); children[i] = child; child->setParent(HSceneObject()); } } bool isInstantiated = !mSO->hasFlag(SOF_DontInstantiate); mSO->_setFlags(SOF_DontInstantiate); MemorySerializer serializer; mSerializedObject = serializer.encode(mSO.get(), mSerializedObjectSize); if (isInstantiated) mSO->_unsetFlags(SOF_DontInstantiate); mSceneObjectProxy = EditorUtility::createProxy(mSO); if (!mRecordHierarchy) { for (UINT32 i = 0; i < numChildren; i++) children[i]->setParent(mSO->getHandle()); bs_stack_delete(children, numChildren); } }
void CmdDeleteSO::revert() { if (mSceneObject == nullptr) return; HSceneObject parent; if (mSerializedObjectParentId != 0) parent = GameObjectManager::instance().getObject(mSerializedObjectParentId); GameObjectManager::instance().setDeserializationMode(GODM_RestoreExternal | GODM_UseNewIds); // Object might still only be queued for destruction, but we need to fully destroy it since we're about to replace // the potentially only reference to the old object if (!mSceneObject.isDestroyed()) mSceneObject->destroy(true); MemorySerializer serializer; SPtr<SceneObject> restored = std::static_pointer_cast<SceneObject>(serializer.decode(mSerializedObject, mSerializedObjectSize)); CmdUtility::restoreIds(restored->getHandle(), mSceneObjectProxy); restored->setParent(parent); }
void CmdRecordSO::recordSO(const HSceneObject& sceneObject) { UINT32 numChildren = mSceneObject->getNumChildren(); HSceneObject* children = nullptr; if (!mRecordHierarchy) { children = bs_stack_new<HSceneObject>(numChildren); for (UINT32 i = 0; i < numChildren; i++) { HSceneObject child = mSceneObject->getChild(i); children[i] = child; child->setParent(HSceneObject()); } } bool isInstantiated = !mSceneObject->hasFlag(SOF_DontInstantiate); mSceneObject->_setFlags(SOF_DontInstantiate); MemorySerializer serializer; mSerializedObject = serializer.encode(mSceneObject.get(), mSerializedObjectSize); if (isInstantiated) mSceneObject->_unsetFlags(SOF_DontInstantiate); mSceneObjectProxy = EditorUtility::createProxy(mSceneObject); if (!mRecordHierarchy) { for (UINT32 i = 0; i < numChildren; i++) children[i]->setParent(sceneObject->getHandle()); bs_stack_delete(children, numChildren); } }